Commit 933ed4d3e9f226a21274ff33ebc735d50d5f0be9

Authored by Stéphane Raimbault
1 parent a5bfc756

Change API modbus_mapping_(offsets_new) to (new_start_address)

Related to 52ab1bbea760ed8eaca184f7d875a2f52a116d0f.
The arguments have been changed (see documentation).

https://groups.google.com/d/msg/libmodbus/aXO8nBzW4Ew/uVGTDmvvBAAJ
doc/Makefile.am
@@ -15,7 +15,7 @@ TXT3 = \ @@ -15,7 +15,7 @@ TXT3 = \
15 modbus_get_socket.txt \ 15 modbus_get_socket.txt \
16 modbus_mapping_free.txt \ 16 modbus_mapping_free.txt \
17 modbus_mapping_new.txt \ 17 modbus_mapping_new.txt \
18 - modbus_mapping_offset_new.txt \ 18 + modbus_mapping_new_start_address.txt \
19 modbus_mask_write_register.txt \ 19 modbus_mask_write_register.txt \
20 modbus_new_rtu.txt \ 20 modbus_new_rtu.txt \
21 modbus_new_tcp_pi.txt \ 21 modbus_new_tcp_pi.txt \
doc/modbus_mapping_new.txt
@@ -18,8 +18,9 @@ The *modbus_mapping_new()* function shall allocate four arrays to store bits, @@ -18,8 +18,9 @@ The *modbus_mapping_new()* function shall allocate four arrays to store bits,
18 input bits, registers and inputs registers. The pointers are stored in 18 input bits, registers and inputs registers. The pointers are stored in
19 modbus_mapping_t structure. All values of the arrays are initialized to zero. 19 modbus_mapping_t structure. All values of the arrays are initialized to zero.
20 20
21 -This function is equivalent to a call of the _modbus_mapping_offset_new()_ function  
22 -with all offsets set to zero. 21 +This function is equivalent to a call of the
  22 +linkmb:modbus_mapping_new_start_address[3] function with all start addresses to
  23 +`0`.
