Пример #1
0
        /// <summary>
        /// 端口映射监听端口的新tcp回调方法
        /// </summary>
        /// <param name="ar"></param>
        public void AcceptSocket_Server(IAsyncResult ar)
        {
            ListenSt    st       = (ListenSt)ar.AsyncState;
            TcpListener listener = st.listener;
            PortMapItem item     = st.item;
            Socket      socket   = null;

            try
            {
                //获取当前接入的tcp
                socket = listener.EndAcceptSocket(ar);
            }
            catch (Exception ex)
            {
                LogUtils.Error(ex.ToString());
                return;
            }

            EasyOp.Do(() =>
            {
                listener.BeginAcceptSocket(AcceptSocket_Server, st);
            }, () =>
            {
                EasyOp.Do(() =>
                {
                    if (tcpCenter.P2PServerTcp != null && tcpCenter.P2PServerTcp.Connected)
                    {
                        P2PTcpClient tcpClient = new P2PTcpClient(socket);
                        //加入待连接集合
                        P2PResult result = new P2PResult();
                        tcpCenter.WaiteConnetctTcp.Add(tcpClient.Token, result);
                        //tcpCenter.WaiteConnetctTcp.Add(tcpClient.Token, tcpClient);
                        //发送消息给服务端,开始内网穿透
                        Send_0x0201_Apply packet = new Send_0x0201_Apply(tcpClient.Token, item.RemoteAddress, item.RemotePort, item.P2PType);
                        LogUtils.Debug(string.Format("正在建立{0}隧道 token:{1} client:{2} port:{3}", item.P2PType == 0 ? "中转模式" : "P2P模式", tcpClient.Token, item.RemoteAddress, item.RemotePort));

                        byte[] dataAr = packet.PackData();
                        EasyOp.Do(() =>
                        {
                            tcpCenter.P2PServerTcp.BeginSend(dataAr);
                        }, () =>
                        {
                            //等待指定超时时间后,判断是否连接成功

                            Monitor.Enter(result.block);
                            if (Monitor.Wait(result.block, AppConfig.P2PTimeout))
                            {
                                if (tcpCenter.WaiteConnetctTcp[tcpClient.Token].IsError)
                                {
                                    LogUtils.Debug(tcpCenter.WaiteConnetctTcp[tcpClient.Token].ErrorMsg);
                                    tcpClient.SafeClose();
                                }
                                else
                                {
                                    P2PTcpClient destTcp = tcpCenter.WaiteConnetctTcp[tcpClient.Token].Tcp;
                                    tcpClient.IsAuth     = destTcp.IsAuth = true;
                                    destTcp.ToClient     = tcpClient;
                                    tcpClient.ToClient   = destTcp;
                                    if (item.P2PType == 0)
                                    {
                                        Global_Func.ListenTcp <Packet_0x0202>(tcpClient);
                                        LogUtils.Debug($"中转模式隧道,连接成功 token:{tcpClient.Token}");
                                    }
                                    else
                                    {
                                        if (Global_Func.BindTcp(tcpClient, destTcp))
                                        {
                                            LogUtils.Debug($"P2P模式隧道,连接成功 token:{tcpClient.Token}");
                                        }
                                        else
                                        {
                                            LogUtils.Debug($"P2P模式隧道,连接失败 token:{tcpClient.Token}");
                                            EasyOp.Do(tcpClient.SafeClose);
                                            EasyOp.Do(destTcp.SafeClose);
                                        }
                                    }
                                }
                            }
                            else
                            {
                                LogUtils.Debug($"建立隧道失败:token:{tcpClient.Token} {item.LocalPort}->{item.RemoteAddress}:{item.RemotePort} {AppConfig.P2PTimeout / 1000}秒无响应,已超时.");
                                EasyOp.Do(tcpClient.SafeClose);
                            }
                            tcpCenter.WaiteConnetctTcp.Remove(tcpClient.Token);
                            Monitor.Exit(result.block);
                            //if (tcpCenter.WaiteConnetctTcp.ContainsKey(tcpClient.Token))
                            //{
                            //    LogUtils.Debug($"建立隧道失败:token:{tcpClient.Token} {item.LocalPort}->{item.RemoteAddress}:{item.RemotePort} {AppConfig.P2PTimeout / 1000}秒无响应,已超时.");
                            //    tcpCenter.WaiteConnetctTcp[tcpClient.Token].tcp?.SafeClose();
                            //    tcpCenter.WaiteConnetctTcp.Remove(tcpClient.Token);
                            //}
                        }, ex =>
                        {
                            EasyOp.Do(tcpClient.SafeClose);
                            LogUtils.Debug($"建立隧道失败,无法连接服务器:token:{tcpClient.Token} {item.LocalPort}->{item.RemoteAddress}:{item.RemotePort}.");
                        });
                    }
                    else
                    {
                        LogUtils.Debug($"建立隧道失败:未连接到服务器!");
                        socket.Close();
                    }
                }, ex =>
                {
                    LogUtils.Debug("处理新tcp连接时发生错误:" + Environment.NewLine + ex.ToString());
                });
            }, ex =>
            {
                LogUtils.Error("监听端口发生错误:" + listener.LocalEndpoint.ToString() + Environment.NewLine + ex.ToString());
            });
        }
