private void OnGetFullResponse(SocksContext context) { List <byte> receivedData = context.ReceivedData; if (receivedData[0] != 5) { OnException("invalid protocol version"); return; } byte b = receivedData[1]; if (b == 0) { OnCompleted(new ProxyEventArgs(context.Socket)); return; } string empty = string.Empty; switch (b) { case 2: empty = "connection not allowed by ruleset"; break; case 3: empty = "network unreachable"; break; case 4: empty = "host unreachable"; break; case 5: empty = "connection refused by destination host"; break; case 6: empty = "TTL expired"; break; case 7: empty = "command not supported / protocol error"; break; case 8: empty = "address type not supported"; break; default: empty = "general failure"; break; } OnException(empty); }
protected override void ProcessSend(SocketAsyncEventArgs e) { if (ValidateAsyncResult(e)) { SocksContext socksContext = e.UserToken as SocksContext; if (socksContext.State == SocksState.NotAuthenticated) { e.SetBuffer(0, 2); StartReceive(socksContext.Socket, e); } else if (socksContext.State == SocksState.Authenticating) { e.SetBuffer(0, 2); StartReceive(socksContext.Socket, e); } else { e.SetBuffer(0, e.Buffer.Length); StartReceive(socksContext.Socket, e); } } }
private void OnGetFullResponse(SocksContext context) { var response = context.ReceivedData; if (response[0] != 0x05) { OnException("invalid protocol version"); return; } var status = response[1]; if (status == 0x00) { OnCompleted(new ProxyEventArgs(context.Socket)); return; } //0x01 = general failure //0x02 = connection not allowed by ruleset //0x03 = network unreachable //0x04 = host unreachable //0x05 = connection refused by destination host //0x06 = TTL expired //0x07 = command not supported / protocol error //0x08 = address type not supported string message = string.Empty; switch (status) { case (0x02): message = "connection not allowed by ruleset"; break; case (0x03): message = "network unreachable"; break; case (0x04): message = "host unreachable"; break; case (0x05): message = "connection refused by destination host"; break; case (0x06): message = "TTL expired"; break; case (0x07): message = "command not supported / protocol error"; break; case (0x08): message = "address type not supported"; break; default: message = "general failure"; break; } OnException(message); }
private void SendHandshake(SocketAsyncEventArgs e) { SocksContext socksContext = e.UserToken as SocksContext; EndPoint targetEndPoint = socksContext.TargetEndPoint; int num = 0; byte[] array; int num2; if (targetEndPoint is IPEndPoint) { IPEndPoint iPEndPoint = targetEndPoint as IPEndPoint; num = iPEndPoint.Port; if (iPEndPoint.AddressFamily == AddressFamily.InterNetwork) { array = new byte[10] { 0, 0, 0, 1, 0, 0, 0, 0, 0, 0 }; Buffer.BlockCopy(iPEndPoint.Address.GetAddressBytes(), 0, array, 4, 4); } else { if (iPEndPoint.AddressFamily != AddressFamily.InterNetworkV6) { OnException("unknown address family"); return; } array = new byte[22]; array[3] = 4; Buffer.BlockCopy(iPEndPoint.Address.GetAddressBytes(), 0, array, 4, 16); } num2 = array.Length; } else { DnsEndPoint dnsEndPoint = targetEndPoint as DnsEndPoint; num = dnsEndPoint.Port; array = new byte[7 + ProxyConnectorBase.ASCIIEncoding.GetMaxByteCount(dnsEndPoint.Host.Length)]; array[3] = 3; num2 = 5; num2 += ProxyConnectorBase.ASCIIEncoding.GetBytes(dnsEndPoint.Host, 0, dnsEndPoint.Host.Length, array, num2); num2 += 2; } array[0] = 5; array[1] = 1; array[2] = 0; array[num2 - 2] = (byte)(num / 256); array[num2 - 1] = (byte)(num % 256); e.SetBuffer(array, 0, num2); socksContext.ReceivedData = new List <byte>(num2 + 5); socksContext.ExpectedLength = 5; StartSend(socksContext.Socket, e); }
protected override void ProcessReceive(SocketAsyncEventArgs e) { if (!ValidateAsyncResult(e)) { return; } SocksContext socksContext = (SocksContext)e.UserToken; if (socksContext.State == SocksState.NotAuthenticated) { if (ProcessAuthenticationResponse(socksContext.Socket, e)) { switch (e.Buffer[1]) { case 0: socksContext.State = SocksState.Authenticated; SendHandshake(e); break; case 2: socksContext.State = SocksState.Authenticating; AutheticateWithUserNamePassword(e); break; case byte.MaxValue: OnException("no acceptable methods were offered"); break; default: OnException("protocol error"); break; } } return; } if (socksContext.State == SocksState.Authenticating) { if (ProcessAuthenticationResponse(socksContext.Socket, e)) { if (e.Buffer[1] == 0) { socksContext.State = SocksState.Authenticated; SendHandshake(e); } else { OnException("authentication failure"); } } return; } byte[] array = new byte[e.BytesTransferred]; Buffer.BlockCopy(e.Buffer, e.Offset, array, 0, e.BytesTransferred); socksContext.ReceivedData.AddRange(array); if (socksContext.ExpectedLength > socksContext.ReceivedData.Count) { StartReceive(socksContext.Socket, e); } else if (socksContext.State != SocksState.FoundLength) { int num; switch (socksContext.ReceivedData[3]) { case 1: num = 10; break; case 3: num = 7 + socksContext.ReceivedData[4]; break; default: num = 22; break; } if (socksContext.ReceivedData.Count < num) { socksContext.ExpectedLength = num; StartReceive(socksContext.Socket, e); } else if (socksContext.ReceivedData.Count > num) { OnException("response length exceeded"); } else { OnGetFullResponse(socksContext); } } else if (socksContext.ReceivedData.Count > socksContext.ExpectedLength) { OnException("response length exceeded"); } else { OnGetFullResponse(socksContext); } }