int tcp_sock = ::socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
struct sockaddr_in remoteaddr;
struct sockaddr_in localAddr;
short local_port = 22222;
short remote_port = 33333;
// local addr
localAddr.sin_family = AF_INET;
localAddr.sin_port = htons(local_port);
localAddr.sin_addr.s_addr = 0xC0A80AA5; // we don't give a shit
int addrLen = sizeof(struct sockaddr_in);
//Now bind TCP to local addr
int result = bind(tcp_sock,(struct sockaddr*)&localAddr,addrLen);
if (result < 0)
{
perror("\nbind failed");
close(tcp_sock);
return -1;
}
result = connect(tcp_sock, (struct sockaddr*)&remoteaddr, sizeof(struct sockaddr_in));
printf("\nConnect returned %d, error no: %d", result, errno);
Here the connect()
call fails after a long time. Is there any way that I can make connect
function return after a time of my choice? I tried calling close()
from another thread but this doesn't change anything.
Put the socket into non-blocking mode before calling connect()
, then you can use select()
to specify a timeout. select()
will tell you whether the connection succeeds or times out. If successful, you can put the socket back into blocking mode, if you want. If failed/timeout, close the socket instead.
int tcp_sock = ::socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
...
int flags = fcntl(tcp_sock, F_GETFL, 0);
fcntl(tcp_sock, F_SETFL, flags | O_NONBLOCK);
int errCode = 0;
result = connect(tcp_sock, ...);
if (result < 0)
{
errCode = errno;
if (errCode == EINPROGRESS)
{
fd_set wfd;
FD_ZERO(&wfd);
FD_SET(tcp_sock, &wfd);
struct timeval timeout;
timeout.tv_sec = ...;
timeout.tv_usec = ...;
result = select(tcp_sock+1, NULL, &wfd, NULL, &timeout);
if (result > 0)
{
socklen_t len = sizeof(errCode);
result = getsockopt(tcp_sock, SOL_SOCKET, SO_ERROR, &errCode, &len);
if (result < 0)
errCode = errno;
else
result = (errCode == 0) ? 0 : -1;
}
else if (result == 0)
{
errCode = ETIMEDOUT;
result = -1;
}
else
{
errCode = errno;
}
}
}
if (result == 0)
{
// connected
fcntl(tcp_sock, F_SETFL, flags);
...
}
else
{
// error, use errCode as needed
...
}