网络交换机在设备和PC之间丢失TCP数据包


0

我有一个定制的AVR微控制器板,它有一个用于与PC通信的TCP / IP模块(芯片)。

我的电脑有一个4端口千兆以太网卡。每个端口都连接到以太网交换机 HP 1410-16G交换机(J9560A) 。每个以太网交换机连接到10~15个自定义控制器板。

更新 我添加了4端口以太网卡。我的电脑现在总共有8个GigE端口。每个端口都连接到网络交换机。我试图分配负载。

Windows IP Configuration     Host Name . . . . . . . . . . . . : rdex4r0al    
Primary Dns Suffix  . . . . . . . :     
Node Type . . . . . . . . . . . . : Unknown    
IP Routing Enabled. . . . . . . . : No    
WINS Proxy Enabled. . . . . . . . : No  

Ethernet adapter HUB#2-4 (192.168.13.2):     
Connection-specific DNS Suffix  . :     
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection #6    
Physical Address. . . . . . . . . : 00-25-90-98-FF-47    
DHCP Enabled. . . . . . . . . . . : No    
IP Address. . . . . . . . . . . . : 192.168.13.2    
Subnet Mask . . . . . . . . . . . : 255.255.255.0    
Default Gateway . . . . . . . . . :   

Ethernet adapter HUB#2-3 (192.168.12.2):     
Connection-specific DNS Suffix  . :     
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection #5    
Physical Address. . . . . . . . . : 00-25-90-98-FF-46    
DHCP Enabled. . . . . . . . . . . : No    
IP Address. . . . . . . . . . . . : 192.168.12.2    
Subnet Mask . . . . . . . . . . . : 255.255.255.0    
Default Gateway . . . . . . . . . :   

Ethernet adapter HUB#2-2 (192.168.11.2):     
Connection-specific DNS Suffix  . :     
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection #4    
Physical Address. . . . . . . . . : 00-25-90-98-FF-45    
DHCP Enabled. . . . . . . . . . . : No    
IP Address. . . . . . . . . . . . : 192.168.11.2    
Subnet Mask . . . . . . . . . . . : 255.255.255.0    
Default Gateway . . . . . . . . . :   

Ethernet adapter HUB#2-1 (192.168.10.2):     
Connection-specific DNS Suffix  . :     
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection #3    
Physical Address. . . . . . . . . : 00-25-90-98-FF-44    
DHCP Enabled. . . . . . . . . . . : No    
IP Address. . . . . . . . . . . . : 192.168.10.2    
Subnet Mask . . . . . . . . . . . : 255.255.255.0    
Default Gateway . . . . . . . . . :   

Ethernet adapter Service (192.168.15.18):     
Media State . . . . . . . . . . . : Media disconnected    
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection #2    
Physical Address. . . . . . . . . : 00-25-90-82-45-7F  

Ethernet adapter ToMain (192.168.2.50):     
Connection-specific DNS Suffix  . :     
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection    
Physical Address. . . . . . . . . : 00-25-90-82-45-7E    
DHCP Enabled. . . . . . . . . . . : No    
IP Address. . . . . . . . . . . . : 192.168.2.50    
Subnet Mask . . . . . . . . . . . : 255.255.255.0    
Default Gateway . . . . . . . . . :   

Ethernet adapter Local Area Connection:     
Media State . . . . . . . . . . . : Media disconnected    
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection #7    
Physical Address. . . . . . . . . : 00-25-90-98-7B-9E  

Ethernet adapter HUB#1-2(192.168.16.2):     
Connection-specific DNS Suffix  . :     
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection #8    
Physical Address. . . . . . . . . : 00-25-90-98-7B-9F    
DHCP Enabled. . . . . . . . . . . : No    
IP Address. . . . . . . . . . . . : 192.168.16.2    
Subnet Mask . . . . . . . . . . . : 255.255.255.0    
Default Gateway . . . . . . . . . :   

