迁移到 ssh 证书认证

前两天给服务器升级完 openssh 7.1,发现无法通过密码登录 ssh 服务器了,查 openssh 7.0 的 changelog,才注意到低于 1024 位的 RSA 认证已经被废弃。而我目前所用的认证算法应该是 768 位 RSA。

幸好 Linode 提供了 lish,还可以登录。于是干脆直接放弃纯密码的认证方式,改为证书认证,也可以顺便增强一下安全性,因为之前查日志发现有可疑 IP 在尝试暴力破解我的 ssh 密码。

首先就是要生成私钥/公钥对,这一步很简单,在服务器端和客户端做都可以:

# 指定采用 4096 位 RSA 算法
[user@localhost]$ ssh-keygen -t rsa -b 4096
Generating public/private rsa key pair.
Enter file in which to save the key (/home/user/.ssh/id_rsa): 
Enter passphrase (empty for no passphrase): 
Enter same passphrase again: 
Your identification has been saved in /home/user/.ssh/id_rsa.
Your public key has been saved in /home/user/.ssh/id_rsa.pub.
The key fingerprint is:
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx user@localhost
The key's randomart image is:
+---[RSA 4096]----+
|*X ==. .         |
|*XX.+.+ .        |
|XX.+ X X X       |
|X.X =   X .      |
|XX X X .X+       |
|XXX . +XX .      |
| X.X XX ..       |
|  . .  . ..      |
|          ..     |
+----[SHA256]-----+

此时会在 /home/user/.ssh 下生成私钥/公钥对,分别名为 id_rsaid_rsa.pub。前者是用于客户端的私钥,后者是用于服务器端的公钥。

然后,把 id_rsa.pub 复制到服务器端,并重命名为 authorized_keys,权限必须是 600。

当然,如果是在服务器生成的私钥/公钥对,那么就把 id_rsa 复制到客户端的 ~/.ssh 下,无需重命名,只需要把权限设置为 600 即可。

注意,如果需要登录服务器的某个用户,那么必须在该用户的 ~/.ssh 下复制一份同样的 authorized_keys 文件。

做完以上设置,为了安全起见,可以在 /etc/ssh/sshd_config 里面进行如下设置:

# 禁止 root 登录
PermitRootLogin no

# 强制采用证书认证,不允许纯密码登录
PasswordAuthentication no

然后重启 sshd 服务即可。

如果一切顺利,到此应该就结束了,但是很可惜,我以普通用户登录失败了,而 root 可以正常登录。

搜索了 Google,都是说检查 ~/.ssh 目录是否为 700 权限,authorized_keys 是否为 600 权限。但是我这两个地方的权限都正常。

后来无意检查了下我的 $HOME 权限,发现居然是 777。于是试着改回 755,果不其然,普通用户也可以顺利登录了,问题解决。