ehensens
asked on
How do I make my cpp connect() timeout?
Hi all,
I have an iPhone app that utilizes a cpp class I made that HTTP posts to my server. I am currently trying to detect when the user has entered in a bad IP address. Please see the attached line of code. With some bogus IP addresses, the connect() command goes through and returns n = -1, and I therefore know when to flag an error and tell the user to change the IP.
The problem is, with SOME IP addresses, the connect() doesn't go through and return n= -1 or something like that, it just SITS there on that line, indefinitely. Meanwhile, the app looks like it has crashed.
How do I make the program go on after a certain length of time if the connect() statement doesn't progress on its own?
I have an iPhone app that utilizes a cpp class I made that HTTP posts to my server. I am currently trying to detect when the user has entered in a bad IP address. Please see the attached line of code. With some bogus IP addresses, the connect() command goes through and returns n = -1, and I therefore know when to flag an error and tell the user to change the IP.
The problem is, with SOME IP addresses, the connect() doesn't go through and return n= -1 or something like that, it just SITS there on that line, indefinitely. Meanwhile, the app looks like it has crashed.
How do I make the program go on after a certain length of time if the connect() statement doesn't progress on its own?
int n = connect(socketFD, (SOCKA *) & serverAddress, sizeof(serverAddress));
You can make the socket non-blocking. Then the connect immediately returns with socket error -1 and errno set to E_WOULDBLOCK (GetLastError() == WSAEWOULDBLOCK on Windows). You, then could call select with timeout to check whether the socket has turned to a writeable state. When select returns timeout you could cancel the connect and output a user message.
ASKER
Hi itsmeandnobodyelse,
Could you give an example? And where do I make the socket non-blocking, on my server or on my client?
Could you give an example? And where do I make the socket non-blocking, on my server or on my client?
To set the socket non-blocking do
unsigned long onoff = 1;
int rc = ioctlsocket(socketFD, FIONBIO, &onoff);
if (rc < 0) return rc; // socket error
if you pass onoff = 0 the socket was reset to blocking mode.
To check for connection is ok you do
int n = connect(socketFD, (SOCKA *) & serverAddress, sizeof(serverAddress));
if (n < 0 && errno == E_WOULDBLOCK)
{
fd_set writeset = { 0 };
TIMEVAL timeout = {TIMEOUT_SECS, TIMEOUT_USECS};
FD_SET(socketFD, &writeset);
int rc = select(0, NULL, &writeset, NULL, &timeout);
if (rc == 0) // timeout
{
}
}
unsigned long onoff = 1;
int rc = ioctlsocket(socketFD, FIONBIO, &onoff);
if (rc < 0) return rc; // socket error
if you pass onoff = 0 the socket was reset to blocking mode.
To check for connection is ok you do
int n = connect(socketFD, (SOCKA *) & serverAddress, sizeof(serverAddress));
if (n < 0 && errno == E_WOULDBLOCK)
{
fd_set writeset = { 0 };
TIMEVAL timeout = {TIMEOUT_SECS, TIMEOUT_USECS};
FD_SET(socketFD, &writeset);
int rc = select(0, NULL, &writeset, NULL, &timeout);
if (rc == 0) // timeout
{
}
}
>>> And where do I make the socket non-blocking, on my server or on my client?
On the client just before the connection. You should make it reverse to blocking (normally) after getting a connection.
On the client just before the connection. You should make it reverse to blocking (normally) after getting a connection.
ASKER
Are there extra include files I need? I am getting error "TIMEVAL was not declared in this scope"
ASKER
Also,
FIONBIO was not declared
ioctlsocket was not declared
FIONBIO was not declared
ioctlsocket was not declared
>>>> FIONBIO was not declared
Hmm. It was FIONBIO at Unix and Windows. Can you check your docs for ioctlsocket? Or ctlsocket? I mean to remember that there was a naming mixup with ioctlsocket.
>>>> Are there extra include files I need?
Probably. The TIMEVAL is a struct with two unsigned long. You can make your own structure or check your docs what select is expecting for last argument.
Hmm. It was FIONBIO at Unix and Windows. Can you check your docs for ioctlsocket? Or ctlsocket? I mean to remember that there was a naming mixup with ioctlsocket.
>>>> Are there extra include files I need?
Probably. The TIMEVAL is a struct with two unsigned long. You can make your own structure or check your docs what select is expecting for last argument.
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
ASKER
yup thats it, thanks