认证目标4.04 使用基于密钥的验证保护SSH
第2章介绍了SSH客户端程序,包括ssh、scp和sftp。本节的关注点是使用基于密钥的验证来保护SSH访问。
因为SSH是远程管理系统的一个重要工具,所以理解SSH如何加密客户端与SSH服务器之间的通信的基础知识是非常重要的。然后将介绍如何创建公钥/私钥对,使连接不会让用户口令处在风险中。但是,首先了解SSH配置命令和文件的基础知识很有帮助。
4.4.1 SSH的配置命令
需要了解如下用于SSH的实用工具:
● sshd 守护进程服务,该服务必须运行,才能接收入站的SSH客户端请求。
● ssh-agent 这是一个程序,用来保存用于数字签名算法(Digital Signature Algorithm, DSA)、椭圆曲线DSA(Elliptic Curve DSA, ECDSA)和Rivest, Shamir, Adleman(RSA)验证的私钥。其思想是,在X会话或登录会话开始时启动ssh-agent命令,其他程序则作为ssh-agent程序的客户端启动。
● ssh-add 向验证代理ssh-agent添加私钥标识。
● ssh Secure Shell命令ssh是登录到远程机器的一种安全的方法,类似于Telnet或rlogin。此命令的基本用法在第2章中已经讨论过。要用在基于密钥的验证中,需要在客户端具有私钥,在服务器具有公钥。本节稍后将创建公钥文件,如id_rsa.pub。将该文件复制到服务器,放到已授权用户的主目录中,即~/.ssh/authorized_keys。
● ssh-keygen 此实用工具为SSH验证创建私钥/公钥对。ssh-keygen -t keytype命令将基于DSA、ECDSA或RSA协议创建一个密钥对。
● ssh-copy-id 此脚本将公钥复制到目标远程系统中。
4.4.2 SSH客户端配置文件
使用SSH配置的系统在两个不同的目录中包含配置文件。对于本地系统,基本的SSH配置文件存储在/etc/ssh目录中。但是,每个用户的主目录下的~/.ssh/子目录中的文件同样重要。
这些文件配置了给定用户连接到远程系统的方式。包含了DSA、ECDSA和RSA密钥时,用户的~/.ssh/子目录中包含以下文件:
● authorized_keys 包含远程用户的一个公钥列表。在此文件中有公钥的用户可以连接到远程系统。在复制到此文件的每个公钥的末尾包含系统用户和名称。
● id_dsa 包含基于DSA算法的本地私钥。
● id_dsa.pub 包含用户的本地公钥,基于DSA算法。
● id_ecdsa 包含基于ECDSA算法的本地私钥。
● id_ecdsa.pub 包含用户的本地公钥,基于ECDSA算法。
● id_rsa 包含基于RSA算法的本地私钥。
● id_rsa.pub 包含用户的本地公钥,基于RSA算法。
● known_hosts 包含远程系统的公共主机密钥。用户第一次登录到系统时,会提示其接受远程服务器的公钥。在RHEL 7上,默认使用ECDSA协议来加密流量。远程服务器上的对应公钥存储在/etc/ssh/ssh_host_ecdsa_key.pub文件中,被客户端添加到其本地的~/.ssh/known_hosts文件中。
4.4.3 基本的加密通信
计算机网络中的基本加密通常需要一个私钥和一个公钥。其原理与第10章将介绍的GPG通信相同。私钥由所有者存储,公钥被发送给第三方。当正确配置密钥对时,用户可以使用自己的私钥加密消息,第三方可使用对应的公钥解密该消息。反过来也一样:第三方可使用接收方的公钥加密一个消息,而接收方可使用其私钥解密该消息。SSH协议的工作方式类似:服务器将公钥副本发送给客户端,客户端使用此密钥解密流量并建立安全的通信渠道。
加密密钥基于随机数。数字极大(RSA密钥通常为2048位或更多),所以入侵服务器系统几乎是不可能的(至少对于使用PC而言如此)。私钥和公钥基于这些随机数的一个相匹配的集合。
1.私钥
私钥必须是安全的。基于密钥的验证依赖于私钥,且该私钥只能被其用户所有者访问;私钥存储在其用户所有者的主目录下的~/.ssh子目录中。为了验证用户,服务器向客户端发送一个“质询”,也就是执行一个加密操作的请求,该操作需要知道私钥。当服务器收到客户端对其质询的响应后,就能够解密消息,证明用户身份的真实性。
2.公钥
公钥就是公共可用的密钥。公钥需要被复制到合适用户的~/.ssh/子目录下的authorized_keys文件中。
图4-7中的例子列出了与SSH的用法有关的目录和文件。
图4-7 用户的.ssh/子目录中的密钥
考试提示
大多数与SSH基于密钥的验证有关的常见问题都和文件权限有关。如图4-7所示,私钥的权限被设为600,公钥的权限被设为644。另外,~/.ssh目录的权限应该是700。
密钥就像是一个口令,用来加密通信数据。但是,密钥并不是标准的口令。试想一下要记忆用十六进制数字表达的1024位数字,如下所示:
308189028181 00D4596E 01DE A012 3CAD 51B7 7835 05A4 DEFC C70B 4382 A733 5D62 A51B B9D6 29EA 860B EC2B 7AB8 2E96 3A4C 71A2 D087 11D0 E149 4DD5 1E208382 FA58 C7DA D9B03865 FF6E 88C7 B672 51F55094 3B35 D8AA BC68 BBEB BFE3 9063 AE75 8B57 09F9 DCF8 FFA4 E32C A17F 82E9 7A4C 0E10 E62D 8A970845007B 169A 0676 E7CF 5713
私钥是类似的,但是必须保持私钥的私有性,否则整个系统就会失败。保持私有意味着其他人不应该能够访问服务器系统。如果PC是公共的,那么需要使用口令短语(口令)来保护私钥。稍后将介绍设置口令短语的过程。不要忘记设置口令短语,否则必须创建新的密钥对,并再次将公钥复制到所有目标系统上。
4.4.4 为基于密钥的验证建立私钥/公钥对
ssh-keygen命令用来建立公钥/私钥对。虽然该命令默认创建一个RSA密钥,但是也可以用它来创建DSA或ECDSA密钥。例如,一些用户可能需要DSA密钥,以遵从美国政府的一些标准。图4-8显示了该命令序列的一个例子。
图4-8 生成SSH密钥对的命令
如图所示,该命令提示输入可选的口令短语来保护私钥。当确认口令短语相同后,就将私钥保存到id_rsa文件中,对应的公钥保存在id_rsa.pub文件中。对于用户michael,两个文件都存储在/home/michael/.ssh目录中。
如果愿意,可以使用更多的位来建立RSA密钥。在我们的测试中,能够相当快速地建立多达8192位的密钥对,即使虚拟机系统上只有一个虚拟CPU。
开始此过程的命令如下:
$ ssh-keygen -b 8192
另外,如果需要DSA密钥,可以使用下面的命令。只允许使用1024位的DSA密钥。执行此命令后,过程与图4-8所示相同。
$ ssh-keygen -t dsa
下一步是将公钥传输到远程系统,可能是你管理的一个服务器。如果愿意通过网络传输公钥(每个连接一次),可以使用下面的命令:
$ ssh-copy-id -i .ssh/id_rsa.pub michael@tester1.example.com
严格来说,不使用-i选项时,ssh-copy-id命令默认传输最新创建的公钥。前面的命令自动将本地RSA密钥追加到远程的~/.ssh/authorized_keys文件的末尾。/home/michael目录中包含该文件。当然,可以选择用IP地址替换主机名。
考试提示
有时,将密钥对复制到远程系统后,在尝试登录时,可能得到一个“agent admitted failure to sign using the key”错误,后跟口令提示。为了解决这个问题,退出控制台或GUI,然后重新登录。大多数时候,ssh命令将提示输入口令短语。
然后应该能够立即连接到该远程系统。在上例中,下面两个命令都是正确的命令:
$ ssh -l michael tester1.example.com $ ssh michael@tester1.example.com
在控制台中执行时,ssh命令使用下面的口令短语提示:
Enter passphrase for key '/home/michael/.ssh/id_rsa'
在基于GUI的命令行执行时,会使用一个窗口进行提示,如图4-9所示。
图4-9 提示输入口令短语