mirror of
https://github.com/esphome/esphome.git
synced 2026-10-06 02:51:29 +00:00
[modbus] Only apply turnaround delay after broadcasts (#17209)
This commit is contained in:
@@ -92,10 +92,14 @@ int32_t Modbus::tx_delay_remaining() {
|
||||
|
||||
int32_t ModbusClientHub::tx_delay_remaining() {
|
||||
const uint32_t now = millis();
|
||||
return std::max({(int32_t) 0,
|
||||
(int32_t) (this->last_send_tx_offset_ + this->frame_delay_ms_ + this->turnaround_delay_ms_ -
|
||||
(now - this->last_send_)),
|
||||
(int32_t) (this->frame_delay_ms_ + this->turnaround_delay_ms_ - (now - this->last_modbus_byte_))});
|
||||
// Turnaround delay only applies after a broadcast: no response is expected, so we must give listening devices
|
||||
// quiet time to process it before the next request. For normal unicast request/response the received reply already
|
||||
// provides the inter-frame timing, so adding turnaround there just throttles throughput.
|
||||
const uint16_t turnaround = this->last_send_was_broadcast_ ? this->turnaround_delay_ms_ : 0;
|
||||
return std::max(
|
||||
{(int32_t) 0,
|
||||
(int32_t) (this->last_send_tx_offset_ + this->frame_delay_ms_ + turnaround - (now - this->last_send_)),
|
||||
(int32_t) (this->frame_delay_ms_ + turnaround - (now - this->last_modbus_byte_))});
|
||||
}
|
||||
|
||||
bool Modbus::tx_blocked() {
|
||||
@@ -396,6 +400,7 @@ bool Modbus::send_frame_(const ModbusFrame &frame) {
|
||||
format_hex_pretty_to(hex_buf, frame.data.get(), frame.size), now - this->last_send_,
|
||||
now - this->last_modbus_byte_);
|
||||
this->last_send_ = now;
|
||||
this->last_send_was_broadcast_ = frame.size > 0 && frame.data[0] == 0;
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -411,7 +416,8 @@ void ModbusClientHub::send_next_frame_() {
|
||||
ModbusDeviceCommand &command = this->tx_buffer_.front();
|
||||
|
||||
if (this->send_frame_(command.frame)) {
|
||||
this->waiting_for_response_ = std::move(command);
|
||||
if (!this->last_send_was_broadcast_)
|
||||
this->waiting_for_response_ = std::move(command);
|
||||
} else {
|
||||
if (command.device)
|
||||
command.device->on_modbus_not_sent();
|
||||
|
||||
Reference in New Issue
Block a user