Ethernet adapter HUB#1-3 (192.168.14.2):     
Connection-specific DNS Suffix  . :     
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection #9    
Physical Address. . . . . . . . . : 00-25-90-98-7B-9C    
DHCP Enabled. . . . . . . . . . . : No    
IP Address. . . . . . . . . . . . : 192.168.14.2    
Subnet Mask . . . . . . . . . . . : 255.255.255.0    
Default Gateway . . . . . . . . . :   

Ethernet adapter HUB#1-4 (192.168.15.2):     
Connection-specific DNS Suffix  . :     
Description . . . . . . . . . . . : Intel(R) 82576 Gigabit Dual Port Network Connection #10    
Physical Address. . . . . . . . . : 00-25-90-98-7B-9D    
DHCP Enabled. . . . . . . . . . . : No    
IP Address. . . . . . . . . . . . : 192.168.15.2    
Subnet Mask . . . . . . . . . . . : 255.255.255.0    
Default Gateway . . . . . . . . . :  

我的PC总共连接了近50个控制器。有时我会收到超时错误,这意味着没有ACK消息。如果我收到多次超时,连接将丢失,我无法再次连接到该控制器。它必须在再次连接之前进行电源循环。

如果我在没有交换机的情况下直接连接到控制器,我就不会收到超时错误。

我试图找到这些丢失数据包的根本原因。如何监控数据包丢失的位置?在PC上,以太网交换机,定制控制器......?

Wireshark的 有助于找到根本原因?

更新

如果其中一个根本原因是超载,那么解决方案是什么?我是否需要添加另一个4端口网卡和网络交换机才能分割连接? **我可以询问更多详细配置或推荐产品吗? **

更新问题

正如我提到的关于网络交换机的配置,我听说DNS非常慢,然后每个连接都很慢。许多人喜欢在8.8.8.8使用Google DNS。它比其他人快得多。我是否需要将其设置为我的PC的DNS服务器? DNS和速度之间有什么关系吗?如何知道DNS速度是否缓慢?在我们的应用程序中,DNS是最佳的?任何帮助表示赞赏。

进一步的问题 双方应使用相同的双工设置。我应该启用还是禁用双方的自动协商?我理解正确吗?

附加信息

我专注于三个项目。

  1. 双工不匹配:PC(Auto-Neg),网络交换机(Auto-Neg),第三方控制器(Auto-Neg选项启用,此控制器具有100T全双工,100T半双工,10T全双​​工,10T-半双工))
  2. 低质量电缆:STP-CAT5e,电缆长度在5米以内
  3. 低信号环境:工业工厂实验室

对于此第三方控制器,我不知道设置或修复了哪种模式。我们可以猜测是否启用了自动协商。 你知道如何保持良好的信号质量吗?

更新代码

using System;
using System.Net;
using System.Net.Sockets;
using System.Reflection;
using System.Threading;
using LogManager;

namespace CoreUnitPlatform
{
    public class SocketCommCoreUnit
    {
        #region property
        private volatile bool _shouldStop;
        private LogWriter log = LogWriter.Instance;

        private bool m_bSocketConnected = false;

        private Socket m_clientSocket = null;

        private SocketCommType m_connectedSockType;

        private EventHandlerDataReceived m_evtHandlerDataReceived;

        private EventHandlerSocketConnected m_evtHandlerSocketConnected;

        private EventHandlerSocketConnectedFailed m_evtHandlerSocketConnectedFailed;

        private EventHandlerSocketDisconnected m_evtHandlerSocketDisconnected;

        private IPAddress m_IPAddress;

        private IPEndPoint m_IPEndPoint;

        private int m_portNo;

        private Socket m_serverSocket = null;

        private Thread m_threadConnectSocket = null;

        private string Name = string.Empty;

        #endregion

        #region constructor
        public SocketCommCoreUnit()
        {
            this.Name = "SocketCommCoreUnit";
            Instance();
        }
        #endregion

        #region delegatge
        public delegate void EventHandlerDataReceived(string msg);

        public delegate void EventHandlerSocketConnected();

        public delegate void EventHandlerSocketConnectedFailed();

        public delegate void EventHandlerSocketDisconnected();
        public enum SocketCommType { SERVER, CLIENT };

