The problem is that on rs485 I get different response lengths. but through the UART connection I began to receive consistently the same length of response
Yesterday you had good solid debug logsâŚ
You said yesterday that this is a bad protocol for rs485 and nothing will work
Modbus library doesnât have output for response from unknown address. Dead end.
So the idea is to use that only for request and grab the data from uart_debug.
When you get it working, the code above should only print the byte count, 8 and 7 to confirm that you have those bytes âon your handsâ.
[18:27:43][C][modbus_controller:345]: ModbusController:
[18:27:43][C][modbus_controller:346]: Address: 0x81
[18:27:44][D][uart_debug:114]: >>> 81:03:00:30:00:01:9B:C5
[18:27:44][D][main:047]: Response data only had 8 bytes!!
[18:27:44][W][modbus:144]: Got Modbus frame from unknown address 0x51!
[18:27:45][D][uart_debug:114]: <<< 51:03:02:00:41:B8:78
[18:27:45][D][main:047]: Response data only had 7 bytes!!
[18:27:48][W][modbus_controller:182]: Duplicate modbus command found: type=0x3 address=48 count=1
[18:27:49][D][uart_debug:114]: >>> 81:03:00:30:00:01:9B:C5
[18:27:50][D][main:047]: Response data only had 8 bytes!!
[18:27:50][W][modbus:144]: Got Modbus frame from unknown address 0x51!
[18:27:50][D][uart_debug:114]: <<< 51:03:02:00:41:B8:78
[18:27:50][D][main:047]: Response data only had 7 bytes!!
[18:27:55][D][uart_debug:114]: >>> 81:03:00:30:00:01:9B:C5
[18:27:55][D][main:047]: Response data only had 8 bytes!!
[18:27:55][W][modbus:144]: Got Modbus frame from unknown address 0x51!
[18:27:55][D][uart_debug:114]: <<< 51:03:02:00:41:B8:78
[18:27:55][D][main:047]: Response data only had 7 bytes!!
uart:
- id: uart_0
baud_rate: 9600
tx_pin: D2
rx_pin: D3
debug:
direction: BOTH
dummy_receiver: true
after:
delimiter: "\n"
sequence:
- lambda: |-
UARTDebug::log_hex(direction, bytes, ':');
ESP_LOGD("main", "Response data only had %d bytes!!", bytes.size() );
std::string str(bytes.begin(), bytes.end());
int temperature = bytes[4]-40;
id(temp).publish_state(temperature);
modbus:
- id: modbus0
uart_id: uart_0
send_wait_time: 1000ms
disable_crc: true
modbus_controller:
- id: bms
address: 0x81
modbus_id: modbus0
command_throttle: 5000ms
update_interval: 10s
setup_priority: -20
sensor:
- platform: template
id: temp
- platform: modbus_controller
modbus_controller_id: bms
name: Temperature 1
address: 0x30
register_type: holding
and i have correct temperature )
Goodâ
Try to add this:
if (bytes.size() == 7) {
ESP_LOGD("main", "Response data &d", bytes[4]);
}
Edit: I didnât see your replay
Thus, to obtain data from one sensor, you need to make 2 sensors. But what to do to get and parse the remaining parameters (voltage, SOCâŚ)?
How many, and what kind of values they are?
about 10-15 parameters
You request them all at once and parse correct bytes to correct sensor
I donât understand how
tell me the first and the last register address
Quite long, I donât know the max you can do, but for 2 it would be:
custom_command: [ 0x81, 0x03, 0x00, 0x00,0x00, 0x02]
for 100
custom_command: [ 0x81, 0x03, 0x00, 0x00,0x00, 0x64]
anyway add this to exclude your request (tx)
if (bytes.size() != 8) {
Edit: not valid for request of 2 registers, but for any other number yes.
I understand this, but how can I then understand that lambda received data from the parameter I need?
first (0x00) is bytes[4]
second (0x01) is bytes[5]
and so on
Actually you could also do it in several requests and use number of registers as a identifier.
For example you request 8 addresses
custom_command: [ 0x81, 0x03, 0x00, 0x52,0x00, 0x08]
it gives you response of 14 bytes
if (bytes.size() == 14) {
int chargingMosStatus = bytes[4];
id(cms).publish_state(chargingMosStatus);
int dischargeMosStatus = bytes[5];
id(dms).publish_state(dischargeMosStatus);
and so on
if request/response sizes are different from each other you can identify them and remap them to right sensors.
thankâs, but why this code donât work
total battery voltage. address 0x38
sensor:
- platform: modbus_controller
modbus_controller_id: bms
name: "Total voltage"
custom_command: [0x81, 0x03, 0x00, 0x38, 0x00, 0x01]
value_type: U_DWORD
lambda: |-
ESP_LOGV("Modbus Sensor TV","Got new data" );
float vv = (data[3]+data[4])* 0.1;
return vv;
and i see
[20:32:01][C][modbus_controller:346]: Address: 0x81
[20:32:03][D][uart_debug:114]: >>> 81:03:00:38:00:01:1A:07
[20:32:03][D][main:047]: Response data only had 8 bytes!!
[20:32:03][D][uart_debug:114]: <<< 51:03:02:01:0A
[20:32:03][D][main:047]: Response data only had 5 bytes!!
[20:32:03][W][modbus:144]: Got Modbus frame from unknown address 0x51!
[20:32:03][D][uart_debug:114]: <<< F9:DF
[20:32:03][D][main:047]: Response data only had 2 bytes!!
[20:32:03][W][modbus_controller:182]: Duplicate modbus command found: type=0x30 address=46809 count=2
[20:32:08][D][uart_debug:114]: >>> 81:03:00:38:00:01:1A:07
my battery voltage is 26.6
266 = 01:0A i see this in answer, but sensor is empty
For multiple reasons.
You already tried to grab the data in modbus_controller and it doesnât have any output for non corresponding slave address. So that data doesnât return anything.
Also, you have 5 bytes response, so there is something else wrong as well.
Why you have to try randomly things if you already have working setup?