- 英文小册原文地址:beej.us/guide/bgnet…
- 作者:Beej
- 中文翻译地址:www.chanmufeng.com/posts/netwo…
停止对socket继续传送与接受。
函数原型
#include <sys/socket.h>
int shutdown(int s, int how);
说明
如果我不需要再对 socket 进行
send()
了,但是我仍然想要
recv()
socket 的数据,反之亦然,那我该怎么做呢?
当你使用
close()
关闭 socket descriptor 时,它会将 socket 的传送与接收两端都关闭,并且释放 socket descriptor。若你只想要关闭其中一端,你就可以使用
shutdown()
这个函数。
在这些参数中,
s
显然是你想要进行动作的 socket,而要进行什么样的动作,则要由
how
参数指定。可以使用
SHUT_RD
来关闭接收,
SHUT_WR
以关闭传送,或者
SHUT_RDWR
将收送功能都关闭。
-
SHUT_RD
关闭连接的读功能,socket中不再有数据可以被接受,而且socket接收缓冲区中的先有数据都被丢弃。进程不能再对这样的socket调用任何读函数。
-
SHUT_WR
关闭连接的写功能。当前留在socket发送缓冲区中的数据将被发送掉,后面跟着TCP的正常连接终止序列。进程不能再对这样的socket调用任何写函数。
-
SHUT_RDWR
连接的读功能和写功能都被关闭,这等于调用
两次:第一次调用指定shutdown
,第二次调用指定SHUT_RD
。SHUT_WR
shutdown()
用来关闭连接,而不是socket,不管调用多少次
shutdown()
,socket依然存在,因为
shutdown()
并没有释放 socket descriptor,所以即使 socket 已经整个 shutdown 了,最终仍然得透过
close()
关闭 socket。
默认情况下,
close()
会立即向网络中发送
FIN
包,不管输出缓冲区中是否还有数据,而
shutdown()
会等输出缓冲区中的数据传输完毕再发送
FIN
包。也就意味着,调用
close()
将丢失输出缓冲区中的数据,而调用
shutdown()
不会。
返回值
例子
int s = socket(PF_INET, SOCK_STREAM, 0);
// ...do some send()s and stuff in here...
// and now that we're done, don't allow any more sends()s:
shutdown(s, SHUT_WR);