setsockopt()详解

一、setsockopt() 是什么?

是:

设置 socket 选项(Socket Options)

作用:

让你修改内核中这个 socket 的行为。

函数原型:

cpp 复制代码
int setsockopt(
    int sockfd,
    int level,
    int optname,
    const void *optval,
    socklen_t optlen
);

二、下面这段代码在干什么?(在实际工程里几乎都会出现)

cpp 复制代码
int opt = 1;
setsockopt(listen_fd, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt));

意思是:

允许端口地址复用

简单说:

让服务器可以立即重新绑定同一个端口

三、不写会发生什么?
场景:

服务器运行在 8080

Ctrl+C 关闭

马上重新运行

可能出现错误:

复制代码
bind: Address already in use

为什么?

因为 TCP 有一个状态:

复制代码
TIME_WAIT

即使程序退出,端口还被内核保留一段时间(通常1~4分钟)。

四、SO_REUSEADDR 的作用
设置后:
允许立即重新使用端口

开发服务器时非常重要,否则你会一直遇到:

复制代码
bind失败

五、setsockopt 参数逐个解释(重点)
1. sockfd

cpp 复制代码
listen_fd

要设置选项的 socket。

2. level

cpp 复制代码
SOL_SOCKET

表示:

在 socket 层设置选项

还有其他层,例如:

cpp 复制代码
IPPROTO_TCP
IPPROTO_IP

但最常用的是

cpp 复制代码
SOL_SOCKET

3. optname

cpp 复制代码
SO_REUSEADDR

选项名称。

常见选项:

4. optval

cpp 复制代码
&opt

选项值的地址。

这里:

复制代码
opt = 1  → 开启
opt = 0  → 关闭

5. optlen

cpp 复制代码
sizeof(opt)

值的大小(字节数)

六、系统底层为什么需要这个?

TCP关闭流程:

复制代码
主动关闭的一方进入 TIME_WAIT

目的是:

确保最后一个ACK能到达

防止旧数据影响新连接

但开发服务器时:

我们知道自己要重新启动服务

所以可以安全复用端口。

七、服务器中标准写法

工程中几乎固定写法:

cpp 复制代码
int listen_fd = socket(AF_INET, SOCK_STREAM, 0);

int opt = 1;
setsockopt(listen_fd, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt));

bind(listen_fd, ...);
listen(listen_fd, 5);

顺序注意:

必须在 bind 之前调用

相关推荐
王老师青少年编程8 小时前
csp信奥赛C++高频考点专项训练之字符串 --【子串查找】:[NOIP 2009 提高组] 潜伏者
c++·字符串·csp·高频考点·信奥赛·子串查找·潜伏者
初願致夕霞8 小时前
基于系统调用的Linux网络编程——UDP与TCP
linux·网络·c++·tcp/ip·udp
小小de风呀10 小时前
de风——【从零开始学C++】(五):内存管理
开发语言·c++
CHANG_THE_WORLD11 小时前
C语言中的 %*s 和 %.*s 和C++的字符串格式化输出
c语言·c++·c#
螺丝钉的扭矩一瞬间产生高能蛋白12 小时前
QT的C++接口基础用法
c++·qt·嵌入式软件·嵌入式linux·linux应用
智者知已应修善业12 小时前
【51单片机模拟生日蜡烛】2023-10-10
c++·经验分享·笔记·算法·51单片机
智者知已应修善业12 小时前
【51单片机如何让LED灯从一亮到八,再从八亮到一】2023-10-13
c++·经验分享·笔记·算法·51单片机
qeen8713 小时前
【数据结构】二叉树相关经典函数C语言实现
c语言·数据结构·c++·笔记·学习·算法·二叉树
良木生香13 小时前
【C++初阶】STL——List从入门到应用完全指南(1)
开发语言·数据结构·c++·程序人生·算法·蓝桥杯·学习方法