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 之前调用

相关推荐
自信150413057593 小时前
重生之从0开始学习c++之模板初级
c++·学习
历程里程碑3 小时前
2. Git版本回退全攻略:轻松掌握代码时光机
大数据·c++·git·elasticsearch·搜索引擎·github·全文检索
极客智造4 小时前
深度解析 C++ 类继承与多态:面向对象编程的核心
c++
Lucis__4 小时前
一文读懂TCP通信机制:基于相关API构建可靠性连接
linux·网络·tcp/ip
PinTrust SSL证书5 小时前
IP地址访问网站,怎么去除不安全提示?
网络协议·tcp/ip·安全·网络安全·https·ssl
零号全栈寒江独钓6 小时前
基于c/c++实现linux/windows跨平台获取ntp网络时间戳
linux·c语言·c++·windows
CSCN新手听安6 小时前
【linux】高级IO,以ET模式运行的epoll版本的TCP服务器实现reactor反应堆
linux·运维·服务器·c++·高级io·epoll·reactor反应堆
松☆8 小时前
C++ 算法竞赛题解:P13569 [CCPC 2024 重庆站] osu!mania —— 浮点数精度陷阱与 `eps` 的深度解析
开发语言·c++·算法
(Charon)8 小时前
【C++/Qt】C++/Qt 实现 TCP Server:支持启动监听、消息收发、日志保存
c++·qt·tcp/ip
并不喜欢吃鱼9 小时前
从零开始C++----七.继承及相关模型和底层(上篇)
开发语言·c++