Linux C套接字选项SO_RCVTIMEO, SO_SNDTIMEO介绍

本文介绍了如何使用套接字选项SO_RCVTIMEO和SO_SNDTIMEO来设置socket接收和发送数据的超时时间,以避免进程因等待对端响应而无限期阻塞。当超时发生时,相关系统调用将返回-1并设置errno为EAGAIN或EWOULDBLOCK。文中提供了两个示例,一个是设置connect超时,另一个是设置recv超时,展示了如何在客户端和服务器端实现超时机制。

套接字选项SO_RCVTIMEO: 用来设置socket接收数据的超时时间; 套接字选项SO_SNDTIMEO: 用来设置socket发送数据的超时时间;

比如,一般情况下,调用accept/connect/send/recv, 进程会阻塞,但是如果对端异常,进行可能无法正常退出等待。如何让这些调用自动定时退出? 可以使用诸如alarm定时器、I/O复用设置定时器,还可以使用socket编程里函数级别的socket套接字选项SO_RCVTIMEO和SO_SNDTIMEO,仅针对与数据接收和发送相关,而无需设置专门的信号捕获函数。

能够作用的系统调用包括:send、sendmsg、recv、recvmsg、accept、connect。

系统调用 有效选项 系统调用超时后的行为
send SO_SNDTIMEO 返回-1,设置errno为EAGAIN或EWOULDBLOCK
sendmsg SO_SNDTIMEO 返回-1,设置errno为EAGAIN或EWOULDBLOCK
recv SO_RCVTIMEO 返回-1,设置errno为EAGAIN或EWOULDBLOCK
recvmsg SO_RCVTIMEO 返回-1,设置errno为EAGAIN或EWOULDBLOCK
accept SO_RCVTIMEO 返回-1,设置errno为EAGAIN或EWOULDBLOCK
connect SO_SNDTIMEO 返回-1,设置errno为EINPROGRESS

注意

  1. EAGAIN通常和EWOULDBLOCK是同一个值;

  2. SO_RCVTIMEO, SO_SNDTIMEO不要求系统调用对应fd是非阻塞(nonblocking)的,但是使用了该套接字选项的sock fd,会成为nonblocking(即使之前是blocking)的。参见man手册ERRORS EAGAIN/EWOULDBLOCK的描述;

man send关于EAGAIN / EWOULDBLOCK描述:

EAGAIN or EWOULDBLOCK The socket is marked nonblocking and the requested operation would block. POSIX.1-2001 allows either error to be returned for this case, and does not require these constants to have the same value, so a portable application should check for both possibilities.

示例1:设置connect超时时间

根据系统调用accept的返回值,以及errno判断超时时间是否已到,从而决定是否开始处理超时定时任务。

客户端程序:超时连接服务器

/*
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值