        public bool SocketConnected
        {
            get { lock (this) { return m_bSocketConnected; } }
            set { lock (this) { m_bSocketConnected = value; } }
        }
        #endregion

        #region public
        public void ConnectSocketProc()
        {
            while (!_shouldStop)
            {
                try
                {
                    if (SocketConnected == false)
                    {
                        if (m_connectedSockType == SocketCommType.SERVER)
                        {
                            m_clientSocket = m_serverSocket.Accept();   // If a client is connected, wait for data from client

                            m_evtHandlerSocketConnected();
                            SocketConnected = true;
                        }
                        else
                        {
                            m_clientSocket.Connect(m_IPAddress, m_portNo);
                            if (m_clientSocket.Connected == true)
                            {
                                m_evtHandlerSocketConnected();
                                SocketConnected = true;
                            }
                        }
                    }
                    else
                    {
                        try
                        {
                            byte[] buffer = new byte[1024];
                            int readBytes = this.m_clientSocket.Receive(buffer);
                            if (readBytes == 0)
                            {
                                this.reConnect();
                            }
                            else
                            {
                                string received = System.Text.Encoding.ASCII.GetString(buffer);
                                m_evtHandlerDataReceived(received);
                            }
                        }
                        catch (SocketException sex)
                        {
                            if (sex.NativeErrorCode.Equals(10054))
                            {
                                log.AddErrorLog(this.Name, MethodBase.GetCurrentMethod().Name, string.Format("Error Occured [{0}]: MESASGE[{1}]\r\nSOURCE[{2}]\r\nTRACE[{3}]", sex.NativeErrorCode, sex.Message, sex.Source, sex.StackTrace));

                                this.reConnect();
                            }
                        }
                    }
                }
                catch
                {
                    m_evtHandlerSocketConnectedFailed();
                }

                Thread.Sleep(100);
            }
        }

        public void Initialize(string IP, int port, SocketCommType sockType, EventHandlerDataReceived evtHandlerDataReceived, EventHandlerSocketConnected evtHandlerDataConnected, EventHandlerSocketDisconnected evtHandlerSocketDisconnected, EventHandlerSocketConnectedFailed evtHandlerSocketConnectedFailed)
        {
            m_connectedSockType = sockType;
            m_evtHandlerDataReceived = evtHandlerDataReceived;
            m_evtHandlerSocketDisconnected = evtHandlerSocketDisconnected;
            m_evtHandlerSocketConnected = evtHandlerDataConnected;
            m_evtHandlerSocketConnectedFailed = evtHandlerSocketConnectedFailed;

            m_portNo = port;
            m_IPAddress = IPAddress.Parse(IP);
            m_IPEndPoint = new IPEndPoint(m_IPAddress, m_portNo);

            if (sockType == SocketCommType.SERVER)
            {
                OpenServer();
            }
            else
            {
                OpenClient();
            }
        }

        public void Instance()
        {
        }

        public void OpenClient()
        {
            try
            {
#if _NO_USE_SOCKET
#else
                RunClientSocket();
#endif
            }
            catch (System.Exception ex)
            {
                log.AddErrorLog(this.Name, MethodBase.GetCurrentMethod().Name, string.Format("Error Occured: MESASGE[{0}]\r\nSOURCE[{1}]\r\nTRACE[{2}]", ex.Message, ex.Source, ex.StackTrace));
            }
        }

        public void OpenServer()
        {
            try
            {
#if _NO_USE_SOCKET
#else
                RunServerSocket();
#endif
            }
            catch (System.Exception ex)
            {
                log.AddErrorLog(this.Name, MethodBase.GetCurrentMethod().Name, string.Format("Error Occured: MESASGE[{0}]\r\nSOURCE[{1}]\r\nTRACE[{2}]", ex.Message, ex.Source, ex.StackTrace));
            }
        }

