mbtcp.c 5.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159
  1. /*
  2. * FreeModbus Libary: A portable Modbus implementation for Modbus ASCII/RTU.
  3. * Copyright (c) 2006 Christian Walter <wolti@sil.at>
  4. * All rights reserved.
  5. *
  6. * Redistribution and use in source and binary forms, with or without
  7. * modification, are permitted provided that the following conditions
  8. * are met:
  9. * 1. Redistributions of source code must retain the above copyright
  10. * notice, this list of conditions and the following disclaimer.
  11. * 2. Redistributions in binary form must reproduce the above copyright
  12. * notice, this list of conditions and the following disclaimer in the
  13. * documentation and/or other materials provided with the distribution.
  14. * 3. The name of the author may not be used to endorse or promote products
  15. * derived from this software without specific prior written permission.
  16. *
  17. * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  18. * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
  19. * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
  20. * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
  21. * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
  22. * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  23. * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
  24. * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  25. * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  26. * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  27. *
  28. * File: $Id: mbtcp.c,v 1.3 2006/12/07 22:10:34 wolti Exp $
  29. */
  30. /* ----------------------- System includes ----------------------------------*/
  31. #include "stdlib.h"
  32. #include "string.h"
  33. /* ----------------------- Platform includes --------------------------------*/
  34. #include "port.h"
  35. /* ----------------------- Modbus includes ----------------------------------*/
  36. #include "mb.h"
  37. #include "mbconfig.h"
  38. #include "mbtcp.h"
  39. #include "mbframe.h"
  40. #include "mbport.h"
  41. #if MB_TCP_ENABLED > 0
  42. /* ----------------------- Defines ------------------------------------------*/
  43. /* ----------------------- MBAP Header --------------------------------------*/
  44. /*
  45. *
  46. * <------------------------ MODBUS TCP/IP ADU(1) ------------------------->
  47. * <----------- MODBUS PDU (1') ---------------->
  48. * +-----------+---------------+------------------------------------------+
  49. * | TID | PID | Length | UID |Code | Data |
  50. * +-----------+---------------+------------------------------------------+
  51. * | | | | |
  52. * (2) (3) (4) (5) (6)
  53. *
  54. * (2) ... MB_TCP_TID = 0 (Transaction Identifier - 2 Byte)
  55. * (3) ... MB_TCP_PID = 2 (Protocol Identifier - 2 Byte)
  56. * (4) ... MB_TCP_LEN = 4 (Number of bytes - 2 Byte)
  57. * (5) ... MB_TCP_UID = 6 (Unit Identifier - 1 Byte)
  58. * (6) ... MB_TCP_FUNC = 7 (Modbus Function Code)
  59. *
  60. * (1) ... Modbus TCP/IP Application Data Unit
  61. * (1') ... Modbus Protocol Data Unit
  62. */
  63. #define MB_TCP_TID 0
  64. #define MB_TCP_PID 2
  65. #define MB_TCP_LEN 4
  66. #define MB_TCP_UID 6
  67. #define MB_TCP_FUNC 7
  68. #define MB_TCP_PROTOCOL_ID 0 /* 0 = Modbus Protocol */
  69. /* ----------------------- Start implementation -----------------------------*/
  70. eMBErrorCode
  71. eMBTCPDoInit(fmodbus_t* ctx, USHORT ucTCPPort )
  72. {
  73. eMBErrorCode eStatus = MB_ENOERR;
  74. if( xMBTCPPortInit(ctx, ucTCPPort ) == FALSE )
  75. {
  76. eStatus = MB_EPORTERR;
  77. }
  78. return eStatus;
  79. }
  80. void
  81. eMBTCPStart( fmodbus_t* ctx )
  82. {
  83. }
  84. void
  85. eMBTCPStop( fmodbus_t* ctx )
  86. {
  87. /* Make sure that no more clients are connected. */
  88. vMBTCPPortDisable( ctx );
  89. }
  90. eMBErrorCode
  91. eMBTCPReceive(fmodbus_t* ctx, UCHAR * pucRcvAddress, UCHAR ** ppucFrame, USHORT * pusLength )
  92. {
  93. eMBErrorCode eStatus = MB_EIO;
  94. UCHAR *pucMBTCPFrame;
  95. USHORT usLength;
  96. USHORT usPID;
  97. if( xMBTCPPortGetRequest(ctx, &pucMBTCPFrame, &usLength ) != FALSE )
  98. {
  99. usPID = pucMBTCPFrame[MB_TCP_PID] << 8U;
  100. usPID |= pucMBTCPFrame[MB_TCP_PID + 1];
  101. if( usPID == MB_TCP_PROTOCOL_ID )
  102. {
  103. *ppucFrame = &pucMBTCPFrame[MB_TCP_FUNC];
  104. *pusLength = usLength - MB_TCP_FUNC;
  105. eStatus = MB_ENOERR;
  106. /* Modbus TCP does not use any addresses. Fake the source address such
  107. * that the processing part deals with this frame.
  108. */
  109. *pucRcvAddress = MB_TCP_PSEUDO_ADDRESS;
  110. }
  111. }
  112. else
  113. {
  114. eStatus = MB_EIO;
  115. }
  116. return eStatus;
  117. }
  118. eMBErrorCode
  119. eMBTCPSend(fmodbus_t* ctx, UCHAR _unused, const UCHAR * pucFrame, USHORT usLength )
  120. {
  121. eMBErrorCode eStatus = MB_ENOERR;
  122. UCHAR *pucMBTCPFrame = ( UCHAR * ) pucFrame - MB_TCP_FUNC;
  123. USHORT usTCPLength = usLength + MB_TCP_FUNC;
  124. /* The MBAP header is already initialized because the caller calls this
  125. * function with the buffer returned by the previous call. Therefore we
  126. * only have to update the length in the header. Note that the length
  127. * header includes the size of the Modbus PDU and the UID Byte. Therefore
  128. * the length is usLength plus one.
  129. */
  130. pucMBTCPFrame[MB_TCP_LEN] = ( usLength + 1 ) >> 8U;
  131. pucMBTCPFrame[MB_TCP_LEN + 1] = ( usLength + 1 ) & 0xFF;
  132. if( xMBTCPPortSendResponse(ctx, pucMBTCPFrame, usTCPLength ) == FALSE )
  133. {
  134. eStatus = MB_EIO;
  135. }
  136. return eStatus;
  137. }
  138. #endif