Commit cfeca264b4a5bbfdcfe7e2d4ddba9093b88e75f1
Committed by
GitHub
1 parent
27b90ded
address check in single register / coil responses added (#463)
Address check in single register / coil responses added According to Modbus standard the address of single register / coils request and response must match Co-authored-by: Heinrich Gsponer <heinrich.gsponer@siemens.com>
Showing
1 changed file
with
22 additions
and
2 deletions
src/modbus.c
| ... | ... | @@ -555,6 +555,8 @@ static int check_confirmation(modbus_t *ctx, uint8_t *req, |
| 555 | 555 | function < 0x80) { |
| 556 | 556 | int req_nb_value; |
| 557 | 557 | int rsp_nb_value; |
| 558 | + int resp_addr_ok = TRUE; | |
| 559 | + int resp_data_ok = TRUE; | |
| 558 | 560 | |
| 559 | 561 | /* Check function code */ |
| 560 | 562 | if (function != req[offset]) { |
| ... | ... | @@ -591,6 +593,10 @@ static int check_confirmation(modbus_t *ctx, uint8_t *req, |
| 591 | 593 | break; |
| 592 | 594 | case MODBUS_FC_WRITE_MULTIPLE_COILS: |
| 593 | 595 | case MODBUS_FC_WRITE_MULTIPLE_REGISTERS: |
| 596 | + /* address in request and response must be equal */ | |
| 597 | + if ((req[offset + 1] != rsp[offset + 1]) || (req[offset + 2] != rsp[offset + 2])) { | |
| 598 | + resp_addr_ok = FALSE; | |
| 599 | + } | |
| 594 | 600 | /* N Write functions */ |
| 595 | 601 | req_nb_value = (req[offset + 3] << 8) + req[offset + 4]; |
| 596 | 602 | rsp_nb_value = (rsp[offset + 3] << 8) | rsp[offset + 4]; |
| ... | ... | @@ -599,17 +605,31 @@ static int check_confirmation(modbus_t *ctx, uint8_t *req, |
| 599 | 605 | /* Report slave ID (bytes received) */ |
| 600 | 606 | req_nb_value = rsp_nb_value = rsp[offset + 1]; |
| 601 | 607 | break; |
| 608 | + case MODBUS_FC_WRITE_SINGLE_COIL: | |
| 609 | + case MODBUS_FC_WRITE_SINGLE_REGISTER: | |
| 610 | + /* address in request and response must be equal */ | |
| 611 | + if ((req[offset + 1] != rsp[offset + 1]) || (req[offset + 2] != rsp[offset + 2])) { | |
| 612 | + resp_addr_ok = FALSE; | |
| 613 | + } | |
| 614 | + /* data in request and response must be equal */ | |
| 615 | + if ((req[offset + 3] != rsp[offset + 3]) || (req[offset + 4] != rsp[offset + 4])) { | |
| 616 | + resp_data_ok = FALSE; | |
| 617 | + } | |
| 618 | + /* 1 Write functions & others */ | |
| 619 | + req_nb_value = rsp_nb_value = 1; | |
| 620 | + break; | |
| 602 | 621 | default: |
| 603 | 622 | /* 1 Write functions & others */ |
| 604 | 623 | req_nb_value = rsp_nb_value = 1; |
| 624 | + break; | |
| 605 | 625 | } |
| 606 | 626 | |
| 607 | - if (req_nb_value == rsp_nb_value) { | |
| 627 | + if ((req_nb_value == rsp_nb_value) && (resp_addr_ok == TRUE) && (resp_data_ok == TRUE)) { | |
| 608 | 628 | rc = rsp_nb_value; |
| 609 | 629 | } else { |
| 610 | 630 | if (ctx->debug) { |
| 611 | 631 | fprintf(stderr, |
| 612 | - "Quantity not corresponding to the request (%d != %d)\n", | |
| 632 | + "Received data not corresponding to the request (%d != %d)\n", | |
| 613 | 633 | rsp_nb_value, req_nb_value); |
| 614 | 634 | } |
| 615 | 635 | ... | ... |