安全扫描一句话:OpenSSH 版本过低,高危漏洞,限期整改。

现实情况一句话:线上环境不能联网,系统源太老,不能乱升级。

这篇文章,专门解决一个问题:👉 自己做 OpenSSH 的 RPM 包,拷到线上直接 rpm -Uvh 安装。

一、为什么要自己做 OpenSSH RPM 包?

很多生产环境你一定见过:

  • 系统版本老(CentOS 7 / 国产系统)

  • yum 源里的 OpenSSH 版本低

  • 不能 yum update openssh*

  • 编译安装又怕污染系统、被安全部门质疑

📌 最稳妥的方式只有一个:制作标准 RPM 包,走 “正规升级流程”

优点很明显:

  • ✔ 可控、可回滚

  • ✔ 符合安全整改要求

  • ✔ 适合离线环境

  • ✔ 不破坏系统 rpm 管理体系

二、RPM 构建环境准备(只在一台机器上做)

⚠️ 构建机 ≠ 生产机

建议使用:

  • 与生产环境相同系统版本

  • 可联网(下载源码用)

1️⃣ 安装构建工具

plaintext

yum install -y rpm-build rpmdevtools gcc make openssl-devel pam-devel zlib-devel

2️⃣ 初始化 RPM 目录结构

plaintext

rpmdev-setuptree

生成目录:

plaintext

~/rpmbuild/
├── BUILD
├── RPMS
├── SOURCES
├── SPECS
└── SRPMS

三、准备 OpenSSH 源码

1️⃣ 下载官方源码

plaintext

cd ~/rpmbuild/SOURCES
wget https://cdn.openbsd.org/pub/OpenBSD/OpenSSH/portable/openssh-9.6p1.tar.gz

⚠️ 版本建议选:9.6p1 / 9.7p1(与 OpenSSL 1.1.x 兼容更好)

四、编写 OpenSSH Spec 文件(核心)

进入 spec 目录:

plaintext

cd ~/rpmbuild/SPECS
vim openssh.spec

📄 示例 spec

plaintext

Name:           openssh
Version:        9.6p1
Release:        1.ky10
Summary:        OpenSSH secure shell client and server
License:        BSD
URL:            https://www.openssh.com/
Source0:        openssh-9.6p1.tar.gz
%define debug_package %{nil}
BuildRequires:  gcc, make, openssl-devel, pam-devel, zlib-devel
Requires:       openssl, pam, zlib

%description
OpenSSH is a free version of the SSH connectivity tools that technical users
rely on to access remote machines securely.

# ================= client =================
%package client
Summary: OpenSSH client utilities
Requires: %{name} = %{version}-%{release}

%description client
OpenSSH client programs including ssh, scp, sftp and key management tools.

# ================= server =================
%package server
Summary: OpenSSH server daemon
Requires: %{name} = %{version}-%{release}

%description server
OpenSSH server daemon (sshd).

# ================= prep =================
%prep
%setup -q

# ================= build =================
%build
./configure \
    --prefix=/usr \
    --sysconfdir=/etc/ssh \
    --libexecdir=/usr/libexec \
    --with-pam \
    --with-ssl-engine \
    --with-md5-passwords
make %{?_smp_mflags}

# ================= install =================
%install
rm -rf %{buildroot}
make install DESTDIR=%{buildroot}

# ================= files =================
# -------- 主包 --------
%files
%doc README INSTALL

# -------- client 包(终极兜底) --------
%files client
/usr/bin/ssh
/usr/bin/scp
/usr/bin/sftp
/usr/bin/ssh-add
/usr/bin/ssh-agent
/usr/bin/ssh-keygen
/usr/bin/ssh-keyscan
/etc/ssh/ssh_config
/etc/ssh/moduli
/usr/libexec/ssh-pkcs11-helper
/usr/libexec/ssh-sk-helper
/usr/share/man/man1/ssh*
/usr/share/man/man1/scp*
/usr/share/man/man1/sftp*
/usr/share/man/man5/ssh_config.5*
/usr/share/man/man5/moduli.5*
/usr/share/man/man8/ssh-pkcs11-helper.8*

# -------- server 包 --------
%files server
/usr/sbin/sshd
/usr/libexec/sftp-server
/usr/libexec/ssh-keysign
/etc/ssh/sshd_config
/usr/share/man/man5/sshd_config.5*
/usr/share/man/man8/sshd.*
/usr/share/man/man8/sftp-server.*
/usr/share/man/man8/ssh-keysign.*
/usr/share/man/man8/ssh-sk-helper.*

五、开始构建 RPM 包

plaintext

rpmbuild -ba openssh.spec

执行过程示例:

plaintext

