昨天发的求助帖给沉啦,今天再发一帖
http://bbs.csdn.net/topics/390342556(昨天的帖子)
增加几点说明:
1、通讯双方的所有信息(内网IP,公网IP和端口)都可以告诉对方,这样是不是就不需要穿透NAT啦,这样两个不同内网应该是怎么建立TCP连接的
2、这种点对多的通讯是使用异步通讯好呢还是使用同步加多线程好,是不是使用同步通讯还要处理TCP消息无边界的问题
3、如果有例子程序最好,没有的话给出设计方案以及可能还会存在的问题,万分感谢!网络编程

解决方案 »

  1.   

    1--NAT?是什么?不明白! 有内网ip,还有公网ip ,双网卡?  内网中,两个不同网段的ip.可以通过交换机组成可以互访的吧.(好像配置过思科的交换机).或者找台机器,双网卡,接入两个网段,做服务器端.2--点对多?   指的是 S对多C? 服务器端做监听端?来个客户端就开个线程处理消息交互不就好了. 点多的话,可以考虑 iocp3--
    private class ConnectionInfo
            {
                public Socket Socket;
                public byte[] Buffer;        }        private List<ConnectionInfo> _connections = new List<ConnectionInfo>();        private void SetupServerSocket()
            {
                // Resolving local machine information
                IPHostEntry localMachineInfo =
                    Dns.GetHostEntry(Dns.GetHostName());
                IPEndPoint myEndpoint = new IPEndPoint(
                    localMachineInfo.AddressList[0], _port);            // Create the socket, bind it, and start listening
                _serverSocket = new Socket(myEndpoint.Address.AddressFamily,
                    SocketType.Stream, ProtocolType.Tcp);
                _serverSocket.Bind(myEndpoint);
                int max = (int)SocketOptionName.MaxConnections;
                _serverSocket.Listen(max);
            }        public void Start()
            {
                _fm.Print("开始工作站启动网络..\r\n");
                //_fm.logWrite("开始Start连接..");            SetupServerSocket();
                for (int i = 0; i < 10; i++)
                    _serverSocket.BeginAccept(
                        new AsyncCallback(AcceptCallback), _serverSocket);
            }        private void AcceptCallback(IAsyncResult result)
            {
                ConnectionInfo connection = new ConnectionInfo();
                try
                {
                    Socket s = (Socket)result.AsyncState;
                    connection.Socket = s.EndAccept(result);
                    connection.Buffer = new byte[255];                lock (_connections) _connections.Add(connection);
                    // Start Receive and a new Accept
                    connection.Socket.BeginReceive(connection.Buffer, 0,
                        connection.Buffer.Length, SocketFlags.None,
                        new AsyncCallback(ReceiveCallback), connection);
                    _serverSocket.BeginAccept(new AsyncCallback(AcceptCallback),
                        result.AsyncState);
                }
                catch (SocketException exc)
                {                CloseConnection(connection);
                    //_fm.logWrite("Socket exception: " + exc.SocketErrorCode);
                }
                catch (Exception exc)
                {                CloseConnection(connection);
                    //_fm.logWrite("Exception: " + exc);
                }        }  
            private void ReceiveCallback(IAsyncResult result)
            {
                int termNo;
                ConnectionInfo connection = (ConnectionInfo)result.AsyncState;
                try
                {
                    int bytesRead = connection.Socket.EndReceive(result);
                    if (0 != bytesRead)
                    {
                        // get addr snd;
                        termNo = RefHzPtl.getTermNo(connection.Buffer, bytesRead);
                        if ((termNo != 0) && (termNo != -1))
                        {
                            _fm._mUt._asyIoSever.TcpSend(termNo, connection.Buffer, bytesRead);
                        }
                        connection.Socket.BeginReceive(connection.Buffer, 0,
                            connection.Buffer.Length, SocketFlags.None,
                            new AsyncCallback(ReceiveCallback), connection);
                    }
                    else CloseConnection(connection);
                }
                catch (SocketException exc)
                {                CloseConnection(connection);
                    //_fm.logWrite("Socket exception: " + exc.SocketErrorCode);            }
                catch (Exception exc)
                {
                    CloseConnection(connection);
                    //_fm.logWrite("Exception: " + exc);
                }
            }        private void CloseConnection(ConnectionInfo ci)
            {
                try
                {                ci.Socket.Close();
                    lock (_connections) _connections.Remove(ci);            }
                catch (SocketException exc)
                {
                    //_fm.logWrite("Socket close: " + exc);
                }
                catch (Exception exc)
                {                //_fm.logWrite("Socket close ception: " + exc);
                }
            }
      

  2.   

    1 如果你有公网ip端口,其实就是做好了nat端口映射(虚拟服务器,upnp),这样tcp是可以连接的。
    但是如果没有在路由器做这个端口映射(或路由器不开upnp),则tcp无法连接。
    2 异步(线程池)。
    3 你首先解决寻址和端口开放的问题,然后才能下一步的tcp连接。看你的说明寻址是手工输入tcp ip端口,那可以。但是输入的端口要保证在对方路由器上是开放的。