1. 私钥格式问题
1.1 问题表现
Load key "xxx": invalid format
error in libcrypto
Unable to load key
1.2 原因分析
SSH私钥主要存在两种格式:
- OpenSSH新格式(7.8版本引入),头部标识为
-----BEGIN OPENSSH PRIVATE KEY----- - PEM旧格式,头部标识为
-----BEGIN RSA PRIVATE KEY-----或-----BEGIN DSA PRIVATE KEY-----
旧版OpenSSH客户端(低于7.8)或部分第三方SSH库(如Paramiko、旧版Java SSH实现)无法识别OpenSSH新格式,导致加载失败。
1.3 解决方案
查看私钥格式:
head -n 1 ~/.ssh/id_rsa
将新格式转换为PEM旧格式:
ssh-keygen -p -m PEM -f ~/.ssh/id_rsa -P "" -N ""
验证私钥是否可以正常读取:
ssh-keygen -y -f ~/.ssh/id_rsa
如果该命令成功输出对应的公钥内容,说明私钥格式正确;若报错,则需要进一步排查。
2. 私钥权限问题
2.1 问题表现
Permissions 0644 for 'xxx' are too open.
It is required that your private key files are NOT accessible by others.
This private key will be ignored.
bad permissions: ignore key: xxx
2.2 原因分析
OpenSSH出于安全考虑,要求私钥文件仅能被当前用户读取。如果文件权限设置为组用户或其他用户可读,SSH客户端会拒绝加载该私钥。
2.3 解决方案
Linux / macOS 环境:
chmod 600 ~/.ssh/id_rsa
chmod 644 ~/.ssh/id_rsa.pub
chmod 700 ~/.ssh
Windows 环境(以管理员身份运行PowerShell):
icacls "C:\Users\用户名\.ssh\私钥文件" /inheritance:r
icacls "C:\Users\用户名\.ssh\私钥文件" /remove "Authenticated Users" "Users" "Everyone"
icacls "C:\Users\用户名\.ssh\私钥文件" /grant:r "%USERNAME%:R"
执行完毕后,可用 icacls "私钥文件路径" 验证权限设置是否生效。
3. 换行符与文件结尾问题
3.1 问题表现
Load key "xxx": invalid format
使用 dos2unix 转换换行符后问题依旧存在,且 ssh-keygen -y 仍然报错。
3.2 原因分析
此问题包含两个层面:
第一,Windows系统使用 CRLF(\r\n)作为换行符,而OpenSSH要求使用Unix标准的 LF(\n)。若私钥文件中包含 CRLF,客户端可能无法正确解析。
第二,OpenSSH要求私钥文件必须以换行符(LF)结尾。若文件在 -----END OPENSSH PRIVATE KEY----- 后直接结束而缺少末尾换行符,即使文件头部和内容完全正确,也会被判定为 invalid format。这是最容易遗漏的问题。
3.3 解决方案
检查文件换行符和末尾状态:
xxd ~/.ssh/id_ed25519 | tail -n 5
正确格式的末尾应显示 0a(LF换行符)。若显示 0d 0a(CRLF),则需要转换;若末尾没有 0a,则需要添加。
修复CRLF换行符:
dos2unix ~/.ssh/id_ed25519
修复末尾缺少换行符:
echo "" >> ~/.ssh/id_ed25519
Windows PowerShell环境下:
Add-Content -Path "C:\Users\用户名\.ssh\id_ed25519" -Value "`n"
使用文本编辑器(如VS Code、Notepad++)时,应确保右下角换行符设置为 LF,并在文件末尾添加一个空行后保存,编码格式选择 UTF-8 without BOM。
4. 路径与配置问题
4.1 问题表现
Warning: Identity file xxx not accessible: No such file or directory
Permission denied (publickey)
4.2 原因分析
配置文件(~/.ssh/config)中的 IdentityFile 路径设置不正确,导致SSH客户端无法找到指定的私钥文件。具体原因包括:
- 路径拼写错误,包含多余字符或遗漏字符
- Windows环境下使用单反斜杠
\作为路径分隔符,被解析为转义字符 ~在Windows SSH客户端中解析失败或解析为错误的路径- 配置文件中指定的私钥文件名与实际文件名不一致
4.3 解决方案
使用绝对路径替代 ~ 相对路径,可避免路径解析歧义。
Windows环境配置文件示例:
Host myserver
HostName 192.168.1.100
User root
IdentityFile C:/Users/用户名/.ssh/id_rsa
Linux / macOS 环境:
Host myserver
HostName 192.168.1.100
User root
IdentityFile /home/用户名/.ssh/id_rsa
Windows路径分隔符规范:
- 推荐使用正斜杠:
C:/Users/用户名/.ssh/id_rsa - 或使用双反斜杠:
C:\\Users\\用户名\\.ssh\\id_rsa - 避免使用单反斜杠:
C:\Users\用户名\.ssh\id_rsa(可能被解析为转义序列)
命令行指定私钥进行测试:
ssh -i /path/to/private_key user@hostname
若此命令可以正常连接,则说明配置文件中的路径设置存在问题,应检查 IdentityFile 的写法。
5. 代理跳转与转发问题
5.1 问题表现
Load key "xxx": invalid format
Permission denied (publickey)
直接连接跳板机正常,但通过 ProxyJump 跳转至目标机时认证失败。
5.2 原因分析
典型的跳转配置如下:
Host jump
HostName 192.168.1.10
User root
IdentityFile ~/.ssh/id_rsa_jump
Host target
HostName 192.168.56.100
User root
IdentityFile ~/.ssh/id_rsa_target
ProxyJump jump
可能的原因包括:
- 跳板机与目标机使用相同的私钥文件,但目标机上未部署对应的公钥
ForwardAgent启用时,SSH客户端尝试将本地私钥转发至跳板机,而跳板机未配置相应公钥- 目标机使用的私钥文件本身存在格式或权限问题,但此前未被发现
5.3 解决方案
首先验证目标机的私钥文件是否可正常读取:
ssh-keygen -y -f ~/.ssh/id_rsa_target
若该命令失败,说明私钥文件本身存在问题,应参照前文相关章节进行修复。
确认公私钥配对关系,确保目标机上 ~/.ssh/authorized_keys 包含与本地私钥对应的公钥内容。
检查公钥部署:
ssh -v target
查看详细输出,确认加载了哪个私钥文件,以及服务器端是否接受了该公钥。
如需禁用私钥转发,可在目标机配置中添加:
ForwardAgent no
若跳转过程中需要在不同主机使用不同私钥,应在每个Host段分别指定 IdentityFile。
6. 密钥类型不兼容问题
6.1 问题表现
no matching host key type found. Their offer: ssh-rsa,ssh-dss
Unable to negotiate with xxx: no matching key exchange method found.
6.2 原因分析
高版本OpenSSH客户端(8.5及以上)出于安全考虑,默认禁用了部分旧版加密算法,包括 ssh-rsa 公钥签名算法和 diffie-hellman-group1-sha1 等密钥交换算法。若服务器端仅支持这些旧算法,则无法完成密钥协商。
6.3 解决方案
临时启用旧算法进行连接:
ssh -o HostKeyAlgorithms=+ssh-rsa -o PubkeyAcceptedKeyTypes=+ssh-rsa user@hostname
永久配置,在 ~/.ssh/config 中为指定主机添加:
Host oldserver
HostName 192.168.1.100
User root
HostKeyAlgorithms +ssh-rsa
PubkeyAcceptedKeyTypes +ssh-rsa
注意,启用旧算法会降低连接安全性,仅应在连接到确实无法升级的旧服务器时使用。
7. 常见错误信息速查表
| 错误信息 | 主要原因 | 解决方案 |
|---|---|---|
| invalid format | 格式错误、末尾缺换行、头部损坏 | 检查头部标识→修复换行符→添加末尾换行→转换格式 |
| Permissions too open | 私钥权限过于开放 | Linux: chmod 600 / Windows: icacls 收紧权限 |
| No such file or directory | 文件路径错误 | 使用绝对路径,检查文件名拼写 |
| Permission denied (publickey) | 公钥未部署或私钥不匹配 | 检查服务器 authorized_keys,验证公私钥配对 |
| no matching host key type found | 加密算法不兼容 | 配置 HostKeyAlgorithms 启用旧算法 |
| bad passphrase | 密码错误或格式问题 | 确认密码,或使用 -N “” 移除密码 |
| Agent admitted failure to sign | ssh-agent 缓存问题 | ssh-add -D 清空后重新添加 |
| load failed: invalid format | 文件末尾缺少换行符 | echo “” >> 私钥文件 |
私钥健康检查流程
遇到私钥认证问题时,建议按照以下顺序进行排查:
检查私钥文件是否存在:
ls -la ~/.ssh/id_*
检查文件权限:
ls -la ~/.ssh/id_* # Linux/macOS
icacls ~/.ssh/id_* # Windows
检查文件头部标识是否正确:
head -n 1 ~/.ssh/id_*
检查是否存在CRLF换行符问题:
file ~/.ssh/id_* | grep CRLF
检查文件末尾是否有换行符:
xxd ~/.ssh/id_* | tail -n 5
尝试从私钥提取公钥,验证私钥是否可读:
ssh-keygen -y -f ~/.ssh/id_*
使用详细模式连接,查看完整认证过程:
ssh -v user@hostname
最佳实践建议
使用ED25519密钥类型替代RSA,具有更高的安全性和性能:
ssh-keygen -t ed25519 -C "user@example.com"
生成私钥时使用新格式和较高的加密迭代次数:
ssh-keygen -t ed25519 -o -a 100
为不同环境使用不同的密钥对,避免单一密钥泄露影响所有系统。
定期备份私钥文件,并存储在安全的位置。
配置文件(~/.ssh/config)中使用绝对路径指定 IdentityFile,避免路径解析歧义。
私钥权限应严格限制为仅当前用户可读写,不可被其他用户访问。
原文 https://blog.csdn.net/2301_79518550/article/details/163314908