コード例 #1
0
        private void SendItem(ReceiveSendItem item)
        {
            SocketAsyncEventArgs args = cache.PopOrCreate();

            args.Completed += Send_Completed;
            SendItem(item, args);
        }
コード例 #2
0
 private void ReceiveItem(ReceiveSendItem item, SocketAsyncEventArgs args)
 {
     args.UserToken = item;
     if (!socket.ReceiveAsync(args))
     {
         Receive_Completed(socket, args);
     }
 }
コード例 #3
0
        private void SendItem(ReceiveSendItem item, SocketAsyncEventArgs args)
        {
            args.UserToken = item;
            int cplen = Math.Min(args.Count, item.Count);

            Array.Copy(item.Buffer, item.Offset, args.Buffer, args.Offset, cplen);
            args.SetBuffer(args.Offset, cplen);
            if (!socket.SendAsync(args))
            {
                Send_Completed(socket, args);
            }
        }
コード例 #4
0
 private bool TryDequeue(out ReceiveSendItem item)
 {
     if (realtimeQueue.TryDequeue(out item))
     {
         return(true);
     }
     if (backgroundQueue.TryDequeue(out item))
     {
         return(true);
     }
     return(false);
 }
コード例 #5
0
        private void Receive_Completed(object sender, SocketAsyncEventArgs e)
        {
            ReceiveSendItem item = (ReceiveSendItem)e.UserToken;

            if (e.SocketError == SocketError.Shutdown || e.SocketError == SocketError.OperationAborted)
            {
                item.Tcs.SetResult(false);
                RecycleReceive(e);
                return;
            }
            else if (e.SocketError != SocketError.Success)
            {
                item.Tcs.SetResult(false);
                RecycleReceive(e);
                exhandler.CloseConnection(e.SocketError, e.LastOperation);
                return;
            }
            if (e.BytesTransferred == 0)
            {
                item.Tcs.SetResult(false);
                RecycleReceive(e);
                exhandler.CloseConnection(SocketError.Disconnecting, e.LastOperation);
                return;
            }
            ReceivedBytes += e.BytesTransferred; // for statistics
            int cplen = Math.Min(e.BytesTransferred, item.Count);

            Array.Copy(e.Buffer, e.Offset, item.Buffer, item.Offset, cplen);
            item.Offset += cplen;
            item.Count  -= cplen;
            if (item.Count > 0)
            {
                ReceiveItem(item, e);
            }
            else if (e.BytesTransferred - cplen > 0)
            {
                e.SetBuffer(e.Offset + cplen, e.BytesTransferred - cplen);
                receiveCache = e;
                item.Tcs.SetResult(true);
                // Do not recycle this item now when we cache its buffer
            }
            else
            {
                item.Tcs.SetResult(true);
                RecycleReceive(e);
            }
        }
コード例 #6
0
        private void Send_Completed(object sender, SocketAsyncEventArgs e)
        {
            ReceiveSendItem item = (ReceiveSendItem)e.UserToken;

            if (e.SocketError == SocketError.Shutdown)
            {
                item.Tcs.SetResult(false);
                RecycleSend(e);
                return;
            }
            else if (e.SocketError != SocketError.Success)
            {
                item.Tcs.SetResult(false);
                exhandler.CloseConnection(e.SocketError, e.LastOperation);
                RecycleSend(e);
                return;
            }
            if (e.BytesTransferred == 0)
            {
                item.Tcs.SetResult(false);
                exhandler.CloseConnection(SocketError.ConnectionReset, e.LastOperation);
                RecycleSend(e);
                return;
            }
            SentBytes   += e.BytesTransferred; // for statistics
            item.Offset += e.BytesTransferred;
            item.Count  -= e.BytesTransferred;
            if (item.Count > 0)
            {
                SendItem(item, e);
            }
            else
            {
                item.Tcs.SetResult(true);
                RecycleSend(e);
                StartSend(locked: false);
            }
        }
コード例 #7
0
        /// <summary>
        /// Sends data to the remote host asynchronously.
        /// </summary>
        /// <exception cref="ObjectDisposedException" />
        public Task <bool> SendAsync(byte[] buffer, int offset, int count, bool background)
        {
            if (disposed)
            {
                throw new ObjectDisposedException(GetType().FullName);
            }
            if (shutdown)
            {
                return(Task.FromResult(false));
            }

            ReceiveSendItem item = new ReceiveSendItem(buffer, offset, count);

            if (background)
            {
                backgroundQueue.Enqueue(item);
            }
            else
            {
                realtimeQueue.Enqueue(item);
            }
            EnsureSend();
            return(item.Task);
        }
コード例 #8
0
        /// <summary>
        /// Receives the specified count of bytes from the remote host asynchronously. This method is not threadsafe!
        /// </summary>
        /// <exception cref="ObjectDisposedException" />
        public Task <bool> ReceiveAsync(byte[] buffer, int offset, int count)
        {
            if (disposed)
            {
                throw new ObjectDisposedException(GetType().FullName);
            }
            if (shutdown)
            {
                return(Task.FromResult(false));
            }

            if (receiveCache != null)
            {
                int cplen = Math.Min(receiveCache.Count, count);
                Array.Copy(receiveCache.Buffer, receiveCache.Offset, buffer, offset, cplen);
                receiveCache.SetBuffer(receiveCache.Offset + cplen, receiveCache.Count - cplen);
                offset += cplen;
                count  -= cplen;

                if (receiveCache.Count == 0)
                {
                    RecycleReceive(receiveCache);
                    receiveCache = null;
                }
            }
            if (count > 0)
            {
                ReceiveSendItem item = new ReceiveSendItem(buffer, offset, count);
                ReceiveItem(item);
                return(item.Task);
            }
            else
            {
                return(Task.FromResult(true));
            }
        }