diff --git a/src/P2PSocket.Client/Commands/Cmd_0x0201.cs b/src/P2PSocket.Client/Commands/Cmd_0x0201.cs index 17738f0..c5f6058 100644 --- a/src/P2PSocket.Client/Commands/Cmd_0x0201.cs +++ b/src/P2PSocket.Client/Commands/Cmd_0x0201.cs @@ -43,6 +43,14 @@ public override bool Excute() { tcpCenter.WaiteConnetctTcp[token].P2PType = p2pType; } + else + { + tcpCenter.WaiteConnetctTcp.Add(token, new P2PResult() { P2PType = p2pType }); + TimerUtils.Instance.AddJob(() => + { + tcpCenter.WaiteConnetctTcp.Remove(token); + }, 30000); + } if (p2pType == 0) { if (isDestClient) CreateTcpFromDest(token); @@ -100,7 +108,7 @@ protected virtual void TryBindP2PTcp() p2pClient.UpdateEndPoint(); }, ex => { - LogUtils.Trace($"命令:0x0201 P2P模式隧道,端口打洞错误{ex}"); + LogUtils.Trace($"命令:0x0201 P2P模式隧道,端口打洞错误:{p2pClient.Client.LocalEndPoint} -> {ip}:{port}{Environment.NewLine}{ex}"); }); tryCount--; } diff --git a/src/P2PSocket.Client/P2PClient.cs b/src/P2PSocket.Client/P2PClient.cs index 65466c1..332d008 100644 --- a/src/P2PSocket.Client/P2PClient.cs +++ b/src/P2PSocket.Client/P2PClient.cs @@ -216,91 +216,91 @@ public void AcceptSocket_Server(IAsyncResult ar) { EasyOp.Do(() => { - if (tcpCenter.P2PServerTcp != null && tcpCenter.P2PServerTcp.Connected) + if(!CreateP2PConnect(item, socket)) { - 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)); + EasyOp.Do(socket.SafeClose); + } + }, ex => + { + LogUtils.Debug("处理新tcp连接时发生错误:" + Environment.NewLine + ex.ToString()); + }); + }, ex => + { + LogUtils.Error("监听端口发生错误:" + listener.LocalEndpoint.ToString() + Environment.NewLine + ex.ToString()); + }); + } + + 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(() => + 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) { - tcpCenter.P2PServerTcp.BeginSend(dataAr); - }, () => + LogUtils.Debug(tcpCenter.WaiteConnetctTcp[tcpClient.Token].ErrorMsg); + //tcpClient.SafeClose(); + } + else { - //等待指定超时时间后,判断是否连接成功 - - Monitor.Enter(result.block); - if (Monitor.Wait(result.block, AppConfig.P2PTimeout)) + 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(tcpClient); + ret = true; + LogUtils.Debug($"中转模式隧道,连接成功 token:{tcpClient.Token}"); + } + else { - if (tcpCenter.WaiteConnetctTcp[tcpClient.Token].IsError) + if (Global_Func.BindTcp(tcpClient, destTcp)) { - LogUtils.Debug(tcpCenter.WaiteConnetctTcp[tcpClient.Token].ErrorMsg); - tcpClient.SafeClose(); + ret = true; + LogUtils.Debug($"P2P模式隧道,连接成功 token:{tcpClient.Token}"); } 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(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); - } - } + 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}秒无响应,已超时."); - 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(); + 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("处理新tcp连接时发生错误:" + Environment.NewLine + ex.ToString()); + LogUtils.Debug($"建立隧道失败,无法连接服务器:token:{tcpClient.Token} {item.LocalPort}->{item.RemoteAddress}:{item.RemotePort}."); }); - }, ex => + } + else { - LogUtils.Error("监听端口发生错误:" + listener.LocalEndpoint.ToString() + Environment.NewLine + ex.ToString()); - }); + LogUtils.Debug($"建立隧道失败:未连接到服务器!"); + } + return ret; } struct ListenSt