首先附上TCP三次握手和四次挥手过程图,结合理解
SO_REUSEADDR,使用这个选项可以让端口释放后立即使用,主要针对上图time_wait阶段,在bind前设置这个套接字选项。
允许启动一个监听服务器并捆绑其众所周知的端口,并且以前建
立的将此端口用做它们的本地端口的连接仍存在。 这通常是重启监昕服务器时会出现的情况,若不设置此选项,则bind时将出错。
允许在同一端口上启动同一服务器的多个实例,只要每个实例捆
绑一个不同的本地IP地址即可
允许单个进程捆绑同一端口到多个套接口上,只要每个进程捆绑
的指定不同的本地IP地址即可。
当一个IP地址和端口绑定到某个套接口上时,还允许此IP地址和端口捆绑到另一个套接口上。一般来说,这个特性仅在支持多播的系统上才有,而且只对UDP套接口而言
如果服务程序停止后想立即重启,而新套接字依旧使用同一端口,此时使用REUSEADDR选项非常有用。 但必须意识到,此时任何非期望数据到达,都可能导致服务程序反应?昆乱,不过这只是一种可能,事实上可能性较小。
TCP NODELAY/TCP CHORK
TCP_NODELAY和TCP一CORK基本上控制了包的“Nagle化”, Nagle化在这里的含义是采用Nagle算法把较小的包组装为更大的帧。
TCP _NODELAY不使用Nagle算法,不会将小包进行拼接成大包再进行发送,而是直接将小包发送出去,这会使得用户体验要好。
当在传送大量数据的时候,为了提高TCP发送效率,可以设置TCPCORK, CORK就是“塞子”的意思,它会尽量在每次发送最大的数据量。 当设置了TCP_CORK后, 会有200ms阻塞,当阻塞时间过后,数据就会自动传送。
SO LINGER
struct linger{
int l_onoff; /O=off, no口zero=on/
int l_linger; /l工口ger time, POSIX specif工es units as seconds/
}
优雅的关闭。
close默认操作:立即返回。
此种情况,close立即返回,如果sendbuffer中还有数据,close将会等到所有数据被发送完之后返回。 由于并没有等待对方TCP.发送的ACK信息,所以只能保证数据已经发送到对方,所以并不知道对方是否已经接受了数据。 由于此种情况,TCP连接终止是按照正常的4次挥手方式,需要经过TIME_WAIT
l_onoff非0,并且使之!_linger为一个整数。
在这种情况下,close会在接收到对方TCP的ACK信息之后才返回(!_linger消耗完之前)。 但是这种ACK信息只能保证对方已经接收到数据,并不保证对方应用程序已经读取。
注意此处的return时机!
l_linger设置值太小。
这种情况,由于l linger值太小,在sendbuffer·中的数据都发送完之前,close就返回,此种情况终止TCP连接,与l_linger=0类似,TCP连接终止不是按照正常的4步握手,所以, TCP连接不会进入TIMEWAIT状态,那么,client会向server发送一个RST信息
shutdown可以确保服务器端应用程序已经读取数据了,而不仅仅是服务器端已经接收到数据而己,
SHUT_RD指调用shutdown的一端receivebuffer将被丢弃掉,无法接收数据,但是可以发送数据,sendbuffer的数据可以被发送出去;
SHUT_WR指调用shutdown的一端无法发送数据,但是可以接收数据。 该参数表示不能调用send.但是如果还有数据在sendbuffer中,这些数据还是会被继续发送出去的。
TCP DEFER ACCEPT
防御空连接攻击
val = 5;
setsockopt(srv_socket->fd, SOL_TCP, TCP_DEFER ACCEPT, &val, si
zeof(val)) ;
SO KEEPALIVE
保持连接检测对方主机是否崩溃,避免(服务器)永远阻塞于TCP
连接的输入。
SOSNDTIMEO幸口SORCVTIMEO
当timeval结构为0时, 表示选项无效。 接收超时会影
响read、 readv、 recv、 recvfrom和recvmsg的状态;发送超时会影响write、 writev、 send、send to和sendmsg的状态。
(setsockopt(connfd, SOL_SOCKET, SO_SNDTIMEO , &stTimeValStruct, sizeof(stTimeValStruct))
SO RCVBUF和SOSNDBUF
每个TCP套接字都有一个发送缓冲区和一个接收缓冲区,每个UDP套接字都有一个接收缓冲区。 使用SORCVBUF和SOSNDB旧这两个套接口选项可以改变默认缓冲区大小。
getsockopt( acceptfd, SOL_SOCKET, SO_RCVBUF, (void *)&rcvbuf_len, &len )