        public void Release()
        {
            try
            {
                if (this.m_clientSocket != null && this.m_clientSocket.Connected)
                {
                    SocketConnected = false;
                    m_evtHandlerSocketDisconnected();

                    this.m_clientSocket.Shutdown(SocketShutdown.Both);
                    this.m_clientSocket.Close();
                }

                if (m_serverSocket != null)
                {
                    m_serverSocket.Close();
                }

                if ((m_threadConnectSocket != null) && (m_threadConnectSocket.IsAlive == true))
                {
                    Thread.Sleep(1);
                    RequestStop();

                    SocketConnected = false;
                    m_threadConnectSocket.Abort();
                    m_threadConnectSocket.Join();
                }
            }
            catch (System.Exception ex)
            {
                log.AddErrorLog(this.Name, MethodBase.GetCurrentMethod().Name, string.Format("Error Occured: MESASGE[{0}]\r\nSOURCE[{1}]\r\nTRACE[{2}]", ex.Message, ex.Source, ex.StackTrace));
            }
        }

        public void RequestStop()
        {
            _shouldStop = true;
        }

        public void RunClientSocket()
        {
            m_clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            ConfigureTcpSocket(m_clientSocket, SocketCommType.CLIENT);

            m_threadConnectSocket = new Thread(new ThreadStart(ConnectSocketProc));
            m_threadConnectSocket.Start();
        }

        public void RunServerSocket()
        {
            m_serverSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            m_serverSocket.Bind(m_IPEndPoint);
            m_serverSocket.Blocking = true;          // The server socket is working in blocking mode

            ConfigureTcpSocket(m_serverSocket, SocketCommType.SERVER);

            m_serverSocket.Listen(1);

            m_threadConnectSocket = new Thread(new ThreadStart(ConnectSocketProc));
            m_threadConnectSocket.Start();
        }

        public void Send(byte[] msg)
        {
#if _NO_USE_SOCKET
#else
            if (SocketConnected == false)
            {
                throw new Exception("SOCKET_NOT_CONNECT_BEFORE_SEND_DATA;");
            }

            try
            {
                m_clientSocket.Send(msg);
            }
            catch (System.Exception ex)
            {
                SocketConnected = false;
                m_evtHandlerSocketDisconnected();
                log.AddErrorLog(this.Name, MethodBase.GetCurrentMethod().Name, string.Format("Error Occured: MESASGE[{0}]\r\nSOURCE[{1}]\r\nTRACE[{2}]", ex.Message, ex.Source, ex.StackTrace));
            }
#endif
        }

        #endregion

        #region private

        private void ConfigureTcpSocket(Socket tcpSocket, SocketCommType socketCommType)
        {
            //// Don't allow another socket to bind to this port.
            //tcpSocket.ExclusiveAddressUse = true;

            //// The socket will linger for 10 seconds after
            //// Socket.Close is called.
            //tcpSocket.LingerState = new LingerOption(true, 10);

            // Disable the Nagle Algorithm for this tcp socket.
            tcpSocket.NoDelay = true;

            //if (socketCommType == SocketCommType.CLIENT)
            //{
            //    tcpSocket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.DontLinger, false);
            //    tcpSocket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
            //    //tcpSocket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReceiveTimeout, 3000);
            //    //tcpSocket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.SendTimeout, 3000);

            //    // Set the receive buffer size to 8k
            //    tcpSocket.ReceiveBufferSize = 2048;

            //    // Set the send buffer size to 8k.
            //    tcpSocket.SendBufferSize = 2048;
            //}

            //// Set the receive buffer size to 8k
            //tcpSocket.ReceiveBufferSize = 1024;

            // Set the timeout for synchronous receive methods to
            // 1 second (1000 milliseconds.)
            //tcpSocket.ReceiveTimeout = 1000;

            //// Set the send buffer size to 8k.
            //tcpSocket.SendBufferSize = 1024;

            // Set the timeout for synchronous send methods
            // to 1 second (1000 milliseconds.)
            //tcpSocket.SendTimeout = 1000;

            //// Set the Time To Live (TTL) to 42 router hops.
            //tcpSocket.Ttl = 42;
        }

