After setting up a non blocking socket correctly I do the following to connect:
- Call connect on the socket.
- If it returns 0, I have already connected, if not, check errno.
- If errno is not EINPROGRESS there is an error.
All of the above is correct (except under Windows you'd need to check for WSAEWOULDBLOCK instead of EINPROGRESS).
- if errno is EINPROGRESS I can poll the connect status by: select_status = sock_select(FD_SETSIZE, NULL, &file_descriptor_set, NULL, &timeout); if select_status > 0 then check with FD_ISSET if the file descriptor is set.
Correct (assuming sock_select() is the same thing as select()), except that FD_SETSIZE should be the maximum value of all the file-descriptor values you are watching, plus 1.
Is that correct? And should I check for fd_write not fd_read?
Right.
What tells me that the connection was made?
When the async-connection-operation has completed, select() will return and FD_ISSET(theSocket, &writeSet) will return true.
When that happens, you need to find out if the connection attempt succeeded or failed. Here's a function I use for that:
// Returns true if the async connection on (fd) is connected; false if it failed
bool DidTheAsyncTCPConnectionSucceed(int fd)
{
struct sockaddr_in junk;
socklen_t length = sizeof(junk);
memset(&junk, 0, sizeof(junk));
return (getpeername(fd, (struct sockaddr *)&junk, &length) == 0);
}
If that returns true, your socket is connected and ready to use in the normal ways. If it returns false, the async-connection failed and you should close() the socket and handle that failure somehow.
(Again there is a slightly different behavior under Windows; under Windows, getting notified about the connection succeeding works as described above, but if you want to be notified about the connection failing, you'll need to watch the exception-fd-set as well. Under Windows, FD_ISSET(fd, &exceptionSet) is what will notify you when the asynchronous TCP connection failed).