Inheritance: BaseOverlappedAsyncResult
Exemplo n.º 1
0
        // Implements ConnectEx - this provides completion port IO and support for disconnect and reconnects.
        // Since this is private, the unsafe mode is specified with a flag instead of an overload.
        private IAsyncResult BeginConnectEx(EndPoint remoteEP, bool flowContext, AsyncCallback callback, object state)
        {
            if (s_loggingEnabled)
            {
                Logging.Enter(Logging.Sockets, this, "BeginConnectEx", "");
            }

            // This will check the permissions for connect.
            EndPoint endPointSnapshot = remoteEP;
            Internals.SocketAddress socketAddress = flowContext ? CheckCacheRemote(ref endPointSnapshot, true) : SnapshotAndSerialize(ref endPointSnapshot);

            // The socket must be bound first.
            // The calling method--BeginConnect--will ensure that this method is only
            // called if _rightEndPoint is not null, of that the endpoint is an IPEndPoint.
            if (_rightEndPoint == null)
            {
                GlobalLog.Assert(endPointSnapshot.GetType() == typeof(IPEndPoint), "Socket#{0}::BeginConnectEx()|Socket not bound and endpoint not IPEndPoint.", Logging.HashString(this));
                if (endPointSnapshot.AddressFamily == AddressFamily.InterNetwork)
                {
                    InternalBind(new IPEndPoint(IPAddress.Any, 0));
                }
                else
                {
                    InternalBind(new IPEndPoint(IPAddress.IPv6Any, 0));
                }
            }

            // Allocate the async result and the event we'll pass to the thread pool.
            ConnectOverlappedAsyncResult asyncResult = new ConnectOverlappedAsyncResult(this, endPointSnapshot, state, callback);

            // If context flowing is enabled, set it up here.  No need to lock since the context isn't used until the callback.
            if (flowContext)
            {
                asyncResult.StartPostingAsyncOp(false);
            }

            EndPoint oldEndPoint = _rightEndPoint;
            if (_rightEndPoint == null)
            {
                _rightEndPoint = endPointSnapshot;
            }

            SocketError errorCode;
            try
            {
                errorCode = SocketPal.ConnectAsync(this, _handle, socketAddress.Buffer, socketAddress.Size, asyncResult);
            }
            catch
            {
                // If ConnectEx throws we need to unpin the socketAddress buffer.
                // _rightEndPoint will always equal oldEndPoint.
                asyncResult.InternalCleanup();
                _rightEndPoint = oldEndPoint;
                throw;
            }


            if (errorCode == SocketError.Success)
            {
                SetToConnected();
            }

            GlobalLog.Print("Socket#" + Logging.HashString(this) + "::BeginConnectEx() Interop.Winsock.connect returns:" + errorCode.ToString());

            errorCode = asyncResult.CheckAsyncCallOverlappedResult(errorCode);

            // Throw an appropriate SocketException if the native call fails synchronously.
            if (errorCode != SocketError.Success)
            {
                // Update the internal state of this socket according to the error before throwing.
                _rightEndPoint = oldEndPoint;
                SocketException socketException = new SocketException((int)errorCode);
                UpdateStatusAfterSocketError(socketException);
                if (s_loggingEnabled)
                {
                    Logging.Exception(Logging.Sockets, this, "BeginConnectEx", socketException);
                }
                throw socketException;
            }

            // We didn't throw, so indicate that we're returning this result to the user.  This may call the callback.
            // This is a nop if the context isn't being flowed.
            asyncResult.FinishPostingAsyncOp(ref Caches.ConnectClosureCache);

            GlobalLog.Print("Socket#" + Logging.HashString(this) + "::BeginConnectEx() to:" + endPointSnapshot.ToString() + " returning AsyncResult:" + Logging.HashString(asyncResult));
            if (s_loggingEnabled)
            {
                Logging.Exit(Logging.Sockets, this, "BeginConnectEx", asyncResult);
            }
            return asyncResult;
        }
Exemplo n.º 2
0
 public static SocketError ConnectAsync(Socket socket, SafeCloseSocket handle, byte[] socketAddress, int socketAddressLen, ConnectOverlappedAsyncResult asyncResult)
 {
     return handle.AsyncContext.ConnectAsync(socketAddress, socketAddressLen, asyncResult.CompletionCallback);
 }