        private void ConfigureTcpSocket(Socket tcpSocket)
        {
            //// Don't allow another socket to bind to this port.
            //tcpSocket.ExclusiveAddressUse = true;

            //// The socket will linger for 10 seconds after
            //// Socket.Close is called.
            //tcpSocket.LingerState = new LingerOption(true, 10);

            // Disable the Nagle Algorithm for this tcp socket.
            tcpSocket.NoDelay = true;

            //// Set the receive buffer size to 8k
            //tcpSocket.ReceiveBufferSize = 8192;

            // Set the timeout for synchronous receive methods to
            // 1 second (1000 milliseconds.)
            //tcpSocket.ReceiveTimeout = 1000;

            //// Set the send buffer size to 8k.
            //tcpSocket.SendBufferSize = 8192;

            // Set the timeout for synchronous send methods
            // to 1 second (1000 milliseconds.)
            //tcpSocket.SendTimeout = 1000;

            //// Set the Time To Live (TTL) to 42 router hops.
            //tcpSocket.Ttl = 42;
        }


        private void reConnect()
        {
            ////if (this.m_clientSocket != null && this.m_clientSocket.Connected)
            {
                try
                {
                    SocketConnected = false;
                    m_evtHandlerSocketDisconnected();
                    m_clientSocket.Disconnect(true);

                    log.AddSystemLog(this.Name, MethodBase.GetCurrentMethod().Name, string.Format("Try Re-Connection..."));

                    if (m_connectedSockType == SocketCommType.SERVER)
                    {
                    }
                    else
                    {
                        m_clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                    }
                }
                catch (System.Exception exc)
                {
                    log.AddErrorLog(this.Name, MethodBase.GetCurrentMethod().Name, string.Format("Error Occured: MESASGE[{0}]\r\nSOURCE[{1}]\r\nTRACE[{2}]", exc.Message, exc.Source, exc.StackTrace));
                }
            }
        }
        #endregion
    }
}

1
集线器可以处理这一切吗?根据我的理解,集线器是第1层设备,它只是在一个端口接收通信,并将其发送到每个其他端口。您可以使用第2层交换机来完成您要完成的任务,它可以学习其他设备的MAC地址,从而将其传输到该特定设备,而不是像集线器一样将每个端口爆炸出来吗?还有一个集线器不是与CDMA / CD的一个大的冲突域,它必须发出停止并在每次发生冲突时重新发送。
j_bombay

@j_bombayI检查了HP 1410-16G Switch(J9560A)的详细产品。我认为这是转换,而不是集线器。为了缓解超载,您认为我使用VLAN交换机或路由器来划分网络吗?
Changju.rhee

这种问题往往是双工不匹配(通常是由于一方禁用自动协商而另一方面启用)或布线质量差。
David Schwartz

@DavidSchwartz你知道如何知道双工不匹配吗?第三方控制器制造商没有说配置。
Changju.rhee

@ Changju.rhee:双工不匹配的最可能原因是,如果您在一侧将双工设置为已满,而在另一侧将其设置为自动协商。
David Schwartz

Answers:


1

从简单开始。直接连接,然后连接一个集线器,然后连接更多控制器等。一次添加一个节点直到它中断,然后您将知道导致问题的设备,或者它是否是节点数量的限制。


谢谢,但失去了信息,这是随机发生的。
Changju.rhee

1
@ Changju.rhee这个建议值得一试。您当前的大型设置很可能使主机PC和/或控制器过载。将其缩小以查看是否可以缓解问题。或者用开关更换集线器。 Wireshark将提供大量数据,除非您知道要查找什么,否则可能没有答案。
sawdust

@sawdust我检查了HP 1410-16G Switch(J9560A)的详细产品。我认为这是转换,而不是集线器。为了缓解超载,您认为我使用VLAN交换机或路由器来划分网络吗?
Changju.rhee

@ Changju.rhee如果你确定它超载,你可以使用交换机而不是路由器,如果他们不必到达不同的子网。它不一定是支持VLAN的交换机,常规交换机就足够了。如果主机PC过载是问题,这可能会有所帮助,也可能没有帮助。
MDMoore313

@ MDMoore313如何计算主机PC是否有问题。你有什么主意吗 ?我已经添加了一个网卡来分发客户端。但是,我还有时间错误。
Changju.rhee
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.