资讯动态

银河麒麟V10 SSH安装配置与故障排查实战

发布时间:2026/10/1 11:10:14 来源:尧图企业网站定制
1. 银河麒麟 V10 上的一套 SSH 究竟由哪些东西组成很多人第一次接触银河麒麟 V10 的远程运维脑子里只有一句要用 SSH 连上去但真到机器上敲命令的时候才发现SSH 其实不是一个软件而是一组工具的集合。搞清楚这套集合里每个角色负责什么后面装 OpenSSH、改配置、排故障才不会瞎猜。银河麒麟 V10 是 RPM 系的操作系统包管理走yum/dnf和常见的国产服务器发行版思路一致。SSH 这套东西在麒麟上是以openssh、openssh-server、openssh-clients这几个包的形式存在的openssh提供公共库和密钥工具openssh-server提供服务端守护进程openssh-clients提供你日常敲的ssh、scp、sftp。这三个包拆开是有道理的一台只做客户端跳板的机器根本不需要装服务端装了反而多一个监听端口多一份被扫描面。1.1 sshd、ssh、ssh-keygen、scp 各自管什么先把这几个最容易混淆的命令摆清楚。sshd是服务端的守护进程全称 OpenSSH Daemon它默认监听 22 端口负责接受连接、完成认证、分配 PTY、拉起用户 shell。你在系统里用systemctl status sshd看到的就是它。真正做认证决策、读/etc/ssh/sshd_config的是它不是ssh命令。ssh是客户端你敲ssh userhost时执行的就是它。它读的是另一个配置文件/etc/ssh/ssh_config或者用户目录下的~/.ssh/config和服务端那份sshd_config名字只差一个字母但内容完全不通用这是新手最容易搞混的地方——改错了文件怎么改都不生效。ssh-keygen是密钥生成工具服务端可以用ssh-keygen -A批量补齐主机密钥客户端可以用它生成自己的用户密钥对。scp和sftp都建立在ssh的通道之上本质是复用了 SSH 的加密会话所以它们能和ssh共用同一套端口和认证配置。把这些关系理顺后面遇到能连上但传不了文件这类问题你就知道该往哪个方向查。1.2 出厂状态下 SSH 是装好的还是需要自己装这个问题没有统一答案取决于你手上的是哪个版本和哪种形态。服务器版本的银河麒麟 V10 通常预装了openssh-server并且sshd是开机自启的上电插网线就能连桌面版本或者最小化安装的镜像有可能只带了openssh-clients甚至两个都没有。所以接手一台新机器第一件事不是急着改配置而是先探明家底。rpm -qa | grep -i openssh rpm -q openssh openssh-server openssh-clients systemctl status sshd ss -lntp | grep -E :22|sshd这四条命令跑下来情况就清楚了第一条看装了哪些包第二条看具体版本号第三条看服务有没有在跑第四条看端口有没有真的监听。我见过不少人只看systemctl status显示 active 就以为万事大吉结果发现监听的是 IPv6 而客户端走的是 IPv4或者配置里ListenAddress只绑了回环地址127.0.0.1外网怎么都连不上。多敲一条ss花不了几秒钟能省掉半小时的排查。这里顺带提一句版本差异。银河麒麟 V10 的不同 SP 版本预装的 OpenSSH 版本跨度比较大有 7.x 的也有 8.x 的。版本直接决定了你支持的密钥算法和加密套件比如 7.x 里ssh-rsa还能正常用于用户认证而较新的版本默认已经禁用了基于 SHA-1 的签名。做安全加固或者对接新旧客户端时先ssh -V看一眼版本比什么都实在。1.3 配置文件与密钥文件的分布地图在麒麟 V10 上和 SSH 相关的文件基本集中在两个目录/etc/ssh/和用户的~/.ssh/。服务端的东西全在/etc/ssh/下包括主配置sshd_config、客户端配置ssh_config、主机密钥ssh_host_rsa_key、ssh_host_ecdsa_key、ssh_host_ed25519_key以及各自对应的.pub公钥。这些主机密钥在首次安装或首次启动时生成是服务端身份的凭证客户端第一次连接时弹出来的指纹提示比对的就是这些东西。用户侧的东西在~/.ssh/下id_rsa或id_ed25519是私钥.pub是对应公钥authorized_keys存放允许登录本机的公钥列表known_hosts记录你连过的服务端指纹config是你自己写的客户端别名配置。这几个文件的权限要求非常严格~/.ssh必须是700authorized_keys和私钥必须是600家目录本身不能是777。这条规则很多人栽过跟头——复制粘贴文件的时候顺手chmod 777结果密钥登录直接失效日志里写着Authentication refused: bad ownership or modes看着莫名其妙其实就是权限太宽松。文件路径作用建议权限/etc/ssh/sshd_config服务端主配置600属主 root/etc/ssh/ssh_config全局客户端配置644/etc/ssh/ssh_host_*_key服务端主机私钥600属主 root~/.ssh/id_ed25519用户私钥600~/.ssh/authorized_keys允许登录的公钥列表600~/.ssh/config客户端别名配置600~/.ssh/known_hosts已信任的主机指纹644顺手记一句修改sshd_config之前一定先备份成sshd_config.bak.日期。这不是形式主义是因为sshd一旦因为配置语法错误起不来你手上如果没有控制台或带外管理就只能干瞪眼了。2. OpenSSH 的三种安装路径源安装、离线 rpm、源码编译在银河麒麟 V10 上装 OpenSSH实际操作中会遇到三种场景机器能连内网源、机器完全离线、以及需要升级到比源里更新的版本。这三种场景对应三条不同的路径选错了要么白费力气要么把系统搞出依赖问题。下面按先探底、再动手的顺序把三条路都走一遍。2.1 先摸清版本和依赖再决定走哪条路动手之前先做一次依赖体检。OpenSSH 服务端不是孤立的它依赖openssl-libs、krb5-libs、libedit、pam、zlib等一堆东西。在线安装时包管理器会自动解决这些依赖离线安装时就得你自己把这些包凑齐少一个都装不上。yum deplist openssh-server rpm -qpR openssh-server-*.rpm ldd /usr/sbin/sshd前两条分别是在线和离线场景下看依赖的方式第三条是直接看现有sshd二进制加载了哪些动态库。第三条特别有用——如果你打算升级 OpenSSH新编译出来的sshd必须能链接到系统现有的libcrypto.so、libssl.so否则起来就报error while loading shared libraries。麒麟 V10 自带的 OpenSSL 版本有些是 1.1.1 系列做源码编译时要确认--with-ssl-dir指向的路径下有对应的头文件和库。判断走哪条路的标准很简单能连内网源就用源装图省事且版本够用不能连源就用离线 rpm注意凑依赖源里版本太老、有明确的安全合规要求或者需要特定算法支持才考虑源码编译。源码编译是最后手段因为它绕过了包管理器的版本记录后续升级和回滚都得靠人工维护。2.2 在线源安装dnf/yum 的常规操作与版本锁定银河麒麟 V10 的软件源配置在/etc/yum.repos.d/下文件名通常是kylin-*.repo。装之前先确认源是通的yum repolist yum info openssh openssh-server openssh-clients如果yum info能列出包信息说明源可用接着装就行yum install -y openssh-server openssh-clients systemctl enable --now sshd systemctl status sshdenable --now这个组合值得说一下它等价于systemctl enable sshd加systemctl start sshd一次性把开机自启和立即启动都做了。如果只敲了start机器重启后服务不会自己起来第二天上班发现连不上白折腾一趟。装完之后一定要做版本记录把当前版本号存一份rpm -q openssh openssh-server openssh-clients这个记录有两个用处。一是以后升级出问题时知道原来是什么版本方便回退二是多台机器做一致性管理时可以快速比对各台机器的版本是否统一。运维里最怕的不是版本老而是同一批机器版本参差不齐出问题时现象不一致排查成本翻倍。还有一点如果你明确不想让yum update顺手把 OpenSSH 升上去升级可能带来配置兼容问题可以用版本锁定yum install -y yum-plugin-versionlock yum versionlock openssh openssh-server openssh-clients锁定之后常规更新不会碰这几个包需要升级时再手动解锁。这个做法在需要长期稳定运行的业务机上很常见我个人比较推荐。2.3 离线 rpm 安装下载完整依赖链与本地源做法离线场景是国产化环境里绕不开的一环。机器的网络受限只能靠 U 盘或内部文件服务器转包。这时最稳的做法不是一个个rpm -ivh手动试而是找一台同版本的联网机器把包和依赖一次性下载下来。# 在联网的同版本机器上执行 mkdir -p /tmp/openssh-offline yum install -y --downloadonly --downloaddir/tmp/openssh-offline \ openssh openssh-server openssh-clients--downloadonly加--downloaddir的组合会把包和它依赖的所有包统统下载到指定目录不实际安装。下载完把整个目录拷到目标机器然后# 在离线机器上执行 cd /tmp/openssh-offline yum localinstall -y ./*.rpm用yum localinstall而不是rpm -ivh关键差别在于前者会读取本地目录里的依赖关系自动按正确顺序装后者遇到依赖顺序不对就报错中断。如果包特别多、以后还要反复用可以干脆把目录做成一个本地源yum install -y createrepo createrepo /tmp/openssh-offline cat /etc/yum.repos.d/local-openssh.repo EOF [local-openssh] nameLocal OpenSSH Repo baseurlfile:///tmp/openssh-offline enabled1 gpgcheck0 EOF yum clean all yum makecache yum install -y openssh-server这条路我在内网环境里走过很多次一次做好后面几台机器都能直接用。注意不要轻易使用rpm -Uvh --nodeps --force这类参数跳过依赖检查。短期内看似装上了实际上依赖的库版本不匹配sshd可能起不来或者起来了但认证阶段崩溃排查起来比老老实实解决依赖麻烦得多。2.4 源码编译安装什么时候值得这么干源码编译通常出现在两种诉求下一是源里的 OpenSSH 版本太旧某些安全扫描工具会判定不合格二是需要引入新版才支持的算法或特性。这时候的步骤大致如下但每一步都要留后手。yum install -y gcc make zlib-devel openssl-devel pam-devel krb5-devel libedit-devel tar -xzf openssh-*.tar.gz cd openssh-* ./configure --prefix/usr \ --sysconfdir/etc/ssh \ --with-pam \ --with-zlib \ --with-ssl-dir/usr \ --with-md5-passwords \ --with-privsep-path/var/empty/sshd make -j$(nproc)configure里的几个参数值得解释。--sysconfdir/etc/ssh是为了让新装的配置目录和系统原有位置一致方便后续维护--with-pam打开 PAM 支持否则系统用户认证会出问题--with-privsep-path指定权限分离目录这是 OpenSSH 的一项重要安全设计让监听端口的进程以非特权身份运行即使被攻破也拿不到 root。这些参数不是随便挑的每一项都对应着能不能正常登录、安全边界够不够。编译通过之后先别急着make install。此时建议把原来的二进制备份好再执行安装cp -a /usr/sbin/sshd /usr/sbin/sshd.bak.$(date %F) make install /usr/sbin/sshd -t最后那条sshd -t是语法检查返回空就说明配置没问题。这一步千万不能省因为它能在不影响线上服务的情况下提前发现配置错误等真重启失败了再回头查就晚了。3. sshd_config 里真正需要动的那几行/etc/ssh/sshd_config有上百行配置但百分之九十的场景里你真正需要改的就是那么十几行。把注意力集中在这些关键项上比通读整份文件效率高得多。3.1 端口、监听地址与登录方式的基本取舍默认端口是 22。改端口的动机通常是减少自动化扫描带来的日志噪音但客观来说改端口对真正的定向攻击没有实质防护作用安全还是要靠密钥认证、访问控制和及时打补丁。如果确实要改Port 22 Port 22222 ListenAddress 0.0.0.0同时保留 22 和 22222 是个稳妥做法先用新端口验证能连上确认无误后再把 22 注释掉避免改完直接失联。ListenAddress决定绑定哪些网卡地址只填127.0.0.1的话外部连接一律拒绝这在只允许本地跳转的场景里有用但如果你是从另一台机器来连就会一直报拒绝连接。3.2 认证策略密码、密钥、Root 登录的组合认证相关的几行是最关键的也是最容易配出安全漏洞的地方配置项可选值说明PasswordAuthenticationyes/no是否允许密码登录PubkeyAuthenticationyes/no是否允许密钥登录PermitRootLoginyes/no/prohibit-password是否允许 root 直接登录PermitEmptyPasswordsyes/no是否允许空密码必须为 noMaxAuthTries数字单次连接最大认证尝试次数LoginGraceTime秒认证超时时间实践中的推荐组合是PasswordAuthentication no、PubkeyAuthentication yes、PermitRootLogin prohibit-password。这样普通用户走密钥登录root 只能通过已授权的密钥登录密码爆破这条路直接堵死。如果因为某种原因必须保留密码登录至少把MaxAuthTries降到 3 到 5把LoginGraceTime设为 30 到 60 秒压缩攻击面。注意改PasswordAuthentication no之前务必先确认你已经配好了至少一个账号的密钥登录并且是在另一个没有关掉的会话里验证过能登录成功。这个操作一旦出错而又没有控制台就等于把自己关在门外了。3.3 访问控制与连接稳定性参数访问控制主要靠AllowUsers、DenyUsers、AllowGroups、DenyGroups这几项。写AllowUsers ops01 ops0210.0.0.*这种形式可以同时限定用户和来源网段粒度比单纯的用户白名单细一档。这类限制比防火墙规则更贴近 SSH 语义防火墙只管端口管不了谁能登进来。连接稳定性方面最值得调的是这两行ClientAliveInterval 60 ClientAliveCountMax 3意思是服务端每隔 60 秒向客户端发一次探测连续 3 次无响应就断开。默认情况下这两个值都是 0也就是不探测一条空闲连接可能挂几个小时都不掉。对于通过堡垒机或者负载均衡转发的场景中间设备往往会清理长时间空闲的 TCP 连接导致会话卡死、敲键盘没反应配上一对合适的保活参数能明显改善体验。另外两行建议默认就加上能加快登录速度UseDNS no GSSAPIAuthentication noUseDNS yes会让服务端在客户端连进来时反查 IP 对应的域名如果内网 DNS 配置不完善每次登录都要等几秒钟超时。这个问题表现为登录特别慢但最终还是能登进去很容易被误判成网络问题。3.4 改完之后怎么验证、怎么回滚改配置的流程我建议固定成一套动作养成习惯就不会出事cp /etc/ssh/sshd_config /etc/ssh/sshd_config.bak.$(date %F-%H%M) vi /etc/ssh/sshd_config /usr/sbin/sshd -t systemctl reload sshdsshd -t报错就说明语法有问题这时不要 reload直接查错并修正。reload相比restart的好处是不断开已建立的连接即使新配置有问题你已经连着的会话还在可以从容回滚。回滚就是把备份文件覆盖回去再 reload 一次。想确认某项配置实际生效的值可以用sshd -T/usr/sbin/sshd -T | grep -E permitrootlogin|passwordauthentication|port这条命令打印的是服务端解析后的最终配置包含了默认值。比逐行去看配置文件可靠得多尤其是在配置项被多个位置重复定义的时候——在 SSH 配置里同一项如果出现多次通常是第一个生效而不是最后一个这一点和很多人的直觉相反也是改了没用的常见原因。4. 防火墙、安全策略与麒麟系统的联动检查配置改对了、服务也起来了还是连不上八成卡在系统的外围策略上。银河麒麟 V10 涉及的几个层面需要逐一确认。4.1 firewalld 与 iptables 的放行方式麒麟 V10 服务器版默认用的多是firewalld也有一些场景是直接管理iptables规则。先判断哪一个在起作用systemctl status firewalld firewall-cmd --state iptables -L -n --line-numbers如果firewalld在跑放行方式是这样的firewall-cmd --permanent --add-servicessh firewall-cmd --reload firewall-cmd --list-all改成非 22 端口的话--add-servicessh就不够用了需要显式放行端口firewall-cmd --permanent --add-port22222/tcp firewall-cmd --reload用iptables直接管理的话规则要写成插入到链首的位置否则可能被前面的拒绝规则拦截iptables -I INPUT -p tcp --dport 22222 -j ACCEPT service iptables save麒麟上有service iptables save也有iptables-save /etc/sysconfig/iptables两种存盘方式具体看你的系统里装的是哪一套组件。存盘这个动作必须做否则重启后规则全没了会给人昨天还能连今天怎么不行了的错觉。4.2 SELinux 与端口变更的联动如果系统开着 SELinux把 SSH 端口从 22 改成别的端口光改sshd_config和防火墙是不够的因为 SELinux 的端口标记里 22 属于ssh_port_t新端口不在这个类型里sshd绑定会失败。getenforce semanage port -l | grep ssh semanage port -a -t ssh_port_t -p tcp 22222getenforce返回Enforcing才需要这一步返回Disabled或Permissive就不用管。semanage命令如果提示找不到需要先装policycoreutils-python-utils这个包。我个人不建议为了图省事直接setenforce 0关掉 SELinux那等于把一层安全防护整体拆掉正确做法是加规则。4.3 系统加固策略覆盖配置的排查有一类问题特别隐蔽配置改完、reload 成功、当时也能连过了一段时间或者重启之后又变回去了。原因往往是系统里跑了某种加固或巡检脚本它会按照基线要求重写sshd_config里的某些项。麒麟的某些版本会带安全加固相关的工具集企业环境里也可能有统一的配置管理平台在定时推送。判断方法很直接看文件的修改时间stat /etc/ssh/sshd_config ls -l --full-time /etc/ssh/sshd_config rpm -V openssh-server如果修改时间和你上次编辑的时间对不上那就是被外部改过了。rpm -V会列出被修改过的文件正常的配置文件修改也会被列出来这个需要结合判断。确认是加固脚本干的之后要么调整脚本里的基线项要么把 SSH 配置纳入配置管理让两边保持一致别互相覆盖。5. 客户端实操免密登录、批量运维与长命令执行服务端搞定之后日常干活都在客户端侧。这一块有几个反复被问到的问题集中写一下。5.1 生成密钥对与 authorized_keys 的权限陷阱现在生成密钥优先选 Ed25519短、快、安全性好ssh-keygen -t ed25519 -C ops01kylin -f ~/.ssh/id_ed25519如果对接的老系统不支持 Ed25519那就退回 RSA 4096 位ssh-keygen -t rsa -b 4096 -C ops01kylin -f ~/.ssh/id_rsa公钥推送到目标机器最简单的是ssh-copy-idssh-copy-id -i ~/.ssh/id_ed25519.pub ops0110.0.0.21如果目标机器改了端口加上-p参数。如果ssh-copy-id用不了有些精简环境没装就手动来cat ~/.ssh/id_ed25519.pub | ssh ops0110.0.0.21 \ mkdir -p ~/.ssh chmod 700 ~/.ssh cat ~/.ssh/authorized_keys chmod 600 ~/.ssh/authorized_keys注意这条命令里的权限设置是必须的。我见过的最典型的翻车场景是把公钥追加到authorized_keys之后文件权限是默认的644密钥登录时好时坏日志里却没有明显报错。原因在于sshd对权限的要求是不能比要求更宽松644意味着同组和其他用户可读StrictModes默认开启时会拒绝使用这个文件。改成600立刻恢复。还有个小坑是家目录权限。如果/home/ops01是777同样会被StrictModes判为不安全。chmod 755或者700都可以就是不能给其他用户写权限。5.2 用 ~/.ssh/config 管理多台机器机器一多每次敲长长的ssh userip -p port -i keyfile就很烦。~/.ssh/config能把这些参数固化下来Host kylin-web HostName 10.0.0.21 User ops01 Port 22222 IdentityFile ~/.ssh/id_ed25519 ServerAliveInterval 60 ServerAliveCountMax 3 Host kylin-db HostName 10.0.0.31 User dba Port 22 ProxyJump kylin-web配好之后直接ssh kylin-web就行。ProxyJump这一项特别实用它表示先连到kylin-web再从那里跳到kylin-db等价于手工的两级跳转但写起来干净得多也不用在中间机器上留私钥。ServerAliveInterval放在客户端侧是给客户端发心跳和服务端的ClientAliveInterval是一对两边都配上长连接更稳。文件权限记得设成600否则某些版本的ssh会直接拒绝读这个文件。5.3 scp、sftp 与端口转发的日常用法文件传输基本就是scp和rsync两个。scp简单直接scp -P 22222 ./app.tar.gz ops0110.0.0.21:/opt/deploy/ scp -r -P 22222 ops0110.0.0.21:/var/log/app/ ./logs/注意scp的端口参数是大写-P而ssh是小写-p这个不一致坑过不少人。大量小文件或者需要断点续传、增量同步的场景用rsync更合适rsync -avz -e ssh -p 22222 ./release/ ops0110.0.0.21:/opt/app/release/-e参数用来指定走哪个远程 shell顺便把端口带进去。rsync默认只传变化部分重复同步的速度优势非常明显。端口转发在跨网段访问内部服务时很常用。比如数据库只允许本机访问你想从跳板机上连ssh -L 15432:127.0.0.1:5432 ops0110.0.0.31 -N这条命令在本机开一个15432端口所有流量通过 SSH 隧道转到10.0.0.31上看它自己的5432。-N表示不执行远程命令只做转发。用完CtrlC关掉即可。反向的-R和动态的-D也在同类场景里有用核心思路都是借 SSH 的加密通道承载其他协议。5.4 命令执行中途断开连接会发生什么这个问题问的人特别多ssh会话断了之前跑的命令还会不会继续默认答案是不会。当 SSH 会话终止时sshd会向该会话对应的进程组发送 SIGHUP前台运行的命令随之被终止。除非命令自己有特殊的信号处理逻辑否则进程就没了。想让命令在断线后继续跑有这么几种做法。最规范的是用nohup加后台运行nohup ./long_task.sh /tmp/long_task.log 21 nohup让进程忽略 SIGHUP让它进后台重定向把输出写进文件。这条命令执行完即使立刻断线任务也会继续ps -ef | grep long_task还能看到它。再稳妥一点的是用screen或tmux它们提供的是一个可重新附着attach的会话断线后重新登录再attach回去界面和输出都还在。setsid也能起到脱离控制终端的效果适合写进脚本里。还有一种偷懒的做法是disown先把任务放后台再执行disown把它从 shell 的任务表里摘掉。有个细节值得记如果你执行的是ssh host command这种一次性命令形式然后在本地CtrlC本地ssh进程收到中断后关闭连接远端的命令同样会被终止。所以长时间任务一定要用上面那几种方式保护起来。对比一下这几种方式的适用场景方式断线后是否继续能否回看输出适合场景直接前台运行否否秒级完成的命令nohup 是看日志文件批处理脚本setsid是看日志文件脚本内启动screen/tmux是可附着回看交互式长任务disown是否临时应急6. 升级 OpenSSH 的完整过程与翻车后的救场升级 OpenSSH 是运维里风险比较高的操作之一因为它动的是你唯一的远程入口。做之前要有明确的回滚预案做的过程要有带外手段兜底。6.1 升级前必须备份的三样东西第一样是配置目录tar czf /root/ssh-config-backup-$(date %F).tar.gz /etc/ssh第二样是现有的二进制和版本信息cp -a /usr/sbin/sshd /usr/sbin/sshd.bak.$(date %F) rpm -q openssh openssh-server /root/openssh-version-before.txt第三样是 PAM 相关配置/etc/pam.d/sshd有时候会被升级流程影响备份一下没坏处cp -a /etc/pam.d/sshd /root/pam-sshd.bak这三样齐了最坏情况下也能靠单用户模式或者救援介质恢复回来。另外强烈建议在动手之前先确认带外管理比如 IPMI、虚拟控制台或者机房本地键盘是可用的。只有一条 SSH 通道就去做 SSH 升级属于把鸡蛋全放一个篮子里。6.2 编译升级与 systemd 单元处理按前面 2.4 节的流程编译完成make install之后systemd 单元文件通常不需要改因为麒麟自带的sshd.service里的ExecStart指向的就是/usr/sbin/sshd。但有两种情况要留意。一种是编译时改了安装路径。用了--prefix/usr/local的话新的sshd会装到/usr/local/sbin/sshd而sshd.service里写的还是/usr/sbin/sshdsystemctl restart sshd起的是老版本看起来升级没生效。这种情况要么改 unit 文件要么在configure里就指定--prefix/usr。另一种是新版本在安装时发现已存在sshd_config会把新的默认配置写成sshd_config.out之类的名字避免覆盖你的配置。这时要手动比对一下新旧配置有哪些新增项尤其是安全相关的默认值发生了变化的部分。重启服务之前先做一次语法检查然后用一个独立会话测试/usr/sbin/sshd -V /usr/sbin/sshd -t systemctl restart sshd ss -lntp | grep sshd重启sshd有个让人安心的特性它不会断开已经建立的会话。所以你可以在一个现有会话里执行重启然后立刻在另一个终端尝试新连接两边同时观察。如果新连接失败现有会话还在还有机会回滚。6.3 升级后连不上的报错对照表这一节是实打实的排错经验按报错信息查会快很多。报错信息可能原因处置方式Connection refused服务未启动、端口未监听、防火墙拦截systemctl status sshdss -lntp检查防火墙Connection timed out网络不通或中间设备拦截ping、telnet host port逐层排查No hostkeys available主机密钥缺失ssh-keygen -A重新生成Permission denied (publickey)密钥不被接受、权限过宽检查authorized_keys权限和家目录权限Host key verification failed服务端主机密钥变了清理known_hosts里对应条目REMOTE HOST IDENTIFICATION HAS CHANGED同上重装或换机后常见ssh-keygen -R host移除旧指纹no matching key exchange method found算法协商不匹配检查双方支持的算法列表no matching host key type found客户端与服务端 host key 算法不匹配调整HostKeyAlgorithmsToo many authentication failures本地私钥太多逐个尝试耗尽次数用-i指定密钥或写IdentitiesOnly yeskex_exchange_identification: Connection closed服务端配置错误或触发限制看/var/log/secure和journalctl -u sshderror while loading shared libraries新二进制链接的库不对ldd /usr/sbin/sshd定位缺失库bad ownership or modes文件权限不合规按 5.1 节的权限要求修正日志是最可靠的线索遇到问题先看这两处tail -n 100 /var/log/secure journalctl -u sshd --since 10 minutes ago/var/log/secure记录了认证相关的详细过程journalctl能看到服务启动阶段的错误。升级后的故障几乎都能从这两处找到方向。6.4 回滚方案与验证回滚就是刚才备份的逆向操作systemctl stop sshd cp -a /usr/sbin/sshd.bak.YYYY-MM-DD /usr/sbin/sshd tar xzf /root/ssh-config-backup-YYYY-MM-DD.tar.gz -C / /usr/sbin/sshd -t systemctl start sshd ss -lntp | grep sshd回滚之后立刻用一个新连接验证能登录再检查版本号是否回到了原来的ssh -V /usr/sbin/sshd -V如果操作过程中把 SSH 彻底搞挂了只能靠控制台登录然后从/usr/sbin/sshd.bak.*恢复二进制或者用系统的包管理重装原版本包yum reinstall -y openssh-server openssh-clientsreinstall会把包里的文件按原始状态恢复配置文件一般不会覆盖配置文件通常标记为%config(noreplace)所以自定义配置能保住。7. 故障排查的固定套路与几条个人经验排查 SSH 问题我习惯按从外到内的顺序走这样不会漏层。第一步确认网络可达ping和telnet host port是最直接的判断第二步确认服务在监听ss -lntp看端口和进程第三步确认外围策略放行防火墙和 SELinux 都过一遍第四步看认证日志/var/log/secure里通常会明确写出拒绝原因第五步才回到配置文件本身用sshd -T看实际生效值。这个顺序能覆盖绝大多数场景比一上来就翻配置文件有效率得多。几个我踩过的坑值得单独说。一个是sshd_config里同一配置项重复出现时生效的是先出现的那个这个行为和其他很多配置文件不同改配置时如果只是追加一行而没注释掉原来的大概率不生效。另一个是键盘交互认证KbdInteractiveAuthentication和密码认证是两回事某些版本的客户端在密码认证关闭后仍会尝试交互认证表现上和密码登录很像排查时要分清。还有MaxStartups这个参数默认是10:30:100在高并发批量连接的场景下会触发随机拒绝表现出来是偶尔有几台连不上重试又好了遇到这种间歇性现象可以看看这个值。关于批量操作如果要在几十台机器上执行同样的命令别写for循环里套ssh那样慢且容易因为某一台的问题卡住。可以看看系统里有没有pdsh或者用pssh这类并行工具它们能并发执行并且把输出按主机归集。要用循环的话至少加上连接超时和密钥指定for h in 10.0.0.21 10.0.0.22 10.0.0.23; do ssh -o ConnectTimeout5 -o BatchModeyes -i ~/.ssh/id_ed25519 ops01$h \ hostname; uptime 21 | sed s/^/[$h] / doneBatchModeyes让认证失败时直接退出而不是等待输入ConnectTimeout防止某一台不通导致整个循环卡死sed加前缀是为了输出可读。这几个小参数在批量场景里非常实用。最后说一句关于版本管理的心得。银河麒麟 V10 有多个 SP 版本不同版本的包版本、默认配置、甚至某些工具的行为都有细微差别。我建议给每台机器维护一份简单的清单记录系统版本、OpenSSH 版本、关键配置项的值和改动时间。出了问题时这张表能帮你快速判断是版本差异导致的还是配置被谁动了。运维里真正省时间的不是排查速度快而是一开始就把信息留全。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