bandwidth-client.c 6.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225
  1. /*
  2. * Copyright © 2008-2010 Stéphane Raimbault <stephane.raimbault@gmail.com>
  3. *
  4. * This program is free software: you can redistribute it and/or modify
  5. * it under the terms of the GNU General Public License as published by
  6. * the Free Software Foundation; either version 3 of the License, or
  7. * (at your option) any later version.
  8. *
  9. * This program is distributed in the hope that it will be useful,
  10. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. * GNU General Public License for more details.
  13. *
  14. * You should have received a copy of the GNU General Public License
  15. * along with this program. If not, see <http://www.gnu.org/licenses/>.
  16. */
  17. #include <stdio.h>
  18. #ifndef _MSC_VER
  19. #include <unistd.h>
  20. #include <sys/time.h>
  21. #endif
  22. #include <string.h>
  23. #include <stdlib.h>
  24. #include <time.h>
  25. #include <errno.h>
  26. #include <modbus.h>
  27. #define G_MSEC_PER_SEC 1000
  28. static uint32_t gettime_ms(void)
  29. {
  30. struct timeval tv;
  31. #if !defined(_MSC_VER)
  32. gettimeofday(&tv, NULL);
  33. return (uint32_t) tv.tv_sec * 1000 + tv.tv_usec / 1000;
  34. #else
  35. return GetTickCount();
  36. #endif
  37. }
  38. enum {
  39. TCP,
  40. RTU
  41. };
  42. /* Tests based on PI-MBUS-300 documentation */
  43. int main(int argc, char *argv[])
  44. {
  45. uint8_t *tab_bit;
  46. uint16_t *tab_reg;
  47. modbus_t *ctx;
  48. int i;
  49. int nb_points;
  50. double elapsed;
  51. uint32_t start;
  52. uint32_t end;
  53. uint32_t bytes;
  54. uint32_t rate;
  55. int rc;
  56. int n_loop;
  57. int use_backend;
  58. if (argc > 1) {
  59. if (strcmp(argv[1], "tcp") == 0) {
  60. use_backend = TCP;
  61. n_loop = 100000;
  62. } else if (strcmp(argv[1], "rtu") == 0) {
  63. use_backend = RTU;
  64. n_loop = 100;
  65. } else {
  66. printf("Usage:\n %s [tcp|rtu] - Modbus client to measure data bandwith\n\n", argv[0]);
  67. exit(1);
  68. }
  69. } else {
  70. /* By default */
  71. use_backend = TCP;
  72. n_loop = 100000;
  73. }
  74. if (use_backend == TCP) {
  75. ctx = modbus_new_tcp("127.0.0.1", 1502);
  76. } else {
  77. ctx = modbus_new_rtu("/dev/ttyUSB1", 115200, 'N', 8, 1);
  78. modbus_set_slave(ctx, 1);
  79. }
  80. if (modbus_connect(ctx) == -1) {
  81. fprintf(stderr, "Connexion failed: %s\n",
  82. modbus_strerror(errno));
  83. modbus_free(ctx);
  84. return -1;
  85. }
  86. /* Allocate and initialize the memory to store the status */
  87. tab_bit = (uint8_t *) malloc(MODBUS_MAX_READ_BITS * sizeof(uint8_t));
  88. memset(tab_bit, 0, MODBUS_MAX_READ_BITS * sizeof(uint8_t));
  89. /* Allocate and initialize the memory to store the registers */
  90. tab_reg = (uint16_t *) malloc(MODBUS_MAX_READ_REGISTERS * sizeof(uint16_t));
  91. memset(tab_reg, 0, MODBUS_MAX_READ_REGISTERS * sizeof(uint16_t));
  92. printf("READ BITS\n\n");
  93. nb_points = MODBUS_MAX_READ_BITS;
  94. start = gettime_ms();
  95. for (i=0; i<n_loop; i++) {
  96. rc = modbus_read_bits(ctx, 0, nb_points, tab_bit);
  97. if (rc == -1) {
  98. fprintf(stderr, "%s\n", modbus_strerror(errno));
  99. return -1;
  100. }
  101. }
  102. end = gettime_ms();
  103. elapsed = end - start;
  104. rate = (n_loop * nb_points) * G_MSEC_PER_SEC / (end - start);
  105. printf("Transfert rate in points/seconds:\n");
  106. printf("* %d points/s\n", rate);
  107. printf("\n");
  108. bytes = n_loop * (nb_points / 8) + ((nb_points % 8) ? 1 : 0);
  109. rate = bytes / 1024 * G_MSEC_PER_SEC / (end - start);
  110. printf("Values:\n");
  111. printf("* %d x %d values\n", n_loop, nb_points);
  112. printf("* %.3f ms for %d bytes\n", elapsed, bytes);
  113. printf("* %d KiB/s\n", rate);
  114. printf("\n");
  115. /* TCP: Query and reponse header and values */
  116. bytes = 12 + 9 + (nb_points / 8) + ((nb_points % 8) ? 1 : 0);
  117. printf("Values and TCP Modbus overhead:\n");
  118. printf("* %d x %d bytes\n", n_loop, bytes);
  119. bytes = n_loop * bytes;
  120. rate = bytes / 1024 * G_MSEC_PER_SEC / (end - start);
  121. printf("* %.3f ms for %d bytes\n", elapsed, bytes);
  122. printf("* %d KiB/s\n", rate);
  123. printf("\n\n");
  124. printf("READ REGISTERS\n\n");
  125. nb_points = MODBUS_MAX_READ_REGISTERS;
  126. start = gettime_ms();
  127. for (i=0; i<n_loop; i++) {
  128. rc = modbus_read_registers(ctx, 0, nb_points, tab_reg);
  129. if (rc == -1) {
  130. fprintf(stderr, "%s\n", modbus_strerror(errno));
  131. return -1;
  132. }
  133. }
  134. end = gettime_ms();
  135. elapsed = end - start;
  136. rate = (n_loop * nb_points) * G_MSEC_PER_SEC / (end - start);
  137. printf("Transfert rate in points/seconds:\n");
  138. printf("* %d registers/s\n", rate);
  139. printf("\n");
  140. bytes = n_loop * nb_points * sizeof(uint16_t);
  141. rate = bytes / 1024 * G_MSEC_PER_SEC / (end - start);
  142. printf("Values:\n");
  143. printf("* %d x %d values\n", n_loop, nb_points);
  144. printf("* %.3f ms for %d bytes\n", elapsed, bytes);
  145. printf("* %d KiB/s\n", rate);
  146. printf("\n");
  147. /* TCP:Query and reponse header and values */
  148. bytes = 12 + 9 + (nb_points * sizeof(uint16_t));
  149. printf("Values and TCP Modbus overhead:\n");
  150. printf("* %d x %d bytes\n", n_loop, bytes);
  151. bytes = n_loop * bytes;
  152. rate = bytes / 1024 * G_MSEC_PER_SEC / (end - start);
  153. printf("* %.3f ms for %d bytes\n", elapsed, bytes);
  154. printf("* %d KiB/s\n", rate);
  155. printf("\n\n");
  156. printf("WRITE AND READ REGISTERS\n\n");
  157. nb_points = MODBUS_MAX_WR_WRITE_REGISTERS;
  158. start = gettime_ms();
  159. for (i=0; i<n_loop; i++) {
  160. rc = modbus_write_and_read_registers(ctx,
  161. 0, nb_points, tab_reg,
  162. 0, nb_points, tab_reg);
  163. if (rc == -1) {
  164. fprintf(stderr, "%s\n", modbus_strerror(errno));
  165. return -1;
  166. }
  167. }
  168. end = gettime_ms();
  169. elapsed = end - start;
  170. rate = (n_loop * nb_points) * G_MSEC_PER_SEC / (end - start);
  171. printf("Transfert rate in points/seconds:\n");
  172. printf("* %d registers/s\n", rate);
  173. printf("\n");
  174. bytes = n_loop * nb_points * sizeof(uint16_t);
  175. rate = bytes / 1024 * G_MSEC_PER_SEC / (end - start);
  176. printf("Values:\n");
  177. printf("* %d x %d values\n", n_loop, nb_points);
  178. printf("* %.3f ms for %d bytes\n", elapsed, bytes);
  179. printf("* %d KiB/s\n", rate);
  180. printf("\n");
  181. /* TCP:Query and reponse header and values */
  182. bytes = 12 + 9 + (nb_points * sizeof(uint16_t));
  183. printf("Values and TCP Modbus overhead:\n");
  184. printf("* %d x %d bytes\n", n_loop, bytes);
  185. bytes = n_loop * bytes;
  186. rate = bytes / 1024 * G_MSEC_PER_SEC / (end - start);
  187. printf("* %.3f ms for %d bytes\n", elapsed, bytes);
  188. printf("* %d KiB/s\n", rate);
  189. printf("\n");
  190. /* Free the memory */
  191. free(tab_bit);
  192. free(tab_reg);
  193. /* Close the connection */
  194. modbus_close(ctx);
  195. modbus_free(ctx);
  196. return 0;
  197. }