Socket中如何设置连接超时(转)
2011-06-28 10:34
525 查看
http://tangfeng.iteye.com/blog/795497
Socket中可以使用select设置连接超时,需要先将socket设置为非锁定模式,这样,在connect时,才会立马跳过,同时,通常也会产生一个WSAEWOULDBLOCK错误,这个错误没关系。再执行select则是真正的超时。
C++代码
![](http://tangfeng.iteye.com/images/icon_star.png)
WSADATA wsd;
SOCKET cClient;
int ret;
struct sockaddr_in server;
hostent *host = NULL;
if (WSAStartup(MAKEWORD(2,0), &wsd))
{
return 0;
}
cClient = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (cClient == INVALID_SOCKET)
{
return 0;
}
// set Recv and Send time out
DWORD TimeOut = 6000; // 设置发送超时6秒
if (::setsockopt(cClient, SOL_SOCKET, SO_SNDTIMEO, (char *)&TimeOut, sizeof(TimeOut)) == SOCKET_ERROR)
{
return 0;
}
TimeOut = 6000; // 设置接收超时6秒
if (::setsockopt(cClient, SOL_SOCKET, SO_RCVTIMEO, (char *)&TimeOut, sizeof(TimeOut)) == SOCKET_ERROR)
{
return 0;
}
// 设置非阻塞方式连接
unsigned long ul = 1;
ret = ioctlsocket(cClient, FIONBIO, (unsigned long*)&ul);
if (ret == SOCKET_ERROR)
return 0;
// 连接
server.sin_family = AF_INET;
server.sin_port = htons(25);
server.sin_addr.s_addr = inet_addr((LPCSTR)pSmtp);
if (server.sin_addr.s_addr == INADDR_NONE)
return 0;
connect(cClient, (const struct sockaddr*)&server, sizeof(server));
// select 模型,即设置超时
struct timeval timeout ;
fd_set r;
FD_ZERO(&r);
FD_SET(cClient, &r);
timeout.tv_sec = 15; // 连接超时15秒
timeout.tv_usec = 0;
ret = select(0, 0, &r, 0, &timeout);
if (ret <= 0)
{
::closesocket(cClient);
return 0;
}
// 一般非锁定模式套接字比较难控制,可以根据实际情况考虑再设回阻塞模式
unsigned long ul1 = 0;
ret = ioctlsocket(cClient, FIONBIO, (unsigned long*)&ul1);
if (ret == SOCKET_ERROR)
{
::closesocket(cClient);
return 0;
}
Socket中可以使用select设置连接超时,需要先将socket设置为非锁定模式,这样,在connect时,才会立马跳过,同时,通常也会产生一个WSAEWOULDBLOCK错误,这个错误没关系。再执行select则是真正的超时。
C++代码
![](http://tangfeng.iteye.com/images/icon_star.png)
WSADATA wsd;
SOCKET cClient;
int ret;
struct sockaddr_in server;
hostent *host = NULL;
if (WSAStartup(MAKEWORD(2,0), &wsd))
{
return 0;
}
cClient = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (cClient == INVALID_SOCKET)
{
return 0;
}
// set Recv and Send time out
DWORD TimeOut = 6000; // 设置发送超时6秒
if (::setsockopt(cClient, SOL_SOCKET, SO_SNDTIMEO, (char *)&TimeOut, sizeof(TimeOut)) == SOCKET_ERROR)
{
return 0;
}
TimeOut = 6000; // 设置接收超时6秒
if (::setsockopt(cClient, SOL_SOCKET, SO_RCVTIMEO, (char *)&TimeOut, sizeof(TimeOut)) == SOCKET_ERROR)
{
return 0;
}
// 设置非阻塞方式连接
unsigned long ul = 1;
ret = ioctlsocket(cClient, FIONBIO, (unsigned long*)&ul);
if (ret == SOCKET_ERROR)
return 0;
// 连接
server.sin_family = AF_INET;
server.sin_port = htons(25);
server.sin_addr.s_addr = inet_addr((LPCSTR)pSmtp);
if (server.sin_addr.s_addr == INADDR_NONE)
return 0;
connect(cClient, (const struct sockaddr*)&server, sizeof(server));
// select 模型,即设置超时
struct timeval timeout ;
fd_set r;
FD_ZERO(&r);
FD_SET(cClient, &r);
timeout.tv_sec = 15; // 连接超时15秒
timeout.tv_usec = 0;
ret = select(0, 0, &r, 0, &timeout);
if (ret <= 0)
{
::closesocket(cClient);
return 0;
}
// 一般非锁定模式套接字比较难控制,可以根据实际情况考虑再设回阻塞模式
unsigned long ul1 = 0;
ret = ioctlsocket(cClient, FIONBIO, (unsigned long*)&ul1);
if (ret == SOCKET_ERROR)
{
::closesocket(cClient);
return 0;
}
相关文章推荐
- Socket中如何设置连接超时
- Socket中如何设置连接超时(转)
- Socket中如何设置连接超时(转)
- Socket中如何设置连接超时
- Socket中如何设置连接超时
- Socket中如何设置连接超时
- Socket中如何设置连接超时
- Socket中如何设置连接超时-通过测试
- Socket中如何设置连接超时-通过测试
- Socket中如何设置连接超时(转)
- 【转载】Socket中如何设置连接超时
- Socket中如何设置连接超时
- Socket中如何设置连接超时
- Socket中如何设置连接超时(转载 可能用的到)
- 如何设置socket的连接超时
- Socket中如何设置连接超时
- Socket中如何设置连接超时-通过测试(VC)
- 【转载】Socket中如何设置连接超时-通过测试(VC)
- Socket中如何设置连接超时
- Socket中如何设置连接超时(转):仅仅为了记录