示例#1
0
        public Socks5AuthResponse(Memory <byte> outputBuffer, Socks5AuthMethod method)
        {
            if (outputBuffer.Length < 2)
            {
                ThrowHelper.ThrowArgumentOutOfRange(nameof(outputBuffer), "Размер буфера должен быть больше или равен 2.");
            }

            outputBuffer.Span[0] = 0x05; // Версия SOCKS.
            outputBuffer.Span[1] = (byte)method;
            BufferSlice          = outputBuffer.Slice(0, 2);
        }
示例#2
0
        public static async ValueTask <Socks5AuthRequest> ReceiveAsync(ManagedTcpSocket managedTcp, Memory <byte> buffer)
        {
            Debug.Assert(buffer.Length >= MaximumSize);

            // Как минимум должно быть 2 байта.
            SocketReceiveResult rcvResult = await managedTcp.ReceiveBlockAsync(buffer.Slice(0, 2)).ConfigureAwait(false);

            if (!rcvResult.ReceiveSuccess)
            {
                return(new Socks5AuthRequest(authMethods: null));
            }

            byte version = buffer.Span[0];

            if (version != 5)
            {
                throw new InvalidOperationException($"Не верный номер версии Socks. Получено {version}, ожидалось 5");
            }

            // Количество поддерживаемых методов аутентификации.
            byte authCount = buffer.Span[1];

            // Номера методов аутентификации, переменная длина, 1 байт для каждого поддерживаемого метода.
            Memory <byte> authSpan = buffer.Slice(2, authCount);

            rcvResult = await managedTcp.ReceiveBlockAsync(authSpan).ConfigureAwait(false);

            if (!rcvResult.ReceiveSuccess)
            {
                return(new Socks5AuthRequest(authMethods: null));
            }

            var authMethods = new Socks5AuthMethod[authSpan.Length];

            for (int i = 0; i < authSpan.Length; i++)
            {
                Socks5AuthMethod a = (Socks5AuthMethod)authSpan.Span[i];
                if (Enum.IsDefined(typeof(Socks5AuthMethod), a))
                {
                    authMethods[i] = a;
                }
                else
                {
                    ThrowHelper.ThrowException(new InvalidOperationException("Ошибка протокола SOCKS 5"));
                }
            }

            return(new Socks5AuthRequest(authMethods));
        }
示例#3
0
        static Socks5ParseResult Parse(byte[] request, int requestLength, out Socks5AuthMethod[] methods)
        {
            methods = new Socks5AuthMethod[0];

            // +-----+----------+----------+
            // | VER | NMETHODS | METHODS  |
            // +-----+----------+----------+
            // |  1  |    1     | 1 to 255 |
            // +-----+----------+----------+
            if (requestLength < 1)
            {
                return(Socks5ParseResult.NotEnoughData);
            }

            if (request[0] != 0x05)
            {
                return(Socks5ParseResult.InvalidRequest);
            }

            if (requestLength < 2)
            {
                return(Socks5ParseResult.NotEnoughData);
            }

            int n = request[1];

            if (requestLength < 2 + n)
            {
                return(Socks5ParseResult.NotEnoughData);
            }

            methods = new Socks5AuthMethod[n];
            for (int i = 0; i < n; i++)
            {
                methods[i] = (Socks5AuthMethod)request[2 + i];
            }

            return(Socks5ParseResult.Success);
        }
示例#4
0
 public void AddMethod(Socks5AuthMethod method)
 {
     AddMethod((byte)method);
 }