Exemplo n.º 3
0
        public static unsafe SocketError ConnectAsync(Socket socket, SafeCloseSocket handle, byte[] socketAddress, int socketAddressLen, ConnectOverlappedAsyncResult asyncResult)
        {
            // This will pin the socketAddress buffer.
            asyncResult.SetUnmanagedStructures(socketAddress);

            int ignoreBytesSent;

            if (!socket.ConnectEx(
                    handle,
                    Marshal.UnsafeAddrOfPinnedArrayElement(socketAddress, 0),
                    socketAddressLen,
                    IntPtr.Zero,
                    0,
                    out ignoreBytesSent,
                    asyncResult.OverlappedHandle))
            {
                return(GetLastSocketError());
            }

            return(SocketError.Success);
        }
Exemplo n.º 4
0
        public static unsafe SocketError ConnectAsync(Socket socket, SafeCloseSocket handle, byte[] socketAddress, int socketAddressLen, ConnectOverlappedAsyncResult asyncResult)
        {
            // This will pin the socketAddress buffer.
            asyncResult.SetUnmanagedStructures(socketAddress);
            try
            {
                int  ignoreBytesSent;
                bool success = socket.ConnectEx(
                    handle,
                    Marshal.UnsafeAddrOfPinnedArrayElement(socketAddress, 0),
                    socketAddressLen,
                    IntPtr.Zero,
                    0,
                    out ignoreBytesSent,
                    asyncResult.OverlappedHandle);

                return(asyncResult.ProcessOverlappedResult(success, 0));
            }
            catch
            {
                asyncResult.ReleaseUnmanagedStructures();
                throw;
            }
        }
Exemplo n.º 5
0
        //Implements ConnectEx - this provides completion port IO and support for
        //disconnect and reconnects

        // Since this is private, the unsafe mode is specified with a flag instead of an overload.
        private IAsyncResult BeginConnectEx(EndPoint remoteEP, bool flowContext, AsyncCallback callback, object state)
        {
            if(s_LoggingEnabled)Logging.Enter(Logging.Sockets, this, "BeginConnectEx", "");

            // This will check the permissions for connect.
            EndPoint endPointSnapshot = remoteEP;
            SocketAddress socketAddress = flowContext ? CheckCacheRemote(ref endPointSnapshot, true) : SnapshotAndSerialize(ref endPointSnapshot);

            //socket must be bound first
            //the calling method BeginConnect will ensure that this method is only
            //called if m_RightEndPoint is not null, of that the endpoint is an ipendpoint
            if (m_RightEndPoint==null){
                GlobalLog.Assert(endPointSnapshot.GetType() == typeof(IPEndPoint), "Socket#{0}::BeginConnectEx()|Socket not bound and endpoint not IPEndPoint.", ValidationHelper.HashString(this));
                if (endPointSnapshot.AddressFamily == AddressFamily.InterNetwork)
                    InternalBind(new IPEndPoint(IPAddress.Any, 0));
                else
                    InternalBind(new IPEndPoint(IPAddress.IPv6Any, 0));
            }

            //
            // Allocate the async result and the event we'll pass to the
            // thread pool.
            //
            ConnectOverlappedAsyncResult asyncResult = new ConnectOverlappedAsyncResult(this, endPointSnapshot, state, callback);

            // If context flowing is enabled, set it up here.  No need to lock since the context isn't used until the callback.
            if (flowContext)
            {
                asyncResult.StartPostingAsyncOp(false);
            }

            // This will pin socketAddress buffer
            asyncResult.SetUnmanagedStructures(socketAddress.m_Buffer);

            //we should fix this in Whidbey.
            EndPoint oldEndPoint = m_RightEndPoint;
            if (m_RightEndPoint == null) {
                  m_RightEndPoint = endPointSnapshot;
            }

            SocketError errorCode=SocketError.Success;

            int ignoreBytesSent;

            try
            {
                if (!ConnectEx(
                    m_Handle,
                    Marshal.UnsafeAddrOfPinnedArrayElement(socketAddress.m_Buffer, 0),
                    socketAddress.m_Size,
                    IntPtr.Zero,
                    0,
                    out ignoreBytesSent,
                    asyncResult.OverlappedHandle))
                {
                    errorCode = (SocketError)Marshal.GetLastWin32Error();
                }
            }
            catch
            {
                //
                // Bug 152350: If ConnectEx throws we need to unpin the socketAddress buffer.
                // m_RightEndPoint will always equal oldEndPoint anyways...
                //
                asyncResult.InternalCleanup();
                m_RightEndPoint = oldEndPoint;
                throw;
            }


            if (errorCode == SocketError.Success) {
                SetToConnected();
            }

            GlobalLog.Print("Socket#" + ValidationHelper.HashString(this) + "::BeginConnectEx() UnsafeNclNativeMethods.OSSOCK.connect returns:" + errorCode.ToString());

            errorCode = asyncResult.CheckAsyncCallOverlappedResult(errorCode);

            //
            // if the asynchronous native call fails synchronously
            // we'll throw a SocketException
            //
            if (errorCode != SocketError.Success) {
                //
                // update our internal state after this socket error and throw
                //
                m_RightEndPoint = oldEndPoint;
                SocketException socketException = new SocketException(errorCode);
                UpdateStatusAfterSocketError(socketException);
                if(s_LoggingEnabled)Logging.Exception(Logging.Sockets, this, "BeginConnectEx", socketException);
                throw socketException;
            }

            // We didn't throw, so indicate that we're returning this result to the user.  This may call the callback.
            // This is a nop if the context isn't being flowed.
            asyncResult.FinishPostingAsyncOp(ref Caches.ConnectClosureCache);

            GlobalLog.Print("Socket#" + ValidationHelper.HashString(this) + "::BeginConnectEx() to:" + endPointSnapshot.ToString() + " returning AsyncResult:" + ValidationHelper.HashString(asyncResult));
            if(s_LoggingEnabled)Logging.Exit(Logging.Sockets, this, "BeginConnectEx", asyncResult);
            return asyncResult;
        }
