/// <summary> /// Starts the synchronous authentication process. /// </summary> /// <exception cref="SocksProxyException">Authentication with the proxy server failed.</exception> /// <exception cref="ProtocolViolationException">The proxy server uses an invalid protocol.</exception> /// <exception cref="SocketException">An operating system error occurs while accessing the Socket.</exception> /// <exception cref="ObjectDisposedException">The Socket has been closed.</exception> private void Authenticate() { Server.Send(new byte[] { 5, 2, 0, 2 }); var buffer = ReadBytes(2); if (buffer[1] == 255) { throw new SocksProxyException("No authentication method accepted."); } // Detect authentication type IAuthProtocol authenticate; switch (buffer[1]) { case 0: authenticate = new AuthNoneSocket(Server); break; case 2: authenticate = new AuthUserPassSocket(Server, new NetworkCredential(Username, Password)); break; default: throw new ProtocolViolationException(); } // Attempt to authenticate authenticate.Authenticate(); }
/// <summary> /// Called when an authentication reply has been received. /// </summary> /// <param name="ar">Stores state information for this asynchronous operation as well as any user-defined data.</param> private void OnAuthReceive(IAsyncResult ar) { try { Received += Server.EndReceive(ar); if (Received <= 0) { throw new SocketException(); } } catch (Exception e) { handShakeComplete(e); return; } try { if (Received < 2) { Server.BeginReceive(Buffer, Received, Buffer.Length - Received, SocketFlags.None, OnAuthReceive, Server); } else { IAuthProtocol authenticate; switch (Buffer[1]) { case 0: authenticate = new AuthNoneSocket(Server); break; case 2: var credential = new NetworkCredential(Username, Password); authenticate = new AuthUserPassSocket(Server, credential); break; default: handShakeComplete(new SocketException()); return; } authenticate.BeginAuthenticate(OnAuthenticated); } } catch (Exception e) { handShakeComplete(e); } }