Пример #1
0
        private void AsyncEndReceive(IAsyncResult iar)
        {
            // Asynchronous receive operations will complete here through the call
            // to AsyncBeginReceive

            // aquire a reader lock
            rwLock.AcquireReaderLock(-1);

            if (!shutdownFlag)
            {
                // start another receive - this keeps the server going!
                AsyncBeginReceive();

                // get the buffer that was created in AsyncBeginReceive
                // this is the received data
                WrappedObject <UDPPacketBuffer> wrappedBuffer = (WrappedObject <UDPPacketBuffer>)iar.AsyncState;
                UDPPacketBuffer buffer = wrappedBuffer.Instance;
                //UDPPacketBuffer buffer = (UDPPacketBuffer)iar.AsyncState;

                try
                {
                    // get the length of data actually read from the socket, store it with the
                    // buffer
                    buffer.DataLength = udpSocket.EndReceiveFrom(iar, ref buffer.RemoteEndPoint);

                    // this operation is now complete, decrement the reference count
                    Interlocked.Decrement(ref rwOperationCount);

                    // we're done with the socket, release the reader lock
                    rwLock.ReleaseReaderLock();

                    // call the abstract method PacketReceived(), passing the buffer that
                    // has just been filled from the socket read.
                    PacketReceived(buffer);
                }
                catch (SocketException)
                {
                    // something bad happened
                    //SecondLife.LogStatic(
                    //    "A SocketException occurred in UDPServer.AsyncEndReceive()",
                    //    Helpers.LogLevel.Error, se);

                    // an error occurred, therefore the operation is void.  Decrement the reference count.
                    Interlocked.Decrement(ref rwOperationCount);

                    // we're done with the socket for now, release the reader lock.
                    rwLock.ReleaseReaderLock();
                }

                wrappedBuffer.Dispose();
            }
            else
            {
                // nothing bad happened, but we are done with the operation
                // decrement the reference count and release the reader lock
                Interlocked.Decrement(ref rwOperationCount);
                rwLock.ReleaseReaderLock();
            }
        }
Пример #2
0
        /// <summary>
        /// Checks an instance of <c>T</c> from the pool. If the pool is not sufficient to
        /// allow the checkout, a new segment is created.
        /// </summary>
        /// <returns>A <c>WrappedObject</c> around the instance of <c>T</c>. To check
        /// the instance back into the segment, be sureto dispose the WrappedObject
        /// when finished. </returns>
        public WrappedObject <T> CheckOut()
        {
            if (_disposed)
            {
                throw new ObjectDisposedException("ObjectPoolBase");
            }

            // It's key that this CheckOut always, always, uses a pooled object
            // from the oldest available segment. This will help keep the "newer"
            // segments from being used - which in turn, makes them eligible
            // for deletion.


            lock (_syncRoot)
            {
                ObjectPoolSegment <T> targetSegment = null;

                // find the oldest segment that has items available for checkout
                for (int i = 0; i < _activeSegment; i++)
                {
                    ObjectPoolSegment <T> segment;
                    if (_segments.TryGetValue(i, out segment) == true)
                    {
                        if (segment.AvailableItems > 0)
                        {
                            targetSegment = segment;
                            break;
                        }
                    }
                }

                if (targetSegment == null)
                {
                    // We couldn't find a sigment that had any available space in it,
                    // so it's time to create a new segment.

                    // Before creating the segment, do a GC to make sure the heap
                    // is compacted.
                    if (_gc)
                    {
                        GC.Collect();
                    }

                    targetSegment = CreateSegment(true);

                    if (_gc)
                    {
                        GC.Collect();
                    }

                    _segments.Add(targetSegment.SegmentNumber, targetSegment);
                }

                WrappedObject <T> obj = new WrappedObject <T>(this, targetSegment, targetSegment.CheckOutObject());
                return(obj);
            }
        }
Пример #3
0
        private void AsyncBeginReceive()
        {
            // this method actually kicks off the async read on the socket.
            // we aquire a reader lock here to ensure that no other thread
            // is trying to set shutdownFlag and close the socket.
            rwLock.AcquireReaderLock(-1);

            if (!shutdownFlag)
            {
                // increment the count of pending operations
                Interlocked.Increment(ref rwOperationCount);

                // allocate a packet buffer
                WrappedObject <UDPPacketBuffer> buf = _bufferPool.CheckOut();
                //UDPPacketBuffer buf = new UDPPacketBuffer();

                try
                {
                    // kick off an async read
                    udpSocket.BeginReceiveFrom(
                        buf.Instance.Data,
                        //buf.Data,
                        0,
                        UDPPacketBuffer.BUFFER_SIZE,
                        SocketFlags.None,
                        ref buf.Instance.RemoteEndPoint,
                        new AsyncCallback(AsyncEndReceive),
                        buf);
                }
                catch (SocketException)
                {
                    // something bad happened
                    //SecondLife.LogStatic(
                    //    "A SocketException occurred in UDPServer.AsyncBeginReceive()",
                    //    Helpers.LogLevel.Error, se);

                    // an error occurred, therefore the operation is void.  Decrement the reference count.
                    Interlocked.Decrement(ref rwOperationCount);
                }
            }

            // we're done with the socket for now, release the reader lock.
            rwLock.ReleaseReaderLock();
        }