ソースを参照

【添加】TCP 模式支持

guozhanxin 6 年 前
コミット
31a33df796
4 ファイル変更146 行追加3 行削除
  1. 5 0
      SConscript
  2. 5 0
      modbus/include/mbconfig.h
  3. 112 0
      port/porttcp.c
  4. 24 3
      samples/sample_mb_slave.c

+ 5 - 0
SConscript

@@ -30,6 +30,7 @@ modbus/functions/mbfuncinput.c
 modbus/mb.c
 port/portevent.c
 port/portserial.c
+port/porttcp.c
 port/porttimer.c
 port/user_mb_app.c
 """)
@@ -38,6 +39,7 @@ port/user_mb_app.c
 path = [GetCurrentDir() + '/modbus/include',
     GetCurrentDir() + '/modbus/rtu',
     GetCurrentDir() + '/modbus/ascii',
+    GetCurrentDir() + '/modbus/tcp',
     GetCurrentDir() + '/port']
 
 if GetDepend(['PKG_MODBUS_MASTER_RTU']):
@@ -53,6 +55,9 @@ if GetDepend(['PKG_MODBUS_SLAVE_ASCII']):
     src += ['modbus/ascii/mbascii.c']
     src += ['modbus/rtu/mbrtu.c']
 
+if GetDepend(['PKG_MODBUS_SLAVE_TCP']):
+    src += ['modbus/tcp/mbtcp.c']
+
 if GetDepend(['PKG_MODBUS_MASTER_SAMPLE']):
     src += ['samples/sample_mb_master.c']
 

+ 5 - 0
modbus/include/mbconfig.h

@@ -72,7 +72,12 @@ PR_BEGIN_EXTERN_C
 #endif
 
 /*! \brief If Modbus Slave TCP support is enabled. */
+#ifdef PKG_MODBUS_SLAVE_TCP
+#define MB_SLAVE_TCP_ENABLED                    (  1 )
+#else
 #define MB_SLAVE_TCP_ENABLED                    (  0 )
+#endif
+
 /*! \brief The character timeout value for Modbus ASCII.
  *
  * The character timeout value is not fixed for Modbus ASCII and is therefore

+ 112 - 0
port/porttcp.c

@@ -0,0 +1,112 @@
+/*
+ * FreeModbus Libary: RT-Thread Port
+ * Copyright (C) 2019 flybreak <guozhanxin@rt-thread.com>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ *
+ * File: $Id: portserial.c,v 1.60 2019/07/11 17:04:32 flybreak $
+ */
+
+#include "port.h"
+
+/* ----------------------- Modbus includes ----------------------------------*/
+#include "mb.h"
+#include "mbport.h"
+#include "tcpserver.h"
+
+/* ----------------------- Defines  -----------------------------------------*/
+#define MB_TCP_DEFAULT_PORT     502
+#define MB_TCP_BUF_SIZE     ( 256 + 7 )
+
+/* ----------------------- Static variables ---------------------------------*/
+static tcpclient_t mb_client;
+static UCHAR    prvvTCPBuf[MB_TCP_BUF_SIZE];
+static USHORT   prvvTCPLength;
+
+static void tcpserver_event_notify(tcpclient_t client, rt_uint8_t event)
+{
+    switch (event)
+    {
+    case TCPSERVER_EVENT_CONNECT:
+        if (mb_client == RT_NULL)
+            mb_client = client;
+        else
+            rt_kprintf("Multi-host is not supported, please disconnect the current host first!");
+        break;
+    case TCPSERVER_EVENT_RECV:
+        prvvTCPLength = tcpserver_recv(mb_client, &prvvTCPBuf, MB_TCP_BUF_SIZE, 100);
+        if (prvvTCPLength)
+        {
+            xMBPortEventPost(EV_FRAME_RECEIVED);
+        }
+        break;
+    case TCPSERVER_EVENT_DISCONNECT:
+        mb_client = RT_NULL;
+        break;
+    default:
+        break;
+    }
+}
+
+BOOL
+xMBTCPPortInit(USHORT usTCPPort)
+{
+    struct tcpserver *serv;
+    
+    if (usTCPPort == 0)
+        usTCPPort = MB_TCP_DEFAULT_PORT;
+    
+    serv = tcpserver_create(0, usTCPPort);
+
+    tcpserver_set_notify_callback(serv, tcpserver_event_notify);
+
+    return TRUE;
+}
+
+void
+vMBTCPPortClose(void)
+{
+    tcpserver_destroy(mb_client->server);
+}
+
+void
+vMBTCPPortDisable(void)
+{
+    tcpserver_close(mb_client);
+}
+
+BOOL
+xMBTCPPortGetRequest(UCHAR **ppucMBTCPFrame, USHORT *usTCPLength)
+{
+    *ppucMBTCPFrame = &prvvTCPBuf[0];
+    *usTCPLength = prvvTCPLength;
+
+    return TRUE;
+}
+
+BOOL
+xMBTCPPortSendResponse(const UCHAR *pucMBTCPFrame, USHORT usTCPLength)
+{
+    rt_int16_t ret;
+    BOOL bFrameSent = FALSE;
+
+    if (mb_client)
+    {
+        ret = tcpserver_send(mb_client, (void *)pucMBTCPFrame, usTCPLength, 0);
+        if (ret == usTCPLength)
+            bFrameSent = TRUE;
+    }
+    return bFrameSent;
+}

+ 24 - 3
samples/sample_mb_slave.c

@@ -19,7 +19,7 @@
 #define PORT_BAUDRATE   MB_SLAVE_USING_PORT_BAUDRATE
 #else
 #define SLAVE_ADDR      0x01
-#define PORT_NUM        3
+#define PORT_NUM        2
 #define PORT_BAUDRATE   115200
 #endif
 
@@ -53,7 +53,22 @@ static void send_thread_entry(void *parameter)
 
 static void mb_slave_poll(void *parameter)
 {
-    eMBInit(MB_RTU, SLAVE_ADDR, PORT_NUM, PORT_BAUDRATE, PORT_PARITY);
+    if (rt_strstr(parameter, "RTU"))
+    {
+        eMBInit(MB_RTU, SLAVE_ADDR, PORT_NUM, PORT_BAUDRATE, PORT_PARITY);
+    }
+    else if (rt_strstr(parameter, "ASCII"))
+    {
+        eMBInit(MB_ASCII, SLAVE_ADDR, PORT_NUM, PORT_BAUDRATE, PORT_PARITY);
+    }
+    else if (rt_strstr(parameter, "TCP"))
+    {
+        eMBTCPInit(0);
+    }
+    else
+    {
+        rt_kprintf("Error: unknown parameter");
+    }
     eMBEnable();
     while (1)
     {
@@ -72,7 +87,13 @@ static int mb_slave_samlpe(int argc, char **argv)
         rt_kprintf("sample is running\n");
         return -RT_ERROR;
     }
-    tid1 = rt_thread_create("md_s_poll", mb_slave_poll, RT_NULL, 512, MB_POLL_THREAD_PRIORITY, 10);
+    if (argc < 2)
+    {
+        rt_kprintf("Usage: mb_slave_samlpe RTU/ASCII/TCP\n");
+        return -1;
+    }
+
+    tid1 = rt_thread_create("md_s_poll", mb_slave_poll, argv[1], 1024, MB_POLL_THREAD_PRIORITY, 10);
     if (tid1 != RT_NULL)
     {
         rt_thread_startup(tid1);