背景说明

用了几年的 debian,近期在 Ubuntu 24.04 LTS 服务器上配置 SSH 端口时,发现修改 sshd_config 中的 Port 参数后,服务仍顽固监听默认的 22 端口。

排查发现,这一问题与 Canonical(Ubuntu 母公司)在最新版本中引入的 systemd socket activation 机制密切相关。根据 Canonical 官方在Ubuntu技术公告中披露的基准测试,自 **Ubuntu 22.10(Kinetic Kudu)**起,OpenSSH 服务默认启用基于 systemdSocket Activation 机制。该设计通过动态服务激活模式,使 SSH 守护进程(sshd)仅在接收到实际连接请求时启动,空闲时完全释放资源。

相较于传统常驻进程模式,可减少每个空闲 SSH 进程约 5% 的内存占用(约合 8-12MB)。这一机制的本质革新在于:SSH 的端口监听职责从sshd转移至systemd。形象地说,传统 SSH 服务如同 24 小时运行(常驻进程),而 socket activation 机制则像无人便利店(平时关闭),仅在顾客敲门(连接请求)时才启动服务。在此架构下,端口配置不再通过手动编辑 systemd 单元文件实现,而是由 sshd_config 动态生成并注入系统。

版本演进对比

版本 配置机制 内存消耗
Ubuntu 22.04 LTS 传统预加载模式 65MB
Ubuntu 24.04 LTS 动态socket激活 + 配置自动生成 58MB⬇️

▶ 场景复现:修改SSH端口失败

1
2
3
4
5
6
7
8
9
10
# 修改配置文件
sudo nano /etc/ssh/sshd_config
→ 添加 Port 36000

# 传统重启方式
sudo systemctl restart sshd

# 验证监听端口(仍显示22)
sudo ss -tulnp | grep sshd

▶ 解决方案

方法一:动态适配新机制(推荐)

💡原理说明:
当启用socket激活时,端口配置实际由/etc/systemd/system/ssh.socket.d/addresses.conf控制,传统配置文件仅在连接建立后读取。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
# 完整的正确操作流程:
# 1. 修改SSH配置文件
sudo nano /etc/ssh/sshd_config
→ 添加 Port 36000

# 2. 触发动态配置生成(关键步骤!)
sudo sshd -t # 语法检查
sudo systemctl restart ssh.service # 生成新的socket配置

# 3. 验证socket配置
sudo systemctl cat ssh.socket
→ 应显示动态生成的端口:
[Socket]
ListenStream=36000
Accept=yes

# 4. 重启socket服务
sudo systemctl restart ssh.socket

# 5. 验证端口监听
sudo ss -ltnp | grep 36000
→ 输出应包含「systemd」「ssh.socket」

方法二:回归传统模式(兼容旧环境)

1
2
3
4
5
6
7
8
9
10
11
12
13
# 修正后的完整命令:
sudo systemctl disable --now ssh.socket

# 删除自动生成的配置(新路径!)
sudo rm -f /usr/lib/systemd/system/ssh.service.d/00-socket.conf
sudo rm -f /usr/lib/systemd/system/ssh.socket.d/addresses.conf

# 彻底清除配置缓存
sudo systemctl daemon-reload
sudo systemctl reset-failed ssh.service

# 启用传统模式
sudo systemctl enable --now ssh.service

技术原理剖析

24.04 LTS配置加载流程:

graph TD
    A[客户端连接36000端口] --> B{端口是否注册}
    B -->|是| C[激活ssh.service]
    B -->|否| D[拒绝连接]
    C --> E[读取sshd_config]
    E --> F[建立SSH会话]

新旧机制对比表:

阶段 Socket激活模式 传统模式
服务启动时机 首次连接触发 系统启动时加载
端口声明位置 systemd socket单元 sshd_config
配置更新生效方式 systemctl edit ssh.socket 修改sshd_config
内存占用(空闲状态) 0MB ~8MB

总结建议

  1. 优先使用动态适配方案
    通过 systemctl restart ssh.service 触发配置更新是最安全的做法,兼容未来版本更新。
  2. 传统模式仅作备用
    若必须禁用socket激活,需特别注意配置路径变化,避免残留配置导致冲突。

参考:

https://discourse.ubuntu.com/t/sshd-now-uses-socket-based-activation-ubuntu-22-10-and-later/30189

https://bugs.launchpad.net/ubuntu/+source/openssh/+bug/2069041