private Task WrapAsync(IShadowsocksCrypto encryptor, CancellationToken cancellationToken)
    {
        return(Task.Run(
                   async() =>
        {
            try
            {
                while (true)
                {
                    ReadResult result = await Reader.ReadAsync(cancellationToken);
                    ReadOnlySequence <byte> buffer = result.Buffer;

                    foreach (ReadOnlyMemory <byte> segment in buffer)
                    {
                        SendToRemote(segment.Span);
                        FlushResult flushResult = await InternalWriter.FlushAsync(cancellationToken);
                        if (flushResult.IsCompleted)
                        {
                            goto NoData;
                        }
                    }

                    Reader.AdvanceTo(buffer.End);

                    if (result.IsCompleted)
                    {
                        break;
                    }
                }
                NoData:
                await Reader.CompleteAsync();
            }
            catch (Exception ex)
            {
                await Reader.CompleteAsync(ex);
            }
            finally
            {
                encryptor.Dispose();
            }
        },
                   default
                   ));

        void SendToRemote(ReadOnlySpan <byte> buffer)
        {
            while (!buffer.IsEmpty)
            {
                Span <byte> span = InternalWriter.GetSpan(BufferSize);

                encryptor.EncryptTCP(buffer, span, out int p, out int outLength);

                InternalWriter.Advance(outLength);

                if (p == buffer.Length)
                {
                    break;
                }

                buffer = buffer[p..];
Beispiel #2
0
    public static void Test(string method)
    {
        Console.Write($@"Testing {method}: ");

        ReadOnlySpan <byte> i = new byte[Step];
        Span <byte>         o = new byte[AEADShadowsocksCrypto.GetBufferSize(i.Length)];

        using IShadowsocksCrypto crypto = ShadowsocksCrypto.Create(method, Password);
        ulong     length = 0ul;
        Stopwatch sw     = Stopwatch.StartNew();

        do
        {
            crypto.EncryptTCP(i, o, out int pLength, out _);
            length += (uint)pLength;
        } while (sw.ElapsedMilliseconds < 2000);

        sw.Stop();
        double result = length / sw.Elapsed.TotalSeconds / 1024.0 / 1024.0;

        Console.WriteLine($@"{result:F2} MB/s");
    }