Пример #2
0
        public bool CreateP2PConnect(PortMapItem item, Socket socket)
        {
            bool ret = false;

            if (tcpCenter.P2PServerTcp != null && tcpCenter.P2PServerTcp.Connected)
            {
                P2PTcpClient tcpClient = new P2PTcpClient(socket);
                //加入待连接集合
                P2PResult result = new P2PResult();
                tcpCenter.WaiteConnetctTcp.Add(tcpClient.Token, result);
                //tcpCenter.WaiteConnetctTcp.Add(tcpClient.Token, tcpClient);
                //发送消息给服务端,开始内网穿透
                Send_0x0201_Apply packet = new Send_0x0201_Apply(tcpClient.Token, item.RemoteAddress, item.RemotePort, item.P2PType);
                LogUtils.Debug(string.Format("正在建立{0}隧道 token:{1} client:{2} port:{3}", item.P2PType == 0 ? "中转模式" : "P2P模式", tcpClient.Token, item.RemoteAddress, item.RemotePort));

                byte[] dataAr = packet.PackData();
                EasyOp.Do(() =>
                {
                    tcpCenter.P2PServerTcp.BeginSend(dataAr);
                }, () =>
                {
                    Monitor.Enter(result.block);
                    if (Monitor.Wait(result.block, AppConfig.P2PTimeout))
                    {
                        if (tcpCenter.WaiteConnetctTcp[tcpClient.Token].IsError)
                        {
                            LogUtils.Debug(tcpCenter.WaiteConnetctTcp[tcpClient.Token].ErrorMsg);
                            //tcpClient.SafeClose();
                        }
                        else
                        {
                            P2PTcpClient destTcp = tcpCenter.WaiteConnetctTcp[tcpClient.Token].Tcp;
                            tcpClient.IsAuth     = destTcp.IsAuth = true;
                            destTcp.ToClient     = tcpClient;
                            tcpClient.ToClient   = destTcp;
                            if (item.P2PType == 0)
                            {
                                Global_Func.ListenTcp <Packet_0x0202>(tcpClient);
                                ret = true;
                                LogUtils.Debug($"中转模式隧道,连接成功 token:{tcpClient.Token}");
                            }
                            else
                            {
                                if (Global_Func.BindTcp(tcpClient, destTcp))
                                {
                                    ret = true;
                                    LogUtils.Debug($"P2P模式隧道,连接成功 token:{tcpClient.Token}");
                                }
                                else
                                {
                                    LogUtils.Debug($"P2P模式隧道,连接失败 token:{tcpClient.Token}");
                                    EasyOp.Do(destTcp.SafeClose);
                                }
                            }
                        }
                    }
                    else
                    {
                        LogUtils.Debug($"建立隧道失败:token:{tcpClient.Token} {item.LocalPort}->{item.RemoteAddress}:{item.RemotePort} {AppConfig.P2PTimeout / 1000}秒无响应,已超时.");
                    }
                    tcpCenter.WaiteConnetctTcp.Remove(tcpClient.Token);
                    Monitor.Exit(result.block);
                }, ex =>
                {
                    LogUtils.Debug($"建立隧道失败,无法连接服务器:token:{tcpClient.Token} {item.LocalPort}->{item.RemoteAddress}:{item.RemotePort}.");
                });
            }
            else
            {
                LogUtils.Debug($"建立隧道失败:未连接到服务器!");
            }
            return(ret);
        }