diff --git a/src/async_io.rs b/src/async_io.rs index bf7a265..e05a60b 100644 --- a/src/async_io.rs +++ b/src/async_io.rs @@ -570,6 +570,20 @@ impl Async { // Wait for connect to complete. let wait_connect = |mut stream: &TcpStream| match stream.write(&[]) { Err(err) if err.kind() == io::ErrorKind::NotConnected => { + // On other systems, if a non-blocking connect call fails, a + // sensible error code is returned by the send (write) call. + // + // But not on Windows. If a non-blocking connect call fails, the + // send call always returns NotConnected. We have to use + // take_error (i.e., getsockopt SO_ERROR) to find out whether + // the connect call has failed, and retrieve the error code if + // it has. + #[cfg(windows)] + { + if let Some(e) = stream.take_error()? { + return Err(e); + } + } Err(io::ErrorKind::WouldBlock.into()) } res => res.map(|_| ()), diff --git a/tests/async_io.rs b/tests/async_io.rs index 9c0c7cf..6cda9c1 100644 --- a/tests/async_io.rs +++ b/tests/async_io.rs @@ -35,6 +35,9 @@ fn tcp_connection() -> io::Result<()> { stream1.get_ref().local_addr()? ); + // Now that the listener is closed, connect should fail. + Async::::connect(&addr).await.unwrap_err(); + Ok(()) }) }