예제 #1
0
 private void ResetState()
 {
     step     = -1;
     myStream = null;
     bs.ResetSelf();
     pos = 0;
 }
예제 #2
0
 private void Dequeue(BytesSegment bs, int len)
 {
     Queue.CopyTo(bs, len);
     Queue.SubSelf(len);
     if (Queue.Len == 0)
     {
         Queue.ResetSelf();
     }
 }
예제 #3
0
        private AwaitableWrapper <BytesSegment> ReadNBAsyncRWrapper(int maxSize)
        {
            if (_nb_ra == null)
            {
                _nb_ra = new ReusableAwaiter <BytesSegment>();
            }
            else
            {
                _nb_ra.Reset();
            }
            var bs      = BufferPool.GlobalGetBs(maxSize);
            var awaiter = BaseStream.ReadAsyncR(bs);

            if (awaiter.IsCompleted)
            {
                _nb_ra.SetResult(bs.Sub(0, awaiter.GetResult()));
            }
            else
            {
                _nb_bs = bs;
                if (_nb_continuation == null)
                {
                    _nb_continuation = () => {
                        var _bs      = _nb_bs;
                        var _awaiter = _nb_awaiter;
                        _nb_bs.ResetSelf();
                        _nb_awaiter = default(AwaitableWrapper <int>);
                        int r;
                        try {
                            r = _awaiter.GetResult();
                        } catch (Exception e) {
                            _nb_ra.SetException(e);
                            return;
                        }
                        _nb_ra.SetResult(_bs.Sub(0, r));
                    }
                }
                ;
                _nb_awaiter = awaiter;
                awaiter.OnCompleted(_nb_continuation);
            }
            return(new AwaitableWrapper <BytesSegment>(_nb_ra));
        }
예제 #4
0
            public async Task Copy(int bs, bool shutdown)
            {
                if (WhenCanRead != null)
                {
                    await WhenCanRead;
                }

                IMsgStream msgStream = (From as MsgStreamToMyStream)?.MsgStream;

                if (bs == -1)
                {
                    bs = defaultBufferSize;
                }
                Naive.HttpSvr.BytesSegment buf;
                Msg lastMsg = new Msg();

                if (msgStream != null || (From is IMyStreamNoBuffer && !TryReadSync))
                {
                    buf = new BytesSegment();
                }
                else
                {
                    buf = BufferPool.GlobalGet(bs);
                }
                try {
                    int syncCounter = 0;
                    while (true)
                    {
                        BytesSegment tempBuf = new BytesSegment();
                        if (syncCounter > 64)
                        {
                            syncCounter = 0;
                            await Task.Yield();
                        }

                        // read:
                        int read;
                        if (msgStream != null)
                        {
                            // no buffer preallocated for IMsgStream
                            var msg = await msgStream.RecvMsgR(null).SyncCounter(ref syncCounter);

                            lastMsg = msg;
                            if (msg.IsEOF)
                            {
                                read = 0;
                            }
                            else
                            {
                                read = msg.Data.tlen;
                                if (msg.Data.nextNode == null)
                                {
                                    buf = new BytesSegment(msg.Data);
                                }
                                else
                                {
                                    buf = msg.Data.GetBytes();
                                }
                            }
                        }
                        else if (TryReadSync && From is IMyStreamSync fromSync)
                        {
                            read = fromSync.Read(buf);
                        }
                        else if (From is IMyStreamNoBuffer nb)
                        {
                            tempBuf = await nb.ReadNBAsyncR(bs).SyncCounter(ref syncCounter);

                            buf  = tempBuf;
                            read = tempBuf.Len;
                        }
                        else
                        {
                            read = await From.ReadAsyncR(buf).SyncCounter(ref syncCounter);
                        }

                        // handle shutdown:
                        if (read == 0)
                        {
                            VerboseLogger?.debugForce($"SHUTDOWN: {From} -> {To}");
                            if (shutdown && !To.State.HasShutdown)
                            {
                                await To.Shutdown(SocketShutdown.Send).CAF();
                            }
                            break;
                        }

                        ProcessPayload(buf.Sub(0, read));

                        Progress += read;
                        CounterR?.Add(read);

                        // write:
                        if (TryWriteSync && To is IMyStreamSync toSync)
                        {
                            toSync.Write(new BytesSegment(buf.Bytes, buf.Offset, read));
                        }
                        else
                        {
                            await To.WriteAsyncR(new BytesSegment(buf.Bytes, buf.Offset, read)).SyncCounter(ref syncCounter);
                        }
                        CounterW?.Add(read);

                        // recycle buffer if possible:
                        if (lastMsg.Data != null)
                        {
                            lastMsg.TryRecycle();
                            buf.ResetSelf();
                        }
                        if (tempBuf.Bytes != null)
                        {
                            BufferPool.GlobalPut(tempBuf.Bytes);
                            tempBuf.ResetSelf();
                            buf.ResetSelf();
                        }
                    }
                } finally {
                    VerboseLogger?.debugForce($"STOPPED: {From} -> {To}");
                    //if (buf.Bytes != null) {
                    //    BufferPool.GlobalPut(buf.Bytes);
                    //}
                }
            }