[root@k8s-master SPECS]# rpmbuild -ba openssh.spec
正在执行(%prep): /bin/sh -e /var/tmp/rpm-tmp.lqftt
+ umask 022
+ cd /root/rpmbuild/BUILD
cd /root/rpmbuild/BUILD
rm -rf openssh-9.6pl
/usr/bin/gzip -dc /root/rpmbuild/SOURCES/openssh-9.6p1.tar.gz
/usr/bin/tar -xof -
STATUS=0 *['-ne']
++ jobs -p
cd openssh-9.6p1
/usr/bin/chmod -Rf a+rX,u+w,g-w,o-w .
RPM EC=0
+ exit 0
正在执行(%build): /bin/sh -e /var/tmp/rpm-tmp.FganAV
+ umask 022
+ cd openssh-9.6p1
+ ./configure --prefix=/usr --sysconfdir=/etc/ssh --with-pam --with-ssl-engine --with-md5-passwords
configure: WARNING: unrecognized options: --with-md5-passwords
cd /root/rpmbuild/BUILD
checking for cc... cc
checking whether the C compiler works... yes
checking for C compiler default output file name... a.out
checking for suffix of executables...
checking whether we are cross compiling... no
checking for suffix of object files... o
checking whether the compiler supports GNU C... yes
checking whether cc accepts -g... yes
checking for cc option to enable cil features... none needed
checking if cc supports C99-style variadic macros... yes
checking build system type... x86_64-pc-linux-gnu
checking host system type... x86_64-pc-linux-gnu
checking for stdio.h... yes
checking for stdlib.h... yes
checking for string.h... yes
checking for inttypes.h... yes
checking for stdint.h... yes
checking for strings.h... yes
checking for sys/stat.h... yes
checking for sys/types.h... yes
checking for unistd.h... yes
checking whether byte ordering is bigendian... no
checking for gawk... gawk
checking how to run the C preprocessor... cc -E
checking for ranlib... ranlib
checking for a BSD-compatible install... /usr/bin/install -c
checking for grep that handles long lines and -e... /usr/bin/grep
checking for egrep... /usr/bin/grep -E
checking for a race-free mkdir -p... /usr/bin/mkdir -p
checking for ar... ar
checking for cat... /usr/bin/cat
checking for kill... /usr/bin/kill
checking for sed... /usr/bin/sed
checking for bash... /usr/bin/bash

成功后生成:

plaintext

~/rpmbuild/RPMS/x86_64/
├── openssh-9.6p1-1.x86_64.rpm

文件列表示例:

plaintext

[root@k8s-master RPMS]# cd x86_64/
[root@k8s-master x86_64]# ls
总用量 1292
-rw-r--r-- 1 root root  12080 12月 17 09:12 openssh-9.6p1-1.ky10.x86_64.rpm
-rw-r--r-- 1 root root 776932 12月 17 09:12 openssh-client-9.6p1-1.ky10.x86_64.rpm
-rw-r--r-- 1 root root 528920 12月 17 09:12 openssh-server-9.6p1-1.ky10.x86_64.rpm

🎉 这就是你可以带走的 “离线神器”

六、线上环境离线升级 OpenSSH

1️⃣ 上传 RPM 包

plaintext

scp *.rpm root@prod:/tmp/

2️⃣ 安装前强烈建议

plaintext

# 备份 sshd 配置
cp -a /etc/ssh /etc/ssh.bak

3️⃣ 升级安装

plaintext

rpm -Uvh *.rpm

4️⃣ 验证版本

plaintext

ssh -V

输出示例:

plaintext

OpenSSH_9.6p1, OpenSSL 1.1.1f 31 Mar 2020

安装过程示例:

plaintext

[root@k8s-worker2 x86_64]# rpm -Uvh *.rpm
Verifying...                          ################################# [100%]
准备中...                          ################################# [100%]
正在升级/安装...
1:openssh-9.6p1-1.ky10              ################################# [ 33%]
2:openssh-client-9.6p1-1.ky10       ################################# [ 67%]
3:openssh-server-9.6p1-1.ky10       ################################# [100%]
[root@k8s-worker2 x86_64]# ssh -V
OpenSSH_9.6p1, OpenSSL 1.1.1f 31 Mar 2020

七、生产环境必做的 3 个检查点

🔍 1️⃣ sshd 服务状态

plaintext

systemctl status sshd

🔍 2️⃣ 新开一个 SSH 会话测试

⚠️ 永远不要在当前连接里 “自信重启”

🔍 3️⃣ 安全扫描复测

大部分扫描器只认版本号,RPM 升级是最容易通过的方式

八、常见踩坑总结(血泪经验)

  • ❌ 不要直接 make install 到线上→ 无法回滚、审计不过

  • ❌ 不要跨系统版本做 RPM→ CentOS 7 和 国产系统不通用

  • ❌ 不要覆盖 openssl 系统库→ 80% SSH 起不来的原因在这

九、适合哪些场景?

  • ✔ 等保 / 安全测评整改

  • ✔ 金融 / 能源 / 政企内网

  • ✔ 不能联网的生产环境

  • ✔ 被迫升级 OpenSSH 的运维人

编译 OpenSSH 不难,难的是:“既要安全扫描过,又不能把生产搞挂”,RPM 才是线上环境真正认可的升级方式。

如何使用文章中提到的方法制作OpenSSH的RPM包?

制作OpenSSH的RPM包有哪些注意事项?

除了文章中提到的方法,还有哪些方式可以解决OpenSSH版本过低的问题?