23 24
24 If it isn't necessary to allocate an array for a specific type of data, you can 25 If it isn't necessary to allocate an array for a specific type of data, you can
25 pass the zero value in argument, the associated pointer will be NULL. 26 pass the zero value in argument, the associated pointer will be NULL.
@@ -59,6 +60,7 @@ if (mb_mapping == NULL) { @@ -59,6 +60,7 @@ if (mb_mapping == NULL) {
59 SEE ALSO 60 SEE ALSO
60 -------- 61 --------
61 linkmb:modbus_mapping_free[3] 62 linkmb:modbus_mapping_free[3]
  63 +linkmb:modbus_mapping_new_start_address[3]
62 64
63 65
64 AUTHORS 66 AUTHORS
doc/modbus_mapping_offset_new.txt renamed to doc/modbus_mapping_new_start_address.txt
1 -modbus_mapping_offset_new(3)  
2 -============================ 1 +modbus_mapping_new_start_address(3)
  2 +===================================
3 3
4 4
5 NAME 5 NAME
6 ---- 6 ----
7 -modbus_mapping_offset_new - allocate four arrays of bits and registers 7 +modbus_mapping_new_start_address - allocate four arrays of bits and registers accessible from their starting addresses
8 8
9 9
10 SYNOPSIS 10 SYNOPSIS
11 -------- 11 --------
12 -*modbus_mapping_t* modbus_mapping_new(int 'nb_bits', int 'offset_bits',  
13 - int 'nb_input_bits', int 'offset_input_bits',  
14 - int 'nb_registers', int 'offset_registers',  
15 - int 'nb_input_registers', int 'offset_input_registers');* 12 +*modbus_mapping_t* modbus_mapping_new_start_address(int 'start_bits', int 'nb_bits',
  13 + int 'start_input_bits', int 'nb_input_bits',
  14 + int 'start_registers', int 'nb_registers',
  15 + int 'start_input_registers', int 'nb_input_registers');*
16 16
17 17
18 DESCRIPTION 18 DESCRIPTION
19 ----------- 19 -----------
20 -The _modbus_mapping_offset_new()_ function shall allocate four arrays to store bits,  
21 -input bits, registers and inputs registers. The pointers are stored in  
22 -modbus_mapping_t structure. All values of the arrays are initialized to zero. 20 +The _modbus_mapping_new_start_address()_ function shall allocate four arrays to
  21 +store bits, input bits, registers and inputs registers. The pointers are stored
  22 +in modbus_mapping_t structure. All values of the arrays are initialized to zero.
23 23
24 -The different offsets make it possible to place the mapping at any address in  
25 -each address space. 24 +The different starting adresses make it possible to place the mapping at any
  25 +address in each address space. This way, you can give access to values stored
  26 +at high adresses without allocating memory from the address zero, for eg. to
  27 +make available registers from 10000 to 10009, you can use:
  28 +
  29 +[source,c]
  30 +-------------------
  31 +mb_mapping = modbus_mapping_offset_start_address(0, 0, 0, 0, 10000, 10, 0, 0);
  32 +-------------------
  33 +
  34 +With this code, only 10 registers (`uint16_t`) are allocated.
26 35
27 If it isn't necessary to allocate an array for a specific type of data, you can 36 If it isn't necessary to allocate an array for a specific type of data, you can
28 pass the zero value in argument, the associated pointer will be NULL. 37 pass the zero value in argument, the associated pointer will be NULL.
@@ -46,11 +55,12 @@ EXAMPLE @@ -46,11 +55,12 @@ EXAMPLE
46 ------- 55 -------
47 [source,c] 56 [source,c]
48 ------------------- 57 -------------------
49 -/* The first value of each array is accessible at address 4. */  
50 -mb_mapping = modbus_mapping_offset_new(BITS_ADDRESS + BITS_NB, 4,  
51 - INPUT_BITS_ADDRESS + INPUT_BITS_NB, 4,  
52 - REGISTERS_ADDRESS + REGISTERS_NB, 4,  
53 - INPUT_REGISTERS_ADDRESS + INPUT_REGISTERS_NB, 4); 58 +/* The first value of each array is accessible at the defined address.
  59 + The end address is ADDRESS + NB - 1. */
  60 +mb_mapping = modbus_mapping_offset_start_address(BITS_ADDRESS, BITS_NB,
  61 + INPUT_BITS_ADDRESS, INPUT_BITS_NB,
  62 + REGISTERS_ADDRESS, REGISTERS_NB,
  63 + INPUT_REGISTERS_ADDRESS, INPUT_REGISTERS_NB);
54 if (mb_mapping == NULL) { 64 if (mb_mapping == NULL) {
55 fprintf(stderr, "Failed to allocate the mapping: %s\n", 65 fprintf(stderr, "Failed to allocate the mapping: %s\n",
56 modbus_strerror(errno)); 66 modbus_strerror(errno));
@@ -61,6 +71,7 @@ if (mb_mapping == NULL) { @@ -61,6 +71,7 @@ if (mb_mapping == NULL) {
61 71
62 SEE ALSO 72 SEE ALSO
63 -------- 73 --------
  74 +linkmb:modbus_mapping_new[3]
64 linkmb:modbus_mapping_free[3] 75 linkmb:modbus_mapping_free[3]
65 76
66 77
src/modbus.c
@@ -630,8 +630,8 @@ static int check_confirmation(modbus_t *ctx, uint8_t *req, @@ -630,8 +630,8 @@ static int check_confirmation(modbus_t *ctx, uint8_t *req,
630 return rc; 630 return rc;
631 } 631 }
632 632
633 -static int response_io_status(int address, int nb,  
634 - uint8_t *tab_io_status, 633 +static int response_io_status(uint8_t *tab_io_status,
  634 + int address, int nb,
635 uint8_t *rsp, int offset) 635 uint8_t *rsp, int offset)
636 { 636 {
637 int shift = 0; 637 int shift = 0;
@@ -639,7 +639,7 @@ static int response_io_status(int address, int nb, @@ -639,7 +639,7 @@ static int response_io_status(int address, int nb,
639 int one_byte = 0; 639 int one_byte = 0;
640 int i; 640 int i;
641 641
642 - for (i = address; i < address+nb; i++) { 642 + for (i = address; i < address + nb; i++) {
643 one_byte |= tab_io_status[i] << shift; 643 one_byte |= tab_io_status[i] << shift;
644 if (shift == 7) { 644 if (shift == 7) {
645 /* Byte is full */ 645 /* Byte is full */
@@ -706,7 +706,9 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -706,7 +706,9 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
706 switch (function) { 706 switch (function) {
707 case MODBUS_FC_READ_COILS: { 707 case MODBUS_FC_READ_COILS: {
708 int nb = (req[offset + 3] << 8) + req[offset + 4]; 708 int nb = (req[offset + 3] << 8) + req[offset + 4];
709 - int addr = address - mb_mapping->offset_bits; 709 + /* The mapping can be shifted to reduce memory consumption and it
  710 + doesn't always start at address zero. */
  711 + int mapping_address = address - mb_mapping->start_bits;
710 712
711 if (nb < 1 || MODBUS_MAX_READ_BITS < nb) { 713 if (nb < 1 || MODBUS_MAX_READ_BITS < nb) {
712 if (ctx->debug) { 714 if (ctx->debug) {
@@ -719,10 +721,11 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -719,10 +721,11 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
719 rsp_length = response_exception( 721 rsp_length = response_exception(
720 ctx, &sft, 722 ctx, &sft,
721 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp); 723 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp);
722 - } else if (address < mb_mapping->offset_bits || (addr + nb) > mb_mapping->nb_bits) { 724 + } else if (mapping_address < 0 ||
  725 + (mapping_address + nb) > mb_mapping->nb_bits) {
723 if (ctx->debug) { 726 if (ctx->debug) {
724 fprintf(stderr, "Illegal data address 0x%0X in read_bits\n", 727 fprintf(stderr, "Illegal data address 0x%0X in read_bits\n",
725 - address < mb_mapping->offset_bits ? address : address + nb); 728 + mapping_address < 0 ? address : address + nb);
726 } 729 }
727 rsp_length = response_exception( 730 rsp_length = response_exception(
728 ctx, &sft, 731 ctx, &sft,
@@ -730,8 +733,8 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -730,8 +733,8 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
730 } else { 733 } else {
731 rsp_length = ctx->backend->build_response_basis(&sft, rsp); 734 rsp_length = ctx->backend->build_response_basis(&sft, rsp);
732 rsp[rsp_length++] = (nb / 8) + ((nb % 8) ? 1 : 0); 735 rsp[rsp_length++] = (nb / 8) + ((nb % 8) ? 1 : 0);
733 - rsp_length = response_io_status(addr, nb,  
734 - mb_mapping->tab_bits, 736 + rsp_length = response_io_status(mb_mapping->tab_bits,
  737 + mapping_address, nb,
735 rsp, rsp_length); 738 rsp, rsp_length);
736 } 739 }
737 } 740 }
@@ -740,7 +743,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -740,7 +743,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
740 /* Similar to coil status (but too many arguments to use a 743 /* Similar to coil status (but too many arguments to use a
741 * function) */ 744 * function) */
742 int nb = (req[offset + 3] << 8) + req[offset + 4]; 745 int nb = (req[offset + 3] << 8) + req[offset + 4];
743 - int addr = address - mb_mapping->offset_input_bits; 746 + int mapping_address = address - mb_mapping->start_input_bits;
744 747
745 if (nb < 1 || MODBUS_MAX_READ_BITS < nb) { 748 if (nb < 1 || MODBUS_MAX_READ_BITS < nb) {
746 if (ctx->debug) { 749 if (ctx->debug) {
@@ -753,10 +756,11 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -753,10 +756,11 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
753 rsp_length = response_exception( 756 rsp_length = response_exception(
754 ctx, &sft, 757 ctx, &sft,
755 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp); 758 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp);
756 - } else if (address < mb_mapping->offset_input_bits || (addr + nb) > mb_mapping->nb_input_bits) { 759 + } else if (mapping_address < 0 ||
  760 + (mapping_address + nb) > mb_mapping->nb_input_bits) {
757 if (ctx->debug) { 761 if (ctx->debug) {
758 fprintf(stderr, "Illegal data address 0x%0X in read_input_bits\n", 762 fprintf(stderr, "Illegal data address 0x%0X in read_input_bits\n",
759 - address < mb_mapping->offset_input_bits ? address : address + nb); 763 + mapping_address < 0 ? address : address + nb);
760 } 764 }
761 rsp_length = response_exception( 765 rsp_length = response_exception(
762 ctx, &sft, 766 ctx, &sft,
@@ -764,15 +768,15 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -764,15 +768,15 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
764 } else { 768 } else {
765 rsp_length = ctx->backend->build_response_basis(&sft, rsp); 769 rsp_length = ctx->backend->build_response_basis(&sft, rsp);
766 rsp[rsp_length++] = (nb / 8) + ((nb % 8) ? 1 : 0); 770 rsp[rsp_length++] = (nb / 8) + ((nb % 8) ? 1 : 0);
767 - rsp_length = response_io_status(addr, nb,  
768 - mb_mapping->tab_input_bits, 771 + rsp_length = response_io_status(mb_mapping->tab_input_bits,
  772 + mapping_address, nb,
769 rsp, rsp_length); 773 rsp, rsp_length);
770 } 774 }
771 } 775 }
772 break; 776 break;
773 case MODBUS_FC_READ_HOLDING_REGISTERS: { 777 case MODBUS_FC_READ_HOLDING_REGISTERS: {
774 int nb = (req[offset + 3] << 8) + req[offset + 4]; 778 int nb = (req[offset + 3] << 8) + req[offset + 4];
775 - int addr = address - mb_mapping->offset_registers; 779 + int mapping_address = address - mb_mapping->start_registers;
776 780
777 if (nb < 1 || MODBUS_MAX_READ_REGISTERS < nb) { 781 if (nb < 1 || MODBUS_MAX_READ_REGISTERS < nb) {
778 if (ctx->debug) { 782 if (ctx->debug) {
@@ -785,10 +789,11 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -785,10 +789,11 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
785 rsp_length = response_exception( 789 rsp_length = response_exception(
786 ctx, &sft, 790 ctx, &sft,
787 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp); 791 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp);
788 - } else if (address < mb_mapping->offset_registers || (addr + nb) > mb_mapping->nb_registers) { 792 + } else if (mapping_address < 0 ||
  793 + (mapping_address + nb) > mb_mapping->nb_registers) {
789 if (ctx->debug) { 794 if (ctx->debug) {
790 fprintf(stderr, "Illegal data address 0x%0X in read_registers\n", 795 fprintf(stderr, "Illegal data address 0x%0X in read_registers\n",
791 - address < mb_mapping->offset_registers ? address : address + nb); 796 + mapping_address < 0 ? address : address + nb);
792 } 797 }
793 rsp_length = response_exception( 798 rsp_length = response_exception(
794 ctx, &sft, 799 ctx, &sft,
@@ -798,7 +803,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -798,7 +803,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
798 803
799 rsp_length = ctx->backend->build_response_basis(&sft, rsp); 804 rsp_length = ctx->backend->build_response_basis(&sft, rsp);
800 rsp[rsp_length++] = nb << 1; 805 rsp[rsp_length++] = nb << 1;
801 - for (i = addr; i < addr + nb; i++) { 806 + for (i = mapping_address; i < mapping_address + nb; i++) {
802 rsp[rsp_length++] = mb_mapping->tab_registers[i] >> 8; 807 rsp[rsp_length++] = mb_mapping->tab_registers[i] >> 8;
803 rsp[rsp_length++] = mb_mapping->tab_registers[i] & 0xFF; 808 rsp[rsp_length++] = mb_mapping->tab_registers[i] & 0xFF;
804 } 809 }
@@ -809,7 +814,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -809,7 +814,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
809 /* Similar to holding registers (but too many arguments to use a 814 /* Similar to holding registers (but too many arguments to use a
810 * function) */ 815 * function) */
811 int nb = (req[offset + 3] << 8) + req[offset + 4]; 816 int nb = (req[offset + 3] << 8) + req[offset + 4];
812 - int addr = address - mb_mapping->offset_input_registers; 817 + int mapping_address = address - mb_mapping->start_input_registers;
813 818
814 if (nb < 1 || MODBUS_MAX_READ_REGISTERS < nb) { 819 if (nb < 1 || MODBUS_MAX_READ_REGISTERS < nb) {
815 if (ctx->debug) { 820 if (ctx->debug) {
@@ -822,10 +827,11 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -822,10 +827,11 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
822 rsp_length = response_exception( 827 rsp_length = response_exception(
823 ctx, &sft, 828 ctx, &sft,
824 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp); 829 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp);
825 - } else if (address < mb_mapping->offset_input_registers || (addr + nb) > mb_mapping->nb_input_registers) { 830 + } else if (mapping_address < 0 ||
  831 + (mapping_address + nb) > mb_mapping->nb_input_registers) {
826 if (ctx->debug) { 832 if (ctx->debug) {
827 fprintf(stderr, "Illegal data address 0x%0X in read_input_registers\n", 833 fprintf(stderr, "Illegal data address 0x%0X in read_input_registers\n",
828 - address < mb_mapping->offset_input_registers ? address : address + nb); 834 + mapping_address < 0 ? address : address + nb);
829 } 835 }
830 rsp_length = response_exception( 836 rsp_length = response_exception(
831 ctx, &sft, 837 ctx, &sft,
@@ -835,7 +841,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -835,7 +841,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
835 841
836 rsp_length = ctx->backend->build_response_basis(&sft, rsp); 842 rsp_length = ctx->backend->build_response_basis(&sft, rsp);
837 rsp[rsp_length++] = nb << 1; 843 rsp[rsp_length++] = nb << 1;
838 - for (i = addr; i < addr + nb; i++) { 844 + for (i = mapping_address; i < mapping_address + nb; i++) {
839 rsp[rsp_length++] = mb_mapping->tab_input_registers[i] >> 8; 845 rsp[rsp_length++] = mb_mapping->tab_input_registers[i] >> 8;
840 rsp[rsp_length++] = mb_mapping->tab_input_registers[i] & 0xFF; 846 rsp[rsp_length++] = mb_mapping->tab_input_registers[i] & 0xFF;
841 } 847 }
@@ -843,9 +849,9 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -843,9 +849,9 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
843 } 849 }
844 break; 850 break;
845 case MODBUS_FC_WRITE_SINGLE_COIL: { 851 case MODBUS_FC_WRITE_SINGLE_COIL: {
846 - int addr = address - mb_mapping->offset_bits; 852 + int mapping_address = address - mb_mapping->start_bits;
847 853
848 - if (address < mb_mapping->offset_bits || addr >= mb_mapping->nb_bits) { 854 + if (mapping_address < 0 || mapping_address >= mb_mapping->nb_bits) {
849 if (ctx->debug) { 855 if (ctx->debug) {
850 fprintf(stderr, 856 fprintf(stderr,
851 "Illegal data address 0x%0X in write_bit\n", 857 "Illegal data address 0x%0X in write_bit\n",
@@ -858,7 +864,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -858,7 +864,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
858 int data = (req[offset + 3] << 8) + req[offset + 4]; 864 int data = (req[offset + 3] << 8) + req[offset + 4];
859 865
860 if (data == 0xFF00 || data == 0x0) { 866 if (data == 0xFF00 || data == 0x0) {
861 - mb_mapping->tab_bits[addr] = (data) ? ON : OFF; 867 + mb_mapping->tab_bits[mapping_address] = data ? ON : OFF;
862 memcpy(rsp, req, req_length); 868 memcpy(rsp, req, req_length);
863 rsp_length = req_length; 869 rsp_length = req_length;
864 } else { 870 } else {
@@ -875,9 +881,9 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -875,9 +881,9 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
875 } 881 }
876 break; 882 break;
877 case MODBUS_FC_WRITE_SINGLE_REGISTER: { 883 case MODBUS_FC_WRITE_SINGLE_REGISTER: {
878 - int addr = address - mb_mapping->offset_registers; 884 + int mapping_address = address - mb_mapping->start_registers;
879 885
880 - if (address < mb_mapping->offset_registers || addr >= mb_mapping->nb_registers) { 886 + if (mapping_address < 0 || mapping_address >= mb_mapping->nb_registers) {
881 if (ctx->debug) { 887 if (ctx->debug) {
882 fprintf(stderr, "Illegal data address 0x%0X in write_register\n", 888 fprintf(stderr, "Illegal data address 0x%0X in write_register\n",
883 address); 889 address);
@@ -888,7 +894,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -888,7 +894,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
888 } else { 894 } else {
889 int data = (req[offset + 3] << 8) + req[offset + 4]; 895 int data = (req[offset + 3] << 8) + req[offset + 4];
890 896
891 - mb_mapping->tab_registers[addr] = data; 897 + mb_mapping->tab_registers[mapping_address] = data;
892 memcpy(rsp, req, req_length); 898 memcpy(rsp, req, req_length);
893 rsp_length = req_length; 899 rsp_length = req_length;
894 } 900 }
@@ -896,7 +902,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -896,7 +902,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
896 break; 902 break;
897 case MODBUS_FC_WRITE_MULTIPLE_COILS: { 903 case MODBUS_FC_WRITE_MULTIPLE_COILS: {
898 int nb = (req[offset + 3] << 8) + req[offset + 4]; 904 int nb = (req[offset + 3] << 8) + req[offset + 4];
899 - int addr = address - mb_mapping->offset_bits; 905 + int mapping_address = address - mb_mapping->start_bits;
900 906
901 if (nb < 1 || MODBUS_MAX_WRITE_BITS < nb) { 907 if (nb < 1 || MODBUS_MAX_WRITE_BITS < nb) {
902 if (ctx->debug) { 908 if (ctx->debug) {
@@ -912,17 +918,19 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -912,17 +918,19 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
912 rsp_length = response_exception( 918 rsp_length = response_exception(
913 ctx, &sft, 919 ctx, &sft,
914 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp); 920 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp);
915 - } else if (address < mb_mapping->offset_bits || (addr + nb) > mb_mapping->nb_bits) { 921 + } else if (mapping_address < 0 ||
  922 + (mapping_address + nb) > mb_mapping->nb_bits) {
916 if (ctx->debug) { 923 if (ctx->debug) {
917 fprintf(stderr, "Illegal data address 0x%0X in write_bits\n", 924 fprintf(stderr, "Illegal data address 0x%0X in write_bits\n",
918 - address < mb_mapping->offset_bits ? address : address + nb); 925 + mapping_address < 0 ? address : address + nb);
919 } 926 }
920 rsp_length = response_exception( 927 rsp_length = response_exception(
921 ctx, &sft, 928 ctx, &sft,
922 MODBUS_EXCEPTION_ILLEGAL_DATA_ADDRESS, rsp); 929 MODBUS_EXCEPTION_ILLEGAL_DATA_ADDRESS, rsp);
923 } else { 930 } else {
924 /* 6 = byte count */ 931 /* 6 = byte count */
925 - modbus_set_bits_from_bytes(mb_mapping->tab_bits, addr, nb, &req[offset + 6]); 932 + modbus_set_bits_from_bytes(mb_mapping->tab_bits, mapping_address, nb,
  933 + &req[offset + 6]);
926 934
927 rsp_length = ctx->backend->build_response_basis(&sft, rsp); 935 rsp_length = ctx->backend->build_response_basis(&sft, rsp);
928 /* 4 to copy the bit address (2) and the quantity of bits */ 936 /* 4 to copy the bit address (2) and the quantity of bits */
@@ -933,7 +941,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -933,7 +941,7 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
933 break; 941 break;
934 case MODBUS_FC_WRITE_MULTIPLE_REGISTERS: { 942 case MODBUS_FC_WRITE_MULTIPLE_REGISTERS: {
935 int nb = (req[offset + 3] << 8) + req[offset + 4]; 943 int nb = (req[offset + 3] << 8) + req[offset + 4];
936 - int addr = address - mb_mapping->offset_registers; 944 + int mapping_address = address - mb_mapping->start_registers;
937 945
938 if (nb < 1 || MODBUS_MAX_WRITE_REGISTERS < nb) { 946 if (nb < 1 || MODBUS_MAX_WRITE_REGISTERS < nb) {
939 if (ctx->debug) { 947 if (ctx->debug) {
@@ -949,17 +957,18 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -949,17 +957,18 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
949 rsp_length = response_exception( 957 rsp_length = response_exception(
950 ctx, &sft, 958 ctx, &sft,
951 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp); 959 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp);
952 - } else if (address < mb_mapping->offset_registers || (addr + nb) > mb_mapping->nb_registers) { 960 + } else if (mapping_address < 0 ||
  961 + (mapping_address + nb) > mb_mapping->nb_registers) {
953 if (ctx->debug) { 962 if (ctx->debug) {
954 fprintf(stderr, "Illegal data address 0x%0X in write_registers\n", 963 fprintf(stderr, "Illegal data address 0x%0X in write_registers\n",
955 - address < mb_mapping->offset_registers ? address : address + nb); 964 + mapping_address < 0 ? address : address + nb);
956 } 965 }
957 rsp_length = response_exception( 966 rsp_length = response_exception(
958 ctx, &sft, 967 ctx, &sft,
959 MODBUS_EXCEPTION_ILLEGAL_DATA_ADDRESS, rsp); 968 MODBUS_EXCEPTION_ILLEGAL_DATA_ADDRESS, rsp);
960 } else { 969 } else {
961 int i, j; 970 int i, j;
962 - for (i = addr, j = 6; i < addr + nb; i++, j += 2) { 971 + for (i = mapping_address, j = 6; i < mapping_address + nb; i++, j += 2) {
963 /* 6 and 7 = first value */ 972 /* 6 and 7 = first value */
964 mb_mapping->tab_registers[i] = 973 mb_mapping->tab_registers[i] =
965 (req[offset + j] << 8) + req[offset + j + 1]; 974 (req[offset + j] << 8) + req[offset + j + 1];
@@ -997,9 +1006,9 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -997,9 +1006,9 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
997 return -1; 1006 return -1;
998 break; 1007 break;
999 case MODBUS_FC_MASK_WRITE_REGISTER: { 1008 case MODBUS_FC_MASK_WRITE_REGISTER: {
1000 - int addr = address - mb_mapping->offset_registers; 1009 + int mapping_address = address - mb_mapping->start_registers;
1001 1010
1002 - if (address < mb_mapping->offset_registers || addr >= mb_mapping->nb_registers) { 1011 + if (mapping_address < 0 || mapping_address >= mb_mapping->nb_registers) {
1003 if (ctx->debug) { 1012 if (ctx->debug) {
1004 fprintf(stderr, "Illegal data address 0x%0X in write_register\n", 1013 fprintf(stderr, "Illegal data address 0x%0X in write_register\n",
1005 address); 1014 address);
@@ -1008,12 +1017,12 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -1008,12 +1017,12 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
1008 ctx, &sft, 1017 ctx, &sft,
1009 MODBUS_EXCEPTION_ILLEGAL_DATA_ADDRESS, rsp); 1018 MODBUS_EXCEPTION_ILLEGAL_DATA_ADDRESS, rsp);
1010 } else { 1019 } else {
1011 - uint16_t data = mb_mapping->tab_registers[addr]; 1020 + uint16_t data = mb_mapping->tab_registers[mapping_address];
1012 uint16_t and = (req[offset + 3] << 8) + req[offset + 4]; 1021 uint16_t and = (req[offset + 3] << 8) + req[offset + 4];
1013 uint16_t or = (req[offset + 5] << 8) + req[offset + 6]; 1022 uint16_t or = (req[offset + 5] << 8) + req[offset + 6];
1014 1023
1015 data = (data & and) | (or & (~and)); 1024 data = (data & and) | (or & (~and));
1016 - mb_mapping->tab_registers[addr] = data; 1025 + mb_mapping->tab_registers[mapping_address] = data;
1017 memcpy(rsp, req, req_length); 1026 memcpy(rsp, req, req_length);
1018 rsp_length = req_length; 1027 rsp_length = req_length;
1019 } 1028 }
@@ -1024,8 +1033,8 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -1024,8 +1033,8 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
1024 uint16_t address_write = (req[offset + 5] << 8) + req[offset + 6]; 1033 uint16_t address_write = (req[offset + 5] << 8) + req[offset + 6];
1025 int nb_write = (req[offset + 7] << 8) + req[offset + 8]; 1034 int nb_write = (req[offset + 7] << 8) + req[offset + 8];
1026 int nb_write_bytes = req[offset + 9]; 1035 int nb_write_bytes = req[offset + 9];
1027 - int addr = address - mb_mapping->offset_registers;  
1028 - int addr_write = address_write - mb_mapping->offset_registers; 1036 + int mapping_address = address - mb_mapping->start_registers;
  1037 + int mapping_address_write = address_write - mb_mapping->start_registers;
1029 1038
1030 if (nb_write < 1 || MODBUS_MAX_WR_WRITE_REGISTERS < nb_write || 1039 if (nb_write < 1 || MODBUS_MAX_WR_WRITE_REGISTERS < nb_write ||
1031 nb < 1 || MODBUS_MAX_WR_READ_REGISTERS < nb || 1040 nb < 1 || MODBUS_MAX_WR_READ_REGISTERS < nb ||
@@ -1041,15 +1050,15 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -1041,15 +1050,15 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
1041 rsp_length = response_exception( 1050 rsp_length = response_exception(
1042 ctx, &sft, 1051 ctx, &sft,
1043 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp); 1052 MODBUS_EXCEPTION_ILLEGAL_DATA_VALUE, rsp);
1044 - } else if (address < mb_mapping->offset_registers ||  
1045 - (addr + nb) > mb_mapping->nb_registers ||  
1046 - address_write < mb_mapping->offset_registers ||  
1047 - (addr_write + nb_write) > mb_mapping->nb_registers) { 1053 + } else if (mapping_address < 0 ||
  1054 + (mapping_address + nb) > mb_mapping->nb_registers ||
  1055 + mapping_address < 0 ||
  1056 + (mapping_address_write + nb_write) > mb_mapping->nb_registers) {
1048 if (ctx->debug) { 1057 if (ctx->debug) {
1049 fprintf(stderr, 1058 fprintf(stderr,
1050 "Illegal data read address 0x%0X or write address 0x%0X write_and_read_registers\n", 1059 "Illegal data read address 0x%0X or write address 0x%0X write_and_read_registers\n",
1051 - address < mb_mapping->offset_registers ? address : address + nb,  
1052 - address_write < mb_mapping->offset_registers ? address_write : address_write + nb_write); 1060 + mapping_address < 0 ? address : address + nb,
  1061 + mapping_address_write < 0 ? address_write : address_write + nb_write);
1053 } 1062 }
1054 rsp_length = response_exception(ctx, &sft, 1063 rsp_length = response_exception(ctx, &sft,
1055 MODBUS_EXCEPTION_ILLEGAL_DATA_ADDRESS, rsp); 1064 MODBUS_EXCEPTION_ILLEGAL_DATA_ADDRESS, rsp);
@@ -1060,13 +1069,14 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req, @@ -1060,13 +1069,14 @@ int modbus_reply(modbus_t *ctx, const uint8_t *req,
1060 1069
1061 /* Write first. 1070 /* Write first.
1062 10 and 11 are the offset of the first values to write */ 1071 10 and 11 are the offset of the first values to write */
1063 - for (i = addr_write, j = 10; i < addr_write + nb_write; i++, j += 2) { 1072 + for (i = mapping_address_write, j = 10;
  1073 + i < mapping_address_write + nb_write; i++, j += 2) {
1064 mb_mapping->tab_registers[i] = 1074 mb_mapping->tab_registers[i] =
1065 (req[offset + j] << 8) + req[offset + j + 1]; 1075 (req[offset + j] << 8) + req[offset + j + 1];
1066 } 1076 }
1067 1077
1068 /* and read the data for the response */ 1078 /* and read the data for the response */
1069 - for (i = addr; i < addr + nb; i++) { 1079 + for (i = mapping_address; i < mapping_address + nb; i++) {
1070 rsp[rsp_length++] = mb_mapping->tab_registers[i] >> 8; 1080 rsp[rsp_length++] = mb_mapping->tab_registers[i] >> 8;
1071 rsp[rsp_length++] = mb_mapping->tab_registers[i] & 0xFF; 1081 rsp[rsp_length++] = mb_mapping->tab_registers[i] & 0xFF;
1072 } 1082 }
@@ -1807,12 +1817,14 @@ int modbus_set_debug(modbus_t *ctx, int flag) @@ -1807,12 +1817,14 @@ int modbus_set_debug(modbus_t *ctx, int flag)
1807 /* Allocates 4 arrays to store bits, input bits, registers and inputs 1817 /* Allocates 4 arrays to store bits, input bits, registers and inputs
1808 registers. The pointers are stored in modbus_mapping structure. 1818 registers. The pointers are stored in modbus_mapping structure.
1809 1819
1810 - The modbus_mapping_offset_new() function shall return the new allocated structure if  
1811 - successful. Otherwise it shall return NULL and set errno to ENOMEM. */  
1812 -modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits,  
1813 - int nb_input_bits, int offset_input_bits,  
1814 - int nb_registers, int offset_registers,  
1815 - int nb_input_registers, int offset_input_registers) 1820 + The modbus_mapping_new_ranges() function shall return the new allocated
  1821 + structure if successful. Otherwise it shall return NULL and set errno to
  1822 + ENOMEM. */
  1823 +modbus_mapping_t* modbus_mapping_new_start_address(
  1824 + unsigned int start_bits, unsigned int nb_bits,
  1825 + unsigned int start_input_bits, unsigned int nb_input_bits,
  1826 + unsigned int start_registers, unsigned int nb_registers,
  1827 + unsigned int start_input_registers, unsigned int nb_input_registers)
1816 { 1828 {
1817 modbus_mapping_t *mb_mapping; 1829 modbus_mapping_t *mb_mapping;
1818 1830
@@ -1823,7 +1835,7 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits, @@ -1823,7 +1835,7 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits,
1823 1835
1824 /* 0X */ 1836 /* 0X */
1825 mb_mapping->nb_bits = nb_bits; 1837 mb_mapping->nb_bits = nb_bits;
1826 - mb_mapping->offset_bits = offset_bits; 1838 + mb_mapping->start_bits = start_bits;
1827 if (nb_bits == 0) { 1839 if (nb_bits == 0) {
1828 mb_mapping->tab_bits = NULL; 1840 mb_mapping->tab_bits = NULL;
1829 } else { 1841 } else {
@@ -1839,7 +1851,7 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits, @@ -1839,7 +1851,7 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits,
1839 1851
1840 /* 1X */ 1852 /* 1X */
1841 mb_mapping->nb_input_bits = nb_input_bits; 1853 mb_mapping->nb_input_bits = nb_input_bits;
1842 - mb_mapping->offset_input_bits = offset_input_bits; 1854 + mb_mapping->start_input_bits = start_input_bits;
1843 if (nb_input_bits == 0) { 1855 if (nb_input_bits == 0) {
1844 mb_mapping->tab_input_bits = NULL; 1856 mb_mapping->tab_input_bits = NULL;
1845 } else { 1857 } else {
@@ -1855,7 +1867,7 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits, @@ -1855,7 +1867,7 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits,
1855 1867
1856 /* 4X */ 1868 /* 4X */
1857 mb_mapping->nb_registers = nb_registers; 1869 mb_mapping->nb_registers = nb_registers;
1858 - mb_mapping->offset_registers = offset_registers; 1870 + mb_mapping->start_registers = start_registers;
1859 if (nb_registers == 0) { 1871 if (nb_registers == 0) {
1860 mb_mapping->tab_registers = NULL; 1872 mb_mapping->tab_registers = NULL;
1861 } else { 1873 } else {
@@ -1872,7 +1884,7 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits, @@ -1872,7 +1884,7 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits,
1872 1884
1873 /* 3X */ 1885 /* 3X */
1874 mb_mapping->nb_input_registers = nb_input_registers; 1886 mb_mapping->nb_input_registers = nb_input_registers;
1875 - mb_mapping->offset_input_registers = offset_input_registers; 1887 + mb_mapping->start_input_registers = start_input_registers;
1876 if (nb_input_registers == 0) { 1888 if (nb_input_registers == 0) {
1877 mb_mapping->tab_input_registers = NULL; 1889 mb_mapping->tab_input_registers = NULL;
1878 } else { 1890 } else {
@@ -1895,7 +1907,8 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits, @@ -1895,7 +1907,8 @@ modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits,
1895 modbus_mapping_t* modbus_mapping_new(int nb_bits, int nb_input_bits, 1907 modbus_mapping_t* modbus_mapping_new(int nb_bits, int nb_input_bits,
1896 int nb_registers, int nb_input_registers) 1908 int nb_registers, int nb_input_registers)
1897 { 1909 {
1898 - return modbus_mapping_offset_new(nb_bits, 0, nb_input_bits, 0, nb_registers, 0, nb_input_registers, 0); 1910 + return modbus_mapping_new_start_address(
  1911 + 0, nb_bits, 0, nb_input_bits, 0, nb_registers, 0, nb_input_registers);
1899 } 1912 }
1900 1913
1901 /* Frees the 4 arrays */ 1914 /* Frees the 4 arrays */
src/modbus.h
@@ -156,13 +156,13 @@ typedef struct _modbus modbus_t; @@ -156,13 +156,13 @@ typedef struct _modbus modbus_t;
156 156
157 typedef struct { 157 typedef struct {
158 int nb_bits; 158 int nb_bits;
159 - int offset_bits; 159 + int start_bits;
160 int nb_input_bits; 160 int nb_input_bits;
161 - int offset_input_bits; 161 + int start_input_bits;
162 int nb_input_registers; 162 int nb_input_registers;
163 - int offset_input_registers; 163 + int start_input_registers;
164 int nb_registers; 164 int nb_registers;
165 - int offset_registers; 165 + int start_registers;
166 uint8_t *tab_bits; 166 uint8_t *tab_bits;
167 uint8_t *tab_input_bits; 167 uint8_t *tab_input_bits;
168 uint16_t *tab_input_registers; 168 uint16_t *tab_input_registers;
@@ -213,12 +213,14 @@ MODBUS_API int modbus_write_and_read_registers(modbus_t *ctx, int write_addr, in @@ -213,12 +213,14 @@ MODBUS_API int modbus_write_and_read_registers(modbus_t *ctx, int write_addr, in
213 uint16_t *dest); 213 uint16_t *dest);
214 MODBUS_API int modbus_report_slave_id(modbus_t *ctx, int max_dest, uint8_t *dest); 214 MODBUS_API int modbus_report_slave_id(modbus_t *ctx, int max_dest, uint8_t *dest);
215 215
216 -MODBUS_API modbus_mapping_t* modbus_mapping_offset_new(int nb_bits, int offset_bits,  
217 - int nb_input_bits, int offset_input_bits,  
218 - int nb_registers, int offset_registers,  
219 - int nb_input_registers, int offset_input_registers); 216 +MODBUS_API modbus_mapping_t* modbus_mapping_new_start_address(
  217 + unsigned int start_bits, unsigned int nb_bits,
  218 + unsigned int start_input_bits, unsigned int nb_input_bits,
  219 + unsigned int start_registers, unsigned int nb_registers,
  220 + unsigned int start_input_registers, unsigned int nb_input_registers);
  221 +
220 MODBUS_API modbus_mapping_t* modbus_mapping_new(int nb_bits, int nb_input_bits, 222 MODBUS_API modbus_mapping_t* modbus_mapping_new(int nb_bits, int nb_input_bits,
221 - int nb_registers, int nb_input_registers); 223 + int nb_registers, int nb_input_registers);
222 MODBUS_API void modbus_mapping_free(modbus_mapping_t *mb_mapping); 224 MODBUS_API void modbus_mapping_free(modbus_mapping_t *mb_mapping);
223 225
224 MODBUS_API int modbus_send_raw_request(modbus_t *ctx, uint8_t *raw_req, int raw_req_length); 226 MODBUS_API int modbus_send_raw_request(modbus_t *ctx, uint8_t *raw_req, int raw_req_length);