Exemplo n.º 6
0
        public static unsafe SocketError ConnectAsync(Socket socket, SafeCloseSocket handle, byte[] socketAddress, int socketAddressLen, ConnectOverlappedAsyncResult asyncResult)
        {
            // This will pin the socketAddress buffer.
            asyncResult.SetUnmanagedStructures(socketAddress);

            int ignoreBytesSent;
            if (!socket.ConnectEx(
                handle,
                Marshal.UnsafeAddrOfPinnedArrayElement(socketAddress, 0),
                socketAddressLen,
                IntPtr.Zero,
                0,
                out ignoreBytesSent,
                asyncResult.OverlappedHandle))
            {
                return GetLastSocketError();
            }

            return SocketError.Success;
        }
Exemplo n.º 7
0
 private IAsyncResult BeginConnectEx(EndPoint remoteEP, bool flowContext, AsyncCallback callback, object state)
 {
     if (Socket.s_LoggingEnabled)
     Logging.Enter(Logging.Sockets, (object) this, "BeginConnectEx", "");
       EndPoint remoteEP1 = remoteEP;
       SocketAddress socketAddress = flowContext ? this.CheckCacheRemote(ref remoteEP1, true) : this.SnapshotAndSerialize(ref remoteEP1);
       if (this.m_RightEndPoint == null)
       {
     if (remoteEP1.AddressFamily == AddressFamily.InterNetwork)
       this.InternalBind((EndPoint) new IPEndPoint(IPAddress.Any, 0));
     else
       this.InternalBind((EndPoint) new IPEndPoint(IPAddress.IPv6Any, 0));
       }
       ConnectOverlappedAsyncResult overlappedAsyncResult = new ConnectOverlappedAsyncResult(this, remoteEP1, state, callback);
       if (flowContext)
     overlappedAsyncResult.StartPostingAsyncOp(false);
       overlappedAsyncResult.SetUnmanagedStructures((object) socketAddress.m_Buffer);
       EndPoint endPoint = this.m_RightEndPoint;
       if (this.m_RightEndPoint == null)
     this.m_RightEndPoint = remoteEP1;
       SocketError errorCode = SocketError.Success;
       try
       {
     int bytesSent;
     if (!this.ConnectEx(this.m_Handle, Marshal.UnsafeAddrOfPinnedArrayElement((Array) socketAddress.m_Buffer, 0), socketAddress.m_Size, IntPtr.Zero, 0, out bytesSent, overlappedAsyncResult.OverlappedHandle))
       errorCode = (SocketError) Marshal.GetLastWin32Error();
       }
       catch
       {
     overlappedAsyncResult.InternalCleanup();
     this.m_RightEndPoint = endPoint;
     throw;
       }
       if (errorCode == SocketError.Success)
     this.SetToConnected();
       SocketError socketError = overlappedAsyncResult.CheckAsyncCallOverlappedResult(errorCode);
       if (socketError != SocketError.Success)
       {
     this.m_RightEndPoint = endPoint;
     SocketException socketException = new SocketException(socketError);
     this.UpdateStatusAfterSocketError(socketException);
     if (Socket.s_LoggingEnabled)
       Logging.Exception(Logging.Sockets, (object) this, "BeginConnectEx", (Exception) socketException);
     throw socketException;
       }
       else
       {
     overlappedAsyncResult.FinishPostingAsyncOp(ref this.Caches.ConnectClosureCache);
     if (Socket.s_LoggingEnabled)
       Logging.Exit(Logging.Sockets, (object) this, "BeginConnectEx", (object) overlappedAsyncResult);
     return (IAsyncResult) overlappedAsyncResult;
       }
 }
 private IAsyncResult BeginConnectEx(EndPoint remoteEP, bool flowContext, AsyncCallback callback, object state)
 {
     if (s_LoggingEnabled)
     {
         Logging.Enter(Logging.Sockets, this, "BeginConnectEx", "");
     }
     EndPoint point = remoteEP;
     SocketAddress address = flowContext ? this.CheckCacheRemote(ref point, true) : this.SnapshotAndSerialize(ref point);
     if (this.m_RightEndPoint == null)
     {
         if (point.AddressFamily == System.Net.Sockets.AddressFamily.InterNetwork)
         {
             this.InternalBind(new IPEndPoint(IPAddress.Any, 0));
         }
         else
         {
             this.InternalBind(new IPEndPoint(IPAddress.IPv6Any, 0));
         }
     }
     ConnectOverlappedAsyncResult retObject = new ConnectOverlappedAsyncResult(this, point, state, callback);
     if (flowContext)
     {
         retObject.StartPostingAsyncOp(false);
     }
     retObject.SetUnmanagedStructures(address.m_Buffer);
     EndPoint rightEndPoint = this.m_RightEndPoint;
     if (this.m_RightEndPoint == null)
     {
         this.m_RightEndPoint = point;
     }
     SocketError success = SocketError.Success;
     try
     {
         int num;
         if (!this.ConnectEx(this.m_Handle, Marshal.UnsafeAddrOfPinnedArrayElement(address.m_Buffer, 0), address.m_Size, IntPtr.Zero, 0, out num, retObject.OverlappedHandle))
         {
             success = (SocketError) Marshal.GetLastWin32Error();
         }
     }
     catch
     {
         retObject.InternalCleanup();
         this.m_RightEndPoint = rightEndPoint;
         throw;
     }
     if (success == SocketError.Success)
     {
         this.SetToConnected();
     }
     success = retObject.CheckAsyncCallOverlappedResult(success);
     if (success != SocketError.Success)
     {
         this.m_RightEndPoint = rightEndPoint;
         SocketException socketException = new SocketException(success);
         this.UpdateStatusAfterSocketError(socketException);
         if (s_LoggingEnabled)
         {
             Logging.Exception(Logging.Sockets, this, "BeginConnectEx", socketException);
         }
         throw socketException;
     }
     retObject.FinishPostingAsyncOp(ref this.Caches.ConnectClosureCache);
     if (s_LoggingEnabled)
     {
         Logging.Exit(Logging.Sockets, this, "BeginConnectEx", retObject);
     }
     return retObject;
 }