From cf1d4d515e19ba3ed6b4834ca8f57ec3d5718498 Mon Sep 17 00:00:00 2001 From: tmoonlight Date: Tue, 26 Nov 2019 17:11:50 +0800 Subject: [PATCH] bugfix: tcp packet broken while client send config to server --- .../ServerConnectionManager.cs | 1 + .../Extensions/StreamExtension.cs | 28 +++++++++++++++++-- .../Shared/NSPVersion.cs | 4 +-- src/NSmartProxy/Server.cs | 4 ++- src/build_simple.cmd | 2 +- 5 files changed, 32 insertions(+), 7 deletions(-) diff --git a/src/NSmartProxy.ClientRouter/ServerConnectionManager.cs b/src/NSmartProxy.ClientRouter/ServerConnectionManager.cs index b78bc09..500e798 100644 --- a/src/NSmartProxy.ClientRouter/ServerConnectionManager.cs +++ b/src/NSmartProxy.ClientRouter/ServerConnectionManager.cs @@ -94,6 +94,7 @@ private async Task SendConfigRequest() var config = ClientConfig; Router.Logger.Debug("Reading Config From Provider.."); TcpClient configClient = new TcpClient(); + configClient.NoDelay = true;//配置协议不使用nagle bool isConnected = false; bool isReconn = (this.ClientID != 0); //TODO XXX如果clientid已经分配到了id 则算作重连 for (int j = 0; j < 3; j++) //连接服务端 diff --git a/src/NSmartProxy.Infrastructure/Extensions/StreamExtension.cs b/src/NSmartProxy.Infrastructure/Extensions/StreamExtension.cs index aed1851..c0f96df 100644 --- a/src/NSmartProxy.Infrastructure/Extensions/StreamExtension.cs +++ b/src/NSmartProxy.Infrastructure/Extensions/StreamExtension.cs @@ -48,7 +48,7 @@ public static async Task WriteAndFlushAsync(this Stream stream, byte[] buffer, i /// /// /// - public static async Task ReadAsync(this NetworkStream stream, byte[] buffer, int offset, int count, int timeOut) + public static async Task ReadAsync(this Stream stream, byte[] buffer, int offset, int count, int timeOut) { var receiveCount = 0; var receiveTask = Task.Run(async () => { receiveCount = await stream.ReadAsync(buffer, offset, count); }); @@ -57,10 +57,32 @@ public static async Task ReadAsync(this NetworkStream stream, byte[] buffer return receiveCount; } + /// + /// 读取接下来N字节的定长数据,如果服务端没有发那么多信息, + /// 可能会出现读不全的情况,也有可能出现阻塞超时的情况 + /// + public static async Task ReadNextSTLengthBytes(this Stream stream, byte[] buffer) + { + int restBufferLength = buffer.Length; + int totalReceivedBytes = 0; + while (restBufferLength > 0) + { + int receivedBytes = await stream.ReadAsyncEx(buffer, totalReceivedBytes, restBufferLength); + if (receivedBytes <= 0) return -1;//没有接收满则断开返回-1 + totalReceivedBytes += receivedBytes; + restBufferLength -= receivedBytes; + } + return totalReceivedBytes; + } + + public static async Task ReadAsyncEx(this Stream stream, byte[] buffer, int offset, int count) + { + return await stream.ReadAsync(buffer, offset, count, Global.DefaultConnectTimeout); + } - public static async Task ReadAsyncEx(this NetworkStream stream, byte[] buffer) + public static async Task ReadAsyncEx(this Stream stream, byte[] buffer) { - return await stream.ReadAsync(buffer, 0, buffer.Length, Global.DefaultConnectTimeout); + return await stream.ReadAsyncEx(buffer, 0, buffer.Length); } public static Stream ProcessSSL(this Stream clientStream, X509Certificate cert) diff --git a/src/NSmartProxy.Infrastructure/Shared/NSPVersion.cs b/src/NSmartProxy.Infrastructure/Shared/NSPVersion.cs index a17f619..d35c2a0 100644 --- a/src/NSmartProxy.Infrastructure/Shared/NSPVersion.cs +++ b/src/NSmartProxy.Infrastructure/Shared/NSPVersion.cs @@ -2,6 +2,6 @@ public sealed class NSPVersion { public const string NO_TOKEN_STRING = "notoken"; - public const string NSmartProxyClientName = "NSmartProxy Client v1.2.7102.9914"; - public const string NSmartProxyServerName = "NSmartProxy Server v1.2.7102.9914"; + public const string NSmartProxyClientName = "NSmartProxy Client v1.2.7103.8377"; + public const string NSmartProxyServerName = "NSmartProxy Server v1.2.7103.8377"; } \ No newline at end of file diff --git a/src/NSmartProxy/Server.cs b/src/NSmartProxy/Server.cs index 58b89a8..dcbdc6f 100644 --- a/src/NSmartProxy/Server.cs +++ b/src/NSmartProxy/Server.cs @@ -701,10 +701,12 @@ private async Task ProcessAppRequestProtocol(TcpClient client, bool IsReco //port proto option(iscompress) host description //2 1 1 1024 96 byte[] consumerPortBytes = new byte[appCount * (2 + 1 + 1 + 1024 + 96)];//TODO 2 暂时这么写,亟需修改 - int resultByte2 = await nstream.ReadAsyncEx(consumerPortBytes); + int resultByte2 = await nstream.ReadNextSTLengthBytes(consumerPortBytes); + // int resultBytetest = await nstream.ReadAsyncEx(consumerPortBytes); //Server.Logger.Debug("consumerPortBytes received."); if (resultByte2 < 1) { + Server.Logger.Debug("定长包没有正确接收"); CloseClient(client); return true; } diff --git a/src/build_simple.cmd b/src/build_simple.cmd index 9a17cd0..b859b23 100644 --- a/src/build_simple.cmd +++ b/src/build_simple.cmd @@ -2,7 +2,7 @@ rem windows only rem NSP v1.1 @ECHO off -set Ver=v1.2_final3 +set Ver=v1.2_final4 set BuildPath=%~dp0../build set nsp_server_path=%BuildPath%/nspclient_%Ver%