Skip to content

Latest commit

 

History

History
1720 lines (1157 loc) · 84.8 KB

File metadata and controls

1720 lines (1157 loc) · 84.8 KB

六、SSH 加固

安全外壳 ( SSH )套件是 Linux 管理员必备的工具之一。它可以让你在自己的小隔间里,甚至在自己家里舒适地照顾 Linux 服务器。无论哪种方式,都比穿上你的派克大衣,穿过安全圈进入冰冷的服务器机房要好很多。安全外壳中的安全意味着您键入或传输的所有内容都将被加密。这就消除了有人通过在你的网络中插入嗅探器来获取敏感数据的可能性。

在你的 Linux 职业生涯的这个阶段,你应该已经知道如何使用安全外壳或 SSH 来进行远程登录和远程文件传输。您可能不知道的是,SSH 的默认配置实际上相当不安全。在本章中,我们将了解如何以各种方式加固默认配置。我们将研究如何使用比默认算法更强的加密算法,如何设置无密码身份验证,以及如何为安全文件传输协议(SFTP)的用户设置监狱。另外,我们将了解如何扫描 SSH 服务器以查找易受攻击的配置,以及如何通过安全外壳文件系统 ( SSHFS )共享远程目录。

在本章中,我们将涵盖以下主题:

  • 确保 SSH 协议 1 被禁用
  • 为无密码登录创建和管理密钥
  • 禁用根用户登录
  • 禁用用户名/密码登录。
  • 使用强加密算法配置安全外壳
  • 在 RHEL 8/CentOS 8 上设置系统范围的加密策略
  • CentOS 8/红帽 8 上的 FIPS 模式
  • 配置更详细的日志记录
  • 使用白名单和 TCP 包装器进行访问控制
  • 配置自动注销和安全横幅
  • 其他杂项安全设置
  • 为不同的主机设置不同的配置
  • 为不同的用户和组设置不同的配置
  • 扫描 SSH 服务器
  • 为 SFTP 用户建立一个客户环境
  • 使用 SSHFS 设置共享目录
  • 从 Windows 桌面远程连接

所以,如果你准备好了,让我们开始吧。

确保 SSH 协议 1 被禁用

SSH 协议版本 1,最初的 SSH 协议,有严重的缺陷,永远不应该使用。它仍然存在于大多数 Linux 发行版中,但幸运的是,它总是被默认禁用。但是,假设您打开您的/etc/ssh/sshd_config文件,看到以下内容:

Protocol 1

或者,您可能会看到:

Protocol 1, 2

如果你做了,那你就有问题了。

sshd_config文件的 Ubuntu 手册页指出,协议版本 1 仍可用于传统设备。然而,如果你还在运行那么旧的设备,你需要开始认真考虑做一些升级。

随着 Linux 发行版的更新,您将看到 SSH 协议 1 逐渐被完全移除,就像红帽和 CentOS 从 7.4 版本开始的情况一样。

为无密码登录创建和管理密钥

SSH 是一套与远程服务器通信的工具。可以使用 SSH 组件远程登录远程机器的命令行,也可以使用scpsftp安全传输文件。使用这些 SSH 组件的默认方式是使用用户名和一个人的普通 Linux 用户帐户。因此,从我的 OpenSUSE 工作站的终端登录到一台远程机器将看起来像这样:

donnie@linux-0ro8:~> ssh donnie@192.168.0.8
donnie@192.168.0.8's password:

虽然用户名和密码确实以加密格式在网络上传播,使得恶意行为者很难拦截,但这仍然不是最安全的做生意方式。问题是攻击者可以访问自动工具,这些工具可以对 SSH 服务器执行暴力密码攻击。僵尸网络,如冰雹玛丽云,在互联网上执行连续扫描,以找到启用 SSH 的面向互联网的服务器。

如果僵尸网络发现服务器允许通过用户名和密码进行 SSH 访问,它将发起暴力密码攻击。可悲的是,这样的攻击已经成功了很多次,尤其是当服务器操作员允许根用户通过 SSH 登录时。

This older article provides more details about the Hail Mary Cloud botnet: http://futurismic.com/2009/11/16/the-hail-mary-cloud-slow-but-steady-brute-force-password-guessing-botnet/.

在下一节中,我们将研究两种有助于防止此类攻击的方法:

  • 通过交换公钥启用 SSH 登录
  • 通过 SSH 禁用根用户登录

现在,让我们创建一些密钥。

创建用户的 SSH 密钥集

每个用户都有能力创建他或她自己的一组私钥和公钥。不管用户的客户端机器是运行 Linux、macOS、Windows 上的 Cygwin,还是 Windows 的 Bash Shell。在所有情况下,程序完全相同。

您可以创建几种不同类型的密钥,2,048 位 RSA 密钥通常是默认的。直到最近,2,048 位 RSA 密钥还被认为在可预见的未来足够强大。但是现在,来自美国国家标准与技术研究所的最新指导意见称使用至少 3072 位的 RSA 密钥或至少 384 位的椭圆曲线数字签名 算法 ( ECDSA )密钥。(你有时会看到这些 ECDSA 键被称为 P-384。)他们的理由是,他们想让我们为量子计算做好准备,量子计算将非常强大,它将使任何较弱的加密算法过时。当然,量子计算还不实用,到目前为止,无论是哪一年,它似乎都是未来十年才会发生的事情之一。但是,即使我们对整个量子理论不以为然,我们仍然必须承认,即使是我们目前的非量子计算机也在变得越来越强大。因此,从更强的加密标准入手仍然不是一个坏主意。

To see the NIST list of recommended encryption algorithms and the recommended key lengths, go to https://cryptome.org/2016/01/CNSA-Suite-and-Quantum-Computing-FAQ.pdf.

对于接下来的几个演示,让我们切换到 Ubuntu 18.04 客户端。要创建 3072 RSA 密钥对,只需执行以下操作:

donnie@ubuntu1804-1:~$ ssh-keygen -t rsa -b 3072

在这种情况下,我们使用-t选项来指定我们想要一个 RSA 密钥,使用-b选项来指定位长。当提示输入钥匙的位置和名称时,我只需点击进入接受默认值。您可以将私钥留为空白密码,但这不是推荐的做法。

Note that if you choose an alternative name for your key files, you'll need to type in the entire path to make things work properly. For example, in my case, I would specify the path for donnie_rsa keys as /home/donnie/.ssh/donnie_rsa.

您将在.ssh目录中看到您的新钥匙:

donnie@ubuntu1804-1:~$ ls -l .ssh
total 8
-rw------- 1 donnie donnie 2546 Aug 28 15:23 id_rsa
-rw-r--r-- 1 donnie donnie 573 Aug 28 15:23 id_rsa.pub
donnie@ubuntu1804-1:~$

Note that if you had created the default 2,048-bit keys, the names would have been identical

id_rsa密钥是私钥,只有我有读写权限。id_rsa.pub公钥必须是世界可读的。对于 ECDSA 密钥,默认长度为 256 位。如果您选择使用 ECDSA 而不是 RSA,请执行以下操作来创建强 384 位密钥:

donnie@ubuntu1804-1:~$ ssh-keygen -t ecdsa -b 384

无论哪种方式,当您查看.ssh目录时,您都会看到 ECDSA 密钥的命名与 RSA 密钥不同:

donnie@ubuntu1804-1:~$ ls -l .ssh
total 8
-rw------- 1 donnie donnie 379 May 27 17:43 id_ecdsa
-rw-r--r-- 1 donnie donnie 225 May 27 17:43 id_ecdsa.pub
donnie@ubuntu1804-1:~$

椭圆曲线算法的美妙之处在于,它们看似较短的密钥长度与较长的 RSA 密钥一样安全。而且,即使是最大的 ECDSA 密钥也比 RSA 密钥需要更少的计算能力。使用 ECDSA 可以实现的最大密钥长度是 521 位。(是的,你没看错。是 521 位,不是 524 位。)所以,你可能会想,我们为什么不直接用 521 位的键去追求那种阵风呢?嗯,主要是因为 NIST 不推荐 521 位密钥。有人担心他们可能会受到填充攻击,这可能会让坏人破坏你的加密并窃取你的数据。

如果你看一下 ssh-keygen 的手册页,你会发现你也可以创建一个Ed25519类型的密钥,有时你会看到它被称为curve25519。这个不在 NIST 推荐算法列表中,但是有些人喜欢使用它有几个原因。

如果操作系统的随机数生成器有缺陷,RSA 和 DSA 在创建签名时可能会泄漏私钥数据。Ed25519在创建签名时不需要随机数生成器,所以对这个问题免疫。此外,Ed25519的编码方式使其更不容易受到旁道攻击。(旁道攻击是指有人试图利用底层操作系统中的弱点,而不是加密算法中的弱点。)

一些人喜欢Ed25519的第二个原因正是因为它在 NIST 榜单上是而不是。不管对错,这些人不信任政府机构的建议。

Quite a few years ago, in the early part of this century, there was a bit of a scandal that involved the Dual Elliptic Curve Deterministic Random Bit Generator (Dual_EC_DRBG). This was a random number generator that was meant for use in elliptic curve cryptography. The problem was that, early on, some independent researchers found that it had the capability to have back doors inserted by anyone who knew about this capability. And, it just so happened that the only people who were supposed to know about this capability were the folk who work at the US National Security Agency (NSA). At the NSA's insistence, NIST included Dual_EC_DRBG in their NIST list of recommended algorithms, and it stayed there until they finally removed it in April 2014. You can get more details about this at the following links:

https://www.pcworld.com/article/2454380/overreliance-on-the-nsa-led-to-weak-crypto-standard-nist-advisers-find.html

http://www.math.columbia.edu/~woit/wordpress/?p=7045

You can read the details about Ed25519 here: https://ed25519.cr.yp.to/.

Ed25519只有一个键大小,256 位。因此,要创建一个curve25519键,只需使用以下代码:

donnie@ubuntu1804-1:~$ ssh-keygen -t ed25519

以下是我创建的密钥:

donnie@ubuntu1804-1:~$ ls -l .ssh
total 8
-rw------- 1 donnie donnie 464 May 27 20:11 id_ed25519
-rw-r--r-- 1 donnie donnie 101 May 27 20:11 id_ed25519.pub
donnie@ubuntu1804-1:~$

然而ed25519也有一些潜在的缺点:

  • 首先,旧的 SSH 客户端不支持它。但是,如果您团队中的每个人都在使用使用当前 SSH 客户端的当前操作系统,这应该不成问题。
  • 第二个是它只支持一个特定的集合密钥长度,相当于 256 位椭圆曲线算法或者 3000 位 RSA 算法。因此,它可能不像我们已经讨论过的其他算法那样经得起未来的考验。
  • 最后,如果您的组织需要遵守 NIST 的建议,您就不能使用它。

好吧。还有一种类型的钥匙我们没有涉及。这是老式的 DSA 密钥,如果您让 ssh-keygen 创建,它仍然会创建。但是,不要这样做。DSA 算法是旧的、陈旧的,并且按照现代标准非常不安全。所以,说到 DSA,就说

将公钥传输到远程服务器

将我的公钥传输到远程服务器可以让服务器轻松识别我和我的客户机。在将公钥传输到远程服务器之前,我需要将私钥添加到我的会话密钥环中。这需要两个命令。(一个命令调用ssh-agent,而另一个命令实际上将私钥添加到密钥环中):

donnie@ubuntu1804-1:~$ exec /usr/bin/ssh-agent $SHELL
donnie@ubuntu1804-1:~$ ssh-add
Enter passphrase for /home/donnie/.ssh/id_rsa: 
Identity added: /home/donnie/.ssh/id_rsa (/home/donnie/.ssh/id_rsa)
Identity added: /home/donnie/.ssh/id_ecdsa (/home/donnie/.ssh/id_ecdsa)
Identity added: /home/donnie/.ssh/id_ed25519 (donnie@ubuntu1804-1)
donnie@ubuntu1804-1:~$

最后,我可以将我的公钥转移到我的 CentOS 服务器,其地址为192.168.0.8:

donnie@ubuntu1804-1:~$ ssh-copy-id donnie@192.168.0.8
The authenticity of host '192.168.0.8 (192.168.0.8)' can't be established.
ECDSA key fingerprint is SHA256:jUVyJDJl2AHJgyrqLudOWx4YUtbUxD88tv5oKeFtfXk.
Are you sure you want to continue connecting (yes/no)? yes
/usr/bin/ssh-copy-id: INFO: attempting to log in with the new key(s), to filter out any that are already installed
/usr/bin/ssh-copy-id: INFO: 3 key(s) remain to be installed -- if you are prompted now it is to install the new keys
donnie@192.168.0.8's password: 

Number of key(s) added: 3

Now try logging into the machine, with: "ssh 'donnie@192.168.0.8'"
and check to make sure that only the key(s) you wanted were added.
donnie@ubuntu1804-1:~$

通常,无论您选择哪种类型,您只会创建一对密钥。如您所见,我创建了三个密钥对,每种类型一对。所有三个私钥都被添加到我的会话密钥环中,所有三个公钥都被传输到远程服务器。

下次登录时,我将使用密钥交换,并且无需输入密码:

donnie@ubuntu1804-1:~$ ssh donnie@192.168.0.8
Last login: Wed Aug 28 13:43:50 2019 from 192.168.0.225
[donnie@localhost ~]$

正如我之前提到的,通常每台机器只能创建一个密钥对。然而,这条规则也有例外。一些管理员更喜欢对他们管理的每台服务器使用不同的密钥对,而不是对所有服务器使用相同的密钥对。一种简便的方法是创建文件名与相应服务器的主机名相匹配的密钥。然后,您可以使用-i选项来指定您想要使用的密钥对。

在这个例子中,我只有一个服务器,但我有多个密钥。假设我更喜欢使用Ed25519键:

donnie@ubuntu1804-1:~$ ssh -i ~/.ssh/id_ed25519 donnie@192.168.0.8
Last login: Wed Aug 28 15:58:26 2019 from 192.168.0.3
[donnie@localhost ~]$

所以,现在,你想知道,如果我可以不输入密码就登录,这有多安全?答案是,一旦您关闭用于登录的客户端机器的终端窗口,私钥将从您的会话密钥环中删除。当您打开一个新的终端并尝试登录到远程服务器时,您将看到以下内容:

donnie@ubuntu1804-1:~$ ssh donnie@192.168.0.8
Enter passphrase for key '/home/donnie/.ssh/id_rsa': 
Last login: Wed Aug 28 16:00:33 2019 from 192.168.0.3
[donnie@localhost ~]$

现在,每次我登录到这个服务器时,我都需要输入我的私钥密码(也就是说,除非我用我在前面部分中向您展示的两个命令将它添加回会话密钥环)。

动手实验–创建和传输 SSH 密钥

在本实验中,您将使用一台虚拟机 ( 虚拟机)作为客户端,一台虚拟机作为服务器。或者,如果您使用的是 Windows 主机,则可以使用 Cygwin、PowerShell 或内置的 Windows Bash shell 作为客户端。(但是请注意,PowerShell 和 Windows Bash shell 将密钥文件存储在不同的位置。)如果您在 Mac 或 Linux 主机上,您可以使用主机的本机命令行终端作为客户端。无论如何,程序都是一样的。

对于服务器虚拟机,使用 Ubuntu 18.04 或 CentOS 7。这个过程在 CentOS 8 上也是一样的。但是,我们将在接下来的几个实验中使用相同的虚拟机,CentOS 8 有一些特殊的注意事项,我们将在后面讨论。让我们开始吧:

  1. 在客户端计算机上,创建一对 384 位椭圆曲线密钥。接受默认文件名和位置,并创建密码:
ssh-keygen -t ecdsa -b 384
  1. 观察按键,注意权限设置:
ls -l ./ssh
  1. 将您的私钥添加到您的会话密钥环中。出现提示时,输入您的密码:
exec /usr/bin/ssh-agent $SHELL
ssh-add
  1. 将公钥传输到服务器虚拟机。出现提示时,输入您在服务器虚拟机上的用户帐户的密码(在以下命令中替换您自己的用户名和 IP 地址):
ssh-copy-id donnie@192.168.0.7
  1. 像平常一样登录服务器虚拟机:
ssh donnie@192.168.0.7
  1. 观察在服务器虚拟机上创建的authorized_keys文件:
ls -l .ssh
cat .ssh/authorized_keys
  1. 注销服务器虚拟机并关闭客户端上的终端窗口。打开另一个终端窗口,尝试再次登录服务器。这一次,应该会提示您输入私钥的密码。
  2. 注销服务器虚拟机,并将您的私钥添加回客户端的会话密钥环。出现提示时,输入您的私钥密码:
exec /usr/bin/ssh-agent $SHELL
ssh-add

只要您在客户端上保持此终端窗口打开,您就可以根据需要多次登录服务器虚拟机,而无需输入密码。但是,当您关闭终端窗口时,您的私钥将从您的会话密钥环中删除。

  1. 保留您的服务器虚拟机,因为我们稍后会用它做更多事情。

您已经到达了实验室的终点–祝贺您!

我们在这里做的很好,但还是不够。一个缺陷是,如果您转到另一台客户端机器,您仍然可以使用正常的用户名/密码身份验证来登录。没关系;我们一会儿就能修好。

禁用根用户登录

几年前,在东南亚的某个地方,有一个颇为著名的案例,恶意行为者设法在相当多的 Linux 服务器上植入了恶意软件。坏人发现这很容易做到有三个原因:

  • 所涉及的面向互联网的服务器被设置为对 SSH 使用用户名/密码验证。
  • 允许根用户通过 SSH 登录。
  • 用户密码,包括根用户的密码,非常弱。

所有这一切意味着冰雹玛丽很容易蛮力进入。

不同的发行版对根用户登录有不同的默认设置。在您的 CentOS 机器的/etc/ssh/sshd_config文件中,您会看到这一行:

#PermitRootLogin yes

与大多数配置文件不同的是,sshd_config中的注释行定义了安全外壳守护程序的默认设置。所以,这一行表示根用户确实被允许通过 SSH 登录。要改变这一点,我将删除注释符号并将设置更改为no:

PermitRootLogin no

为了使新的设置生效,我将重新启动 SSH 守护程序,它在 CentOS 上被命名为sshd,在 Ubuntu 上被命名为ssh:

sudo systemctl restart sshd

在 Ubuntu 机器上,默认设置看起来有点不同:

PermitRootLogin prohibit-password

这意味着允许根用户登录,但只能通过公钥交换。如果您真的需要允许根用户登录,这可能已经足够安全了。但是在大多数情况下,您会希望强制管理员用户使用他们的正常用户帐户登录,并使用sudo来满足他们的管理需求。所以,大多数情况下,你还是要把这个设置改成no

Be aware that if you deploy a Linux instance on a cloud service, such as Rackspace or Vultr, the service owners will have you log into the VM with the root user account. The first thing you'll want to do is create your own normal user account, log back in with that account, disable the root user account, and disable the root user login in sshd_config. Microsoft Azure is one exception to this rule because it automatically creates a non-privileged user account for you.

在下一节中,您将能够在几分钟内练习这一点。

禁用用户名/密码登录

这是您在与客户建立密钥交换后才想做的事情。否则,客户端将被禁止进行远程登录。

动手实验–禁用根登录和密码验证

对于本实验,请使用与上一实验相同的服务器虚拟机。让我们开始吧:

  1. 在 Ubuntu 或 CentOS 服务器虚拟机上,在sshd_config文件中查找这一行:
#PasswordAuthentication yes
  1. 去掉注释符号,将参数值改为no,重启 SSH 守护进程。该行现在应该如下所示:
PasswordAuthentication no

现在,当僵尸网络扫描你的系统时,他们会发现进行暴力密码攻击毫无用处。然后他们就会走开,让你一个人呆着。

  1. 根据服务器是 Ubuntu 还是 CentOS 虚拟机,查找这两行中的任意一行:
#PermitRootLogin yes
#PermitRootLogin prohibit-password

取消对该行的注释,并将其更改为以下内容:

PermitRootLogin no
  1. 重新启动 SSH 守护程序,以便它能够读入新的更改。在 Ubuntu 上,您可以这样做:
sudo systemctl restart ssh

在 CentOS 上,您可以这样做:

sudo systemctl restart sshd
  1. 尝试从您在上一个实验中使用的客户端登录到服务器虚拟机。
  2. 尝试从尚未创建密钥对的另一个客户端登录到服务器虚拟机。(你不应该可以。)
  3. 像以前一样,保留服务器虚拟机,因为我们稍后会用它做更多的事情。

您已经到达了实验室的终点–祝贺您!

既然我们已经介绍了如何在客户端创建私有/公共密钥对,以及如何将公共密钥传输到服务器,那么我们就来谈谈 SSH 使用的算法类型。之后,我们将讨论如何禁用一些较旧、较弱的算法。

使用强加密算法配置安全外壳

正如我之前提到的,当前的 NIST 建议集商业国家安全算法套件 ( CNSA 套件)涉及使用比我们之前需要使用的更强的算法和更长的密钥。我将在此表中总结新的建议:

| 算法 | 用法 | | RSA,3,072 位或更大 | 密钥建立和数字签名 | | Diffie-Hellman (DH),3,072 位或更大 | 关键机构 | | ECDH 与 NIST P-384 | 关键机构 | | 带有 NIST P-384 的电子海图显示和导航系统 | 数字签名 | | SHA-384 | 完整 | | AES-256 | 机密 |

在其他出版物中,您可能会看到 NIST 套件 B 是加密算法的推荐标准。乙套房是一个旧的标准,已被 CNSA 套房取代。

另一个你可能不得不使用的密码标准是联邦信息处理标准 ( FIPS ),它也是由美国政府颁布的。目前的版本是 FIPS 140-2,最近一次修订是在 2002 年 12 月。2019 年 9 月 22 日获得最终批准的 FIPS 140-3 最终将成为新标准。受 FIPS 法规约束的美国政府机构已经被指示开始向 FIPS 140-3 过渡。

了解 SSH 加密算法

SSH 结合了对称和非对称加密技术,类似于传输层安全性。SSH 客户端通过使用公钥方法与 SSH 服务器建立非对称会话来启动该过程。一旦建立了这个会话,两台机器就可以达成一致并交换一个密码,它们将使用这个密码来建立一个对称会话。(正如我们之前在 TLS 中看到的,出于性能原因,我们希望使用对称加密,但我们需要一个非对称会话来执行密钥交换。)为了实现这一神奇功能,我们需要四类加密算法,我们将在服务器端配置它们。这些措施如下:

  • Ciphers:这些是对客户端和服务器之间交换的数据进行加密的对称算法。
  • HostKeyAlgorithms:这是服务器可以使用的主机密钥类型列表。
  • KexAlgorithms:这些是服务器可以用来进行对称密钥交换的算法。
  • MAC:消息认证码是对传输中的加密数据进行加密签名的哈希算法。这可以确保数据的完整性,并让您知道是否有人篡改了您的数据。

获得这种感觉的最好方法是查看sshd_config手册页,如下所示:

man sshd_conf

我可以用任何虚拟机来演示这一点。不过,目前我打算用 CentOS 7,除非我声明不是这样。(对于不同的 Linux 发行版和版本,默认算法和可用算法的列表会有所不同。)

首先,让我们看看支持的密码列表。向下滚动手册页,直到看到它们:

3des-cbc
aes128-cbc
aes192-cbc
aes256-cbc
aes128-ctr
aes192-ctr
aes256-ctr
aes128-gcm@openssh.com
aes256-gcm@openssh.com
arcfour
arcfour128
arcfour256
blowfish-cbc
cast128-cbc
chacha20-poly1305@openssh.com

但是,并非所有这些受支持的密码都已启用。就在这个列表下面,我们可以看到默认启用的密码列表:

chacha20-poly1305@openssh.com,
aes128-ctr,aes192-ctr,aes256-ctr,
aes128-gcm@openssh.com,aes256-gcm@openssh.com,
aes128-cbc,aes192-cbc,aes256-cbc,
blowfish-cbc,cast128-cbc,3des-cbc

接下来,按字母顺序排列的是HostKeyAlgorithms。CentOS 7 上的列表如下所示:

ecdsa-sha2-nistp256-cert-v01@openssh.com,
ecdsa-sha2-nistp384-cert-v01@openssh.com,
ecdsa-sha2-nistp521-cert-v01@openssh.com,
ssh-ed25519-cert-v01@openssh.com,
ssh-rsa-cert-v01@openssh.com,
ssh-dss-cert-v01@openssh.com,
ecdsa-sha2-nistp256,ecdsa-sha2-nistp384,ecdsa-sha2-nistp521,
ssh-ed25519,ssh-rsa,ssh-dss

接下来,向下滚动至密钥算法(简称密钥交换算法)部分。您将看到支持的算法列表,如下所示:

curve25519-sha256
curve25519-sha256@libssh.org
diffie-hellman-group1-sha1
diffie-hellman-group14-sha1
diffie-hellman-group-exchange-sha1
diffie-hellman-group-exchange-sha256
ecdh-sha2-nistp256
ecdh-sha2-nistp384
ecdh-sha2-nistp521

请注意,此列表可能因发行版本而异。例如,RHEL 8/CentOS 8 支持三种更新更强的额外算法。它的列表如下所示:

curve25519-sha256
curve25519-sha256@libssh.org
diffie-hellman-group1-sha1
diffie-hellman-group14-sha1
diffie-hellman-group14-sha256
diffie-hellman-group16-sha512
diffie-hellman-group18-sha512
diffie-hellman-group-exchange-sha1
diffie-hellman-group-exchange-sha256
ecdh-sha2-nistp256
ecdh-sha2-nistp384
ecdh-sha2-nistp521

接下来,您将看到默认启用的算法列表:

curve25519-sha256,curve25519-sha256@libssh.org,
ecdh-sha2-nistp256,ecdh-sha2-nistp384,ecdh-sha2-nistp521,
diffie-hellman-group-exchange-sha256,
diffie-hellman-group14-sha1,
diffie-hellman-group1-sha1

该列表也可能因不同的 Linux 发行版而异。(不过,在这种情况下,CentOS 7 和 CentOS 8 没有区别。)

最后,我们有媒体访问控制算法。CentOS 7 上启用算法的默认列表如下所示:

umac-64-etm@openssh.com,umac-128-etm@openssh.com,
hmac-sha2-256-etm@openssh.com,hmac-sha2-512-etm@openssh.com,
hmac-sha1-etm@openssh.com,
umac-64@openssh.com,umac-128@openssh.com,
hmac-sha2-256,hmac-sha2-512,hmac-sha1,
hmac-sha1-etm@openssh.com

要查看您的特定系统支持的算法列表,请查看该机器的sshd_config手册页或执行以下ssh -Q命令:

ssh -Q cipher
ssh -Q key
ssh -Q kex
ssh -Q mac

当您查看/etc/ssh/sshd_config文件时,您不会看到任何配置这些算法的行。这是因为默认的算法列表是硬编码到 SSH 守护程序中的。您唯一一次配置这些选项是如果您想启用一个未启用的算法或者禁用一个已启用的算法。在此之前,让我们扫描一下我们的系统,看看启用了什么,看看扫描仪是否能提供任何建议。

扫描已启用的 SSH 算法

我们有两种扫描 SSH 服务器的好方法。如果您的服务器可以通过互联网访问,您可以访问位于https://sshcheck.com/的 SSHCheck 站点。

然后,只需输入服务器的 IP 地址或主机名。如果您已经从默认端口22更改了端口,请输入端口号。扫描完成后,您将看到已启用算法的列表,以及启用或禁用哪些算法的建议。

如果您要扫描的机器无法从互联网上访问,或者您更愿意使用本地扫描工具,您可以安装ssh_scan。让我们现在就开始动手练习吧。我会边走边解释一切。

动手实验–安装和使用 ssh_scan

在本实验中,您可以使用您的 Ubuntu 机器或您的 CentOS 机器。让我们开始吧:

  1. ssh_scan不在我们任何一个 Linux 发行版的存储库中。它是用 Ruby 语言编写的,包装成 Ruby 宝石。首先,我们需要安装rubygem软件包。在 Ubuntu 上,执行以下操作:
sudo apt update
sudo apt install ruby gem

在 CentOS 7 上,执行以下操作:

sudo yum install ruby gem

在 CentOS 8 上,执行以下操作:

sudo dnf install ruby gem
  1. 使用以下命令安装ssh_scan宝石:
sudo gem install ssh_scan
  1. 在所有情况下,ssh_scan可执行文件将被安装在/usr/local/bin/目录中。CentOS 的一个长期怪癖是,如果你使用sudo在那个目录中调用一个命令,系统将找不到它,即使这个目录在根用户的 PATH 设置中。解决方法是在/usr/bin/目录中创建一个到ssh_scan的符号链接。仅在 CentOS 上,请执行以下操作:
sudo ln -s /usr/local/bin/ssh_scan /usr/bin/ssh_scan
  1. ssh_scan没有手册页。要查看命令选项列表,请使用以下命令:
sudo ssh_scan -h
  1. 扫描您在前面的实验中创建和配置的服务器虚拟机。用你自己的 IP 地址代替我在这里使用的地址。注意屏幕输出是如何采用 JSON 格式的。此外,请注意,即使您尚未在扫描仪机器上创建密钥对,扫描仍可在禁用用户名/密码身份验证的机器上运行(但当然,您将无法从扫描仪机器登录):
sudo ssh_scan -t 192.168.0.7
  1. 重复扫描,但这一次,将输出保存到一个.json文件,如下所示:
sudo ssh_scan -t 192.168.0.7 -o ssh_scan-7.json
  1. 您可以在普通的文本编辑器或寻呼机中打开 JSON 文件,但是如果您在网络浏览器中打开它,它会看起来更好。将文件传输到具有桌面界面的机器上,并在首选网络浏览器中打开它。应该是这样的:

  1. 您将看到所有已启用算法的完整列表。在底部,您将看到关于应该启用还是禁用哪些算法的建议。由于ssh_scan是一个 Mozilla 基金会的项目,它使用 Mozilla 自己的建议作为其政策指南。这些与 NIST 这样的机构所推荐的不同。因此,你需要将你的结果与适用于你的环境的标准进行比较,比如 NIST 的 CNSA 标准,以确保你启用或禁用了正确的东西。
  2. 在你的主机或带有桌面界面的虚拟机上,访问网站。在搜索窗口中输入ssh,观察出现的面向互联网的 SSH 服务器列表。点击不同的 IP 地址,直到你找到一个运行在默认端口22上的而不是的 SSH 服务器。观察该设备的已启用算法列表。
  3. 扫描设备,使用-p开关扫描不同的端口,如下所示:
sudo ssh_scan -t 178.60.214.30 -p 222 -o ssh_scan-178-60-214-30.json

请注意,除了您在 Shodan 上看到的已启用算法列表之外,您现在还有一个弱算法列表,该设备的所有者需要禁用这些算法。

  1. 将这个扫描仪和这个服务器虚拟机放在手边,因为在禁用一些算法后,我们将再次使用它们。

您已经到达了实验室的终点–祝贺您!

好吧。让我们禁用一些破旧不堪的东西。

禁用弱 SSH 加密算法

ssh_scan工具非常俏皮,非常方便,但是它确实有一个小缺点。它很好地向您展示了在远程机器上启用了哪些加密算法,但是您不能相信它关于启用或禁用什么的建议。问题是 Mozilla 基金会创建这个工具是为了满足他们自己的内部需求,而不是为了符合 FIPS 或 NIST·CNSA 的标准。它的不良建议的一个很好的例子是它告诉你启用任何 192 位算法。如果您想让您的服务器符合公认的最佳安全实践,这是一个很大的禁忌。因此,使用该工具的最佳方式是运行扫描,然后将结果与 NIST·CNSA 或 FIPS 推荐的结果进行比较。然后,相应地禁用或启用算法。

可用算法的列表因 Linux 发行版而异。为了使事情不那么混乱,我将在这一部分介绍两个实际操作过程。一个是针对 Ubuntu 18.04 的,一个是针对 CentOS 7 的。CentOS 8 有自己独特的做生意方式,所以我把它留到下一节。

动手实验–禁用弱 SSH 加密算法–Ubuntu 18.04

在本实验中,您将需要一直用作扫描仪的虚拟机,以及另一个要扫描和配置的 Ubuntu 18.04 虚拟机。让我们开始吧:

  1. 如果您还没有这样做,请扫描 Ubuntu 18.04 虚拟机,并将输出保存到文件中:
sudo ssh_scan -t 192.168.0.7 -o ssh_scan-7.json
  1. 在目标 Ubuntu 18.04 VM 上,在首选文本编辑器中打开/etc/ssh/sshd_config文件。在文件的顶部,找到这两行:
# Ciphers and keying
#RekeyLimit default none
  1. 在这两行下面,插入这三行:
Ciphers -aes128-ctr,aes192-ctr,aes128-gcm@openssh.com

KexAlgorithms ecdh-sha2-nistp384

MACs -hmac-sha1-etm@openssh.com,hmac-sha1,umac-64-etm@openssh.com,umac-64@openssh.com,umac-128-etm@openssh.com,umac-128@openssh.com,hmac-sha2-256-etm@openssh.com,hmac-sha2-256

CiphersMACs行中,您可以看到前面的-符号禁用的算法的逗号分隔列表。(您只需要一个-即可禁用列表中的所有算法。)在KexAlgorithms线,没有-标志。这意味着该行中列出的算法是唯一启用的算法。

  1. 保存文件并重新启动 SSH 守护程序。验证它是否正确启动:
sudo systemctl restart ssh
sudo systemctl status ssh
  1. 再次扫描 Ubuntu 18.04 虚拟机,将输出保存到不同的文件:
sudo ssh_scan -t 192.168.0.7 -o ssh_scan-7-modified.json
  1. 在扫描仪 VM 上,使用diff比较两个文件。您应该看到比以前更少的算法:
diff -y ssh_scan_results-7.json ssh_scan_results-7-modified.json

The sharp-eyed among you will notice that we left one Cipher that isn't on the NIST CNSA list.  chacha20-poly1305@openssh.com is a lightweight algorithm that's good for use with low-powered, hand-held devices. It's a good, strong algorithm that can replace the venerable Advanced Encryption Standard (AES) algorithm, but with higher performance. However, if you have to remain 100% compliant with the NIST CNSA standard, then you might have to disable it.

您已经到达了实验室的终点–祝贺您!

接下来,让我们使用 CentOS 7。

动手实验–禁用弱 SSH 加密算法–CentOS 7

当您开始使用 CentOS 7 时,您会注意到两件事:

  • 启用更多算法:CentOS 7 上的默认 SSH 配置启用的算法比 Ubuntu 18.04 多很多。这包括一些你真的不想再看到的非常古老的东西。我说的是河豚和 3DES 之类的东西,早就应该退役了。
  • 一种不同的配置技术:在 CentOS 上,在你想要禁用的算法列表前放置一个-符号是不起作用的。相反,您需要列出您想要启用的所有算法。

在本实验中,您将需要一个 CentOS 7 虚拟机和您一直使用的同一扫描虚拟机。考虑到这一点,让我们开始工作:

  1. 扫描 CentOS 7 虚拟机,并将输出保存到文件中:
sudo ssh_scan -t 192.168.0.53 -o ssh_scan-53.json
  1. 在目标 CentOS 7 VM 上,在首选文本编辑器中打开/etc/ssh/sshd_config文件。在文件的顶部,找到这两行:
# Ciphers and keying
#RekeyLimit default none
  1. 在这两行下面,插入这三行:
Ciphers aes256-gcm@openssh.com,aes256-ctr,chacha20-poly1305@openssh.com

KexAlgorithms ecdh-sha2-nistp384

MACs hmac-sha2-256-etm@openssh.com,hmac-sha2-256

正如我之前提到的,对于 CentOS,使用-禁用算法是行不通的。相反,我们必须列出所有我们想启用的算法。

  1. 保存文件并重新启动 SSH 守护程序。验证它是否正确启动:
sudo systemctl restart sshd
sudo systemctl status sshd
  1. 再次扫描 CentOS 7 虚拟机,将输出保存到不同的文件:
sudo ssh_scan -t 192.168.0.53 -o ssh_scan-53-modified.json
  1. 在扫描仪 VM 上,使用diff比较两个文件。您应该看到比以前更少的算法:
diff -y ssh_scan_results-53.json ssh_scan_results-53-modified.json

As before, I left the chacha20-poly1305@openssh.com  algorithm enabled. If you have to remain 100% compliant with the NIST CNSA standard, then you might have to disable it.

您已经到达了实验室的终点–祝贺您!

接下来,让我们看看 RHEL 8 系列附带的一个方便的新功能。

在 RHEL 8/CentOS 8 上设置系统范围的加密策略

第 5 章加密技术中,我们简要介绍了如何在 CentOS 8 上设置系统范围的加密策略。有了这个全新的功能,您不再需要为每个单独的守护进程配置加密策略。相反,您只需运行几个简单的命令,多个守护程序的策略就会立即改变。要查看覆盖了哪些守护程序,请查看/etc/crypto-policies/back-ends/目录。以下是部分内容:

[donnie@localhost back-ends]$ ls -l
total 0
. . .
. . .
lrwxrwxrwx. 1 root root 46 Sep 24 18:17 openssh.config -> /usr/share/crypto-policies/DEFAULT/openssh.txt

lrwxrwxrwx. 1 root root 52 Sep 24 18:17 opensshserver.config -> /usr/share/crypto-policies/DEFAULT/opensshserver.txt

lrwxrwxrwx. 1 root root 49 Sep 24 18:17 opensslcnf.config -> /usr/share/crypto-policies/DEFAULT/opensslcnf.txt

lrwxrwxrwx. 1 root root 46 Sep 24 18:17 openssl.config -> /usr/share/crypto-policies/DEFAULT/openssl.txt
[donnie@localhost back-ends]$

如您所见,该目录包含指向文本文件的符号链接,这些文本文件包含关于为DEFAULT配置启用或禁用哪些算法的指令。向上一级,在/etc/crypto-policies目录中,有config文件。打开它,您会看到这是设置系统范围配置的地方。它还包含对各种可用模式的解释:

# * LEGACY: Ensures maximum compatibility with legacy systems (64-bit
# security)
#
# * DEFAULT: A reasonable default for today's standards (112-bit security).
#
# * FUTURE: A level that will provide security on a conservative level that is
# believed to withstand any near-term future attacks (128-bit security).
#
# * FIPS: Policy that enables only FIPS 140-2 approved or allowed algorithms.
#
# After modifying this file, you need to run update-crypto-policies
# for the changes to propagate.
#
DEFAULT

用其DEFAULT配置扫描该虚拟机,显示相当多的较旧算法仍处于启用状态。要摆脱它们,我们可以切换到FUTURE模式或FIPS模式。

为了向您展示这是如何工作的,让我们用另一个实验室来弄脏我们的手。

动手实验–在 CentOS 8 上设置加密策略

从全新的 CentOS 8 虚拟机和您一直使用的扫描虚拟机开始。现在,按照以下步骤操作:

  1. 在 CentOS 8 虚拟机上,使用update-crypto-policies实用程序验证其是否在DEFAULT模式下运行:
sudo update-crypto-policies --show
  1. 在其DEFAULT配置中扫描 CentOS 8 虚拟机,并将输出保存到文件中:
sudo ssh_scan -t 192.168.0.161 -o ssh_scan-161.json
  1. 在 CentOS 8 虚拟机上,将系统范围的加密策略设置为FUTURE并重新启动虚拟机:
sudo update-crypto-policies --set FUTURE
sudo shutdown -r now
  1. 在扫描仪虚拟机上,在文本编辑器中打开~/.ssh/known_hosts文件。删除先前为 CentOS 8 虚拟机创建的条目并保存文件。(我们必须这样做,因为由于新的策略,CentOS 8 VM 上的公钥指纹将发生变化。)

  2. 再次扫描 CentOS 8 虚拟机,将输出保存到不同的文件:

sudo ssh_scan -t 192.168.0.161 -o ssh_scan_results-161-FUTURE.json
  1. 比较两个输出文件。您现在应该看到比以前更少的启用算法。
  2. 查看/etc/crypto-policies/back-ends/目录中的文件:
ls -l /etc/crypto-policies/back-ends/

您现在会看到符号链接指向FUTURE目录中的文件。

  1. 要设置FIPS模式,您需要使用另一个实用程序,因为update-crypto-policies实用程序没有安装FIPS模式所需的额外模块。首先,确认系统没有处于FIPS模式:
sudo fips-mode-setup --check

您应该会看到一条关于没有安装 FIPS 模块的消息。

  1. 启用FIPS模式,然后重启:
sudo fips-mode-setup --enable
sudo shutdown -r now
  1. 验证虚拟机现在处于FIPS模式:
sudo fips-mode-setup --check
  1. 再次扫描 CentOS 虚拟机,将输出保存到新文件中:
sudo ssh_scan -t 192.168.0.161 -o ssh_scan_results-161-FIPS.json
  1. 比较三个输出文件,并注意启用算法的差异。
  2. 查看/etc/crypto-policies/back-ends/目录的内容。请注意,符号链接现在指向 FIPS 目录中的文件。
ls -l /etc/crypto-policies/back-ends/

In this demo, we set the FUTURE mode first, and then we set the FIPS mode. Keep in mind that, in real life, you won't do both. Instead, you'll do either one or the other.

您已经到达了实验室的终点–祝贺您!

您现在知道如何配置 SSH,只使用最现代、最安全的算法。接下来,让我们看看日志。

配置更详细的日志记录

在其默认配置中,只要有人通过 SSH、SCP 或 SFTP 登录,SSH 就已经创建了日志条目。在 Debian/Ubuntu 系统中,条目在/var/log/auth.log文件中创建。在红帽/CentOS 系统上,条目在/var/log/secure文件中创建。无论哪种方式,日志条目看起来都像这样:

Oct  1 15:03:23 donnie-ca sshd[1141]: Accepted password for donnie from 192.168.0.225 port 54422 ssh2

Oct  1 15:03:24 donnie-ca sshd[1141]: pam_unix(sshd:session): session opened for user donnie by (uid=0)

打开sshd_config手册页,向下滚动至LogLevel项。在这里,您将看到为记录 SSH 消息提供不同详细级别的各种设置。级别如下:

  • QUIET
  • FATAL
  • ERROR
  • INFO
  • VERBOSE
  • DEBUGDEBUG1
  • DEBUG2
  • DEBUG3

通常情况下,我们只关心其中的两个INFOVERBOSEINFO是默认设置,而VERBOSE是我们在正常情况下唯一会使用的另一个设置。各种DEBUG级别可能对故障排除有用,但手册页警告我们,在生产设置中使用DEBUG会侵犯用户隐私。

让我们继续,把我们的手弄脏,只是为了感受不同级别记录的内容。

动手实验–配置更详细的 SSH 日志记录

对于本实验,请使用您在之前实验中使用的虚拟机。这样,您将更好地了解完整的sshd_config文件在完全锁定时应该是什么样子。通过 SSH 远程登录到目标虚拟机,并执行以下步骤:

  1. 打开主日志文件,向下滚动到您看到因登录而创建的条目的位置。观察它说什么,然后用更少的 Ubuntu 退出:
sudo less /var/log/auth.log

对于 CentOS:

sudo less /var/log/secure
  1. 正如我之前提到的,您永远不希望在 SSH 日志级别设置为任何DEBUG级别的情况下运行生产机器。但是,为了让您可以看到它记录了什么,现在将您的机器设置为DEBUG。在您最喜欢的文本编辑器中打开/etc/ssh/sshd_config文件。找到下面这句话:
#LogLevel INFO

将其更改为以下内容:

LogLevel DEBUG3
  1. 保存文件后,重新启动 SSH。在 Ubuntu 上,执行以下操作:
sudo systemctl restart ssh

在 CentOS 上,执行以下操作:

sudo systemctl restart sshd
  1. 注销 SSH 会话,然后重新登录。查看系统日志文件,查看新登录的新条目。
  2. 打开/etc/ssh/sshd_config文件进行编辑。将LogLevel DEBUG3线改为如下:
LogLevel VERBOSE
  1. 保存文件后,重新启动 SSH 守护程序。注销 SSH 会话,重新登录,并查看系统日志文件中的条目。

The main benefit of VERBOSE mode is that it will log the fingerprints of any key that was used to log in. This can be a big help with key management.

您已经到达了实验室的终点–祝贺您!

好吧。到目前为止,您已经看到了如何在系统日志中获取关于 SSH 登录的更多信息。接下来,让我们谈谈访问控制。

使用白名单和 TCP 包装器配置访问控制

我们已经通过要求客户端通过密钥交换而不是用户名和密码进行身份验证很好地锁定了一些东西。当我们禁止密码认证时,坏人可以对我们进行暴力密码攻击,直到奶牛回家,这对他们没有任何好处。(虽然,事实上,一旦他们发现密码验证已经被禁用,他们就会放弃。)作为额外的安全措施,我们还可以设置几个访问控制机制,只允许某些用户、组或客户端机器登录 SSH 服务器。这两种机制如下:

  • sshd_config文件中的白名单
  • TCP 包装器,通过/etc/hosts.allow/etc/hosts.deny文件

好吧,你现在是说,*但是防火墙呢?这不是我们可以使用的第三种机制吗?*是的,你是对的。但是,我们已经在第 3 章用防火墙保护您的服务器-第 1 部分第 4 章用防火墙保护您的服务器-第 2 部分中介绍了防火墙,因此我在此不再重复。但是,无论如何,这是控制访问服务器的三种方法。如果你真的想的话,你可以同时使用这三种方法,也可以一次只使用其中一种。(这真的取决于你有多偏执。)

There are two competing philosophies about how to do access control. With blacklists, you specifically prohibit access by certain people or machines. That's difficult to do because the list could get very long, and you still won't block everybody that you need to block. The preferred and easier method is to use whitelists, which specifically allow access by certain people or machines.

首先,让我们通过动手实验来看看如何在sshd_config内创建白名单。

在 sshd _ config 中配置白名单

您可以在sshd_config内设置的四个访问控制指令如下:

  • DenyUsers
  • AllowUsers
  • DenyGroups
  • AllowGroups

对于每个指令,您可以指定多个用户名或组名,并用空格分隔。此外,这四个指令按照我在这里列出的顺序进行处理。换句话说,如果用户同时被列在DenyUsersAllowUsers指令中,则DenyUsers优先。如果用户与DenyUsers一起列出,并且是与AllowGroups一起列出的组的成员,则DenyUsers再次优先。为了演示这一点,让我们完成一个实验。

实验操作–在 sshd _ config 中配置白名单

本实验将在您的任何虚拟机上运行。请遵循以下步骤:

  1. 在要配置的虚拟机上,为弗兰克、查理和玛吉创建用户帐户。在 Ubuntu 上,执行以下操作:
sudo adduser frank
. . .

在 CentOS 上,执行以下操作:

sudo useradd frank
sudo passwd frank
. . .
  1. 创建webadmins组,并在其中添加弗兰克:
sudo groupadd webadmins
sudo usermod -a -G webadmins frank
  1. 从您的主机或另一个虚拟机,让这三个用户登录。然后,将它们注销。

  2. 在你喜欢的文本编辑器中打开/etc/ssh/sshd_config文件。在文件的底部,添加一个带有自己用户名的AllowUsers行,如下所示:

AllowUsers donnie
  1. 然后,重新启动 SSH 服务,并验证它是否已正确启动:
For Ubuntu:
sudo systemctl restart ssh
sudo systemctl status ssh

For CentOS:
sudo systemctl restart sshd
sudo systemctl status sshd
  1. 重复第 3 步。这一次,这三只小猫应该无法登录。在文本编辑器中打开/etc/ssh/sshd_config文件。这一次,在文件底部为webadmins组添加一个AllowGroups行,如下所示:
AllowGroups webadmins
  1. 重新启动 SSH 服务,并验证它是否正确启动。

从您的主机或另一个虚拟机,让 Frank 尝试登录。你会看到,即使他是webadmins组的成员,他仍然会被拒绝。那是因为有你自己用户名的AllowUsers行优先。

  1. 在文本编辑器中打开sshd_config,删除在步骤 4 中插入的AllowUsers行。重新启动 SSH 服务,并验证它是否正确启动。
  2. 尝试登录您自己的帐户,然后尝试登录所有其他用户的帐户。你现在应该看到弗兰克是唯一被允许登录的人。其他用户现在登录虚拟机的唯一方式是从虚拟机的本地控制台登录。
  3. 在虚拟机的本地控制台登录您自己的帐户。从sshd_config中删除AllowGroups行,重新启动 SSH 服务。

您已经到达了实验室的终点–祝贺您!

您刚刚看到了如何使用 SSH 守护程序自己的配置文件在守护程序级别配置白名单。接下来,我们将研究在网络级别配置白名单。

使用 TCP 包装器配置白名单

这是一个奇怪的名字,但是一个简单的概念。TCP 包装器——单数,而不是复数——监听传入的网络连接,并允许或拒绝连接请求。白名单和黑名单配置在/etc/hosts.allow文件和/etc/hosts.deny文件中。这两个文件一起工作。如果您在hosts.allow创建白名单,但没有向hosts.deny添加任何内容,则不会阻止任何内容。这是因为 TCP Wrappers 首先会咨询hosts.allow,如果它在那里找到了一个白名单项,它就会跳过在hosts.deny中查找。如果连接请求是针对未列入白名单的东西,TCP Wrappers 会咨询hosts.allow,发现该连接请求的来源没有什么,然后咨询hosts.deny。如果hosts.deny中没有,连接请求仍然会通过。所以,配置hosts.allow之后,还得配置hosts.deny才能屏蔽任何东西。

Something that I didn't know until I sat down to write this section is that the Red Hat folk have stripped TCP Wrappers from RHEL 8 and its offspring. So, if you decide to practice with the techniques that I present here, you can do so with either your Ubuntu or CentOS 7 VMs, but not on your CentOS 8 VM. (The Red Hat folk now recommend doing access control via firewalld, rather than TCP Wrappers.)

You can read about it here: https://access.redhat.com/solutions/3906701.

(You'll need a Red Hat account to read the whole article. If you don't need to pay for Red Hat support, you can open a free-of-charge developers' account.)

现在,有一件事非常重要。总是,总是,在配置hosts.deny之前先配置hosts.allow。这是因为一旦您保存了其中的任何一个文件,新的配置就会立即生效。因此,如果您在远程登录时在hosts.deny中配置阻止规则,您的 SSH 连接将在您保存文件后立即中断。返回的唯一方法是进入服务器机房,从本地控制台重新配置。你最好习惯于总是先配置hosts.allow的想法,即使你是在本地控制台工作。那样的话,你会一直确信。(然而,令人惊讶的是,还有其他的 TCP 包装教程告诉你先配置hosts.deny。这些家伙在想什么?)

你可以用 TCP Wrappers 做一些相当花哨的小把戏,但现在,我只想让事情变得简单。所以,让我们看看一些最常用的配置。

要将单个 IP 地址列入白名单,请在/etc/hosts.allow文件中放入一行如下内容:

SSHD: 192.168.0.225

然后,将这一行放入/etc/hosts.deny文件:

SSHD: ALL

现在,如果你试图从hosts.allow中列出的 IP 地址以外的任何地方登录,你将被拒绝访问。

您也可以在hosts.allow中列出多个 IP 地址或网络地址。有关如何操作的详细信息,请参见hosts.allow手册页。

正如我之前提到的,您可以使用 TCP Wrappers 做一些花哨的事情。但是,既然红帽人已经弃用了它,你最好还是设置防火墙规则。另一方面,只要您需要快速配置访问控制规则,TCP 包装器就可以派上用场。

配置自动注销和安全横幅

最佳安全实践要求人们在离开办公桌前注销电脑。当管理员使用他或她的隔间计算机远程登录敏感服务器时,这一点尤其重要。默认情况下,SSH 允许一个人永远保持登录状态而不会抱怨。但是,您可以将其设置为自动注销空闲用户。我们将看两个快速的方法。

为本地和远程用户配置自动注销

第一种方法将自动注销在本地控制台或通过 SSH 远程登录的空闲用户。进入/etc/profile.d/目录,创建autologout.sh文件,内容如下:

TMOUT=100
readonly TMOUT
export TMOUT

这将超时值设置为 100 秒。(TMOUT是一个设置超时值的 Linux 环境变量。)

为每个人设置可执行权限:

sudo chmod +x autologout.sh

注销,然后重新登录。然后,让虚拟机闲置。100 秒后,您应该会看到虚拟机在登录提示符下返回。但是,请注意,如果在您创建此文件时有任何用户已经登录,新的配置将不会对他们生效,直到他们注销然后重新登录。

在 sshd _ config 中配置自动注销

第二种方法只注销通过 SSH 远程登录的用户。不创建/etc/profile.d/autologout.sh文件,而是在/etc/ssh/sshd_config文件中查找这两行:

#ClientAliveInterval 0
#ClientAliveCountMax 3

将它们更改为以下内容:

ClientAliveInterval 100
ClientAliveCountMax 0

然后,重新启动 SSH 服务以使更改生效。

I've been using 100 seconds for the timeout value in both of these examples. However, you can set the timeout value to suit your own needs.

您现在知道如何自动注销您的用户。现在,让我们看看设置安全横幅。

创建登录前安全横幅

第 2 章保护用户帐户中,我向您展示了如何创建一条安全消息,该消息在用户登录后显示*。您可以通过在/etc/motd文件中插入一条消息来实现。但是,仔细想想,大家在登录之前看到一个安全横幅不是更好吗?你可以通过sshd_config做到这一点。*

首先,我们创建/etc/ssh/sshd-banner文件,内容如下:

Warning!!  Authorized users only.  All others will be prosecuted.

/etc/ssh/sshd_config文件中,查找这一行:

#Banner none

将其更改为:

Banner /etc/ssh/sshd-banner

像往常一样,重新启动 SSH 服务。现在,无论谁远程登录,都会看到如下内容:

[donnie@fedora-teaching ~]$ ssh donnie@192.168.0.3
Warning!!  Authorized users only.  All others will be prosecuted.
donnie@192.168.0.3's password: 
Welcome to Ubuntu 18.04.3 LTS (GNU/Linux 4.15.0-64-generic x86_64)
. . .
. . .

那么,这个横幅能保证你的系统安全吗?不,但如果你必须把案子拿到法庭上,这可能会有用。有时候,向法官和陪审团证明入侵者知道他们要去不属于他们的地方是很重要的。

现在,您已经知道如何设置安全横幅和自动注销,让我们看看一些杂七杂八的设置,不适合任何一个类别。

配置其他杂项安全设置

我们的 SSH 配置比以前安全多了,但是我们仍然可以做得更好。这里有一些小技巧,你可能在其他地方没有见过。

禁用 X11 转发

当您以正常方式 SSH 到服务器时,就像我们一直在做的那样,您只能运行文本模式的程序。如果你试图远程运行任何基于图形用户界面的程序,比如火狐,你会得到一条错误消息。但是,当您打开几乎所有 Linux 发行版的sshd_config文件时,您会看到下面这一行:

X11Forwarding yes

这意味着通过正确的选项开关,您可以远程运行基于图形用户界面的程序。假设您正在登录一台安装了图形桌面环境的机器,您可以在登录时使用-Y-X选项,如下所示:

ssh -X donnie@192.168.0.12
or
ssh -Y donnie@192.168.0.12

这里的问题是,在大多数 Linux 和 Unix 系统上为图形桌面环境提供动力的 X11 协议存在一些安全弱点,使得远程使用它有些危险。坏人有办法利用它来危害整个系统。最好的办法是通过将X11Forwarding线更改为以下内容来禁用它:

X11Forwarding no

像往常一样,重新启动 SSH 服务,使其在新配置中被读取。

既然知道了 X11 转发,那我们就挖一些隧道吧。

禁用 SSH 隧道

SSH 隧道,或者有时叫做 SSH 端口转发,是一种保护非安全协议的便捷方式。例如,通过 SSH 隧道传输普通的 HTTP,您可以以安全的方式访问不安全的网站。为此,您需要执行以下操作:

sudo ssh -L 80:localhost:80 donnie@192.168.0.12

我不得不在这里使用sudo,因为端口1024以下的所有网络端口都是特权端口。如果我要改变网络服务器的配置来监听非特权的高号码端口,我就不需要sudo

现在,为了以安全的方式连接到该站点,我只需在本地计算机上打开 web 浏览器并键入以下 URL:

http://localhost

是的,通过输入localhost来访问远程机器似乎很奇怪,但这是我用 SSH 登录时使用的指示器。我本可以用另一个名字,但是localhost是你传统上在 SSH 教程中看到的名字,所以我在这里照着做。现在,只要我注销 SSH 会话,我与 web 服务器的连接就会中断。

尽管这听起来是个好主意,但它实际上造成了一个安全问题。假设您的公司防火墙被设置为阻止人们回家并远程访问他们公司的工作站。这是件好事,对吗?现在,假设公司防火墙必须允许出站 SSH 连接。用户可以创建一个 SSH 隧道,从他们的公司工作站到另一个位置的计算机,然后到那个位置,创建一个反向隧道回到他们的公司工作站。因此,如果无法在防火墙上阻止传出的 SSH 流量,那么您最好禁用 SSH 隧道。在您的sshd_config文件中,确保您有如下几行:

AllowTcpForwarding no
AllowStreamLocalForwarding no
GatewayPorts no
PermitTunnel no

像往常一样重新启动 SSH 服务。现在,端口隧道将被禁用。

现在您已经知道如何禁用 SSH 隧道,让我们来谈谈更改默认端口。

更改默认 SSH 端口

默认情况下,SSH 监听端口22 /TCP。如果你已经有一段时间了,你肯定已经看到了很多关于使用其他端口是多么重要的文档,以便让坏人更难找到你的 SSH 服务器。但是,我必须说,这个概念有点争议。

首先,如果启用密钥身份验证并禁用密码身份验证,则更改端口的价值有限。当一个扫描机器人找到你的服务器,看到密码认证被禁用,它就会消失,不会再打扰你。其次,如果你要换端口,坏人的扫描工具还是能找到的。不信就去 Shodan.io 搜索ssh。在这个例子中,有人认为他们通过切换到端口2211是聪明的:

是的,自作聪明。这并没有很好地隐藏事情,现在,是吗?

另一方面,安全专家丹尼尔·米斯勒说,改变端口仍然是有用的,以防有人试图利用零日漏洞攻击 SSH。他最近公布了自己做的一个非正式实验的结果,在这个实验中,他设置了一个公共服务器,监听到端口22和端口24的 SSH 连接,并观察到每个端口的连接尝试次数。他说,仅在一个周末,就有 18000 条线路连接到 T2 港,只有 5 条连接到 T3 港。但是,虽然他没有明确表示,似乎他没有启用密码验证。为了获得真正科学准确的结果,他需要在禁用密码验证的情况下进行同样的研究。他还需要在为端口22或端口24启用 SSH 的独立服务器上进行研究,而不是在单台机器上同时启用这两个端口。我的预感是,当扫描机器人发现端口22是打开的时候,他们根本懒得扫描其他任何打开的 SSH 端口。

You can read about his experiment here: https://danielmiessler.com/study/security-by-obscurity/.

无论如何,如果你确实想改变端口,只需取消sshd_config#Port 22行的注释,将端口号改变为你想要的。

接下来,我们来谈谈密钥管理。

管理 SSH 密钥

之前,我向您展示了如何在本地工作站上创建一对密钥,然后将公钥传输到远程服务器。这允许您在服务器上禁用用户名/密码身份验证,使坏人更难闯入。我们没有解决的唯一问题是,公钥进入了用户自己主目录中的authorized_keys文件。因此,用户可以手动向文件中添加额外的密钥,这将允许用户从授权位置之外的其他位置登录。此外,还有一个问题是在每个用户的主目录中到处都有authorized_keys文件。这使得跟踪每个人的钥匙变得有点困难。

处理这种情况的一种方法是将每个人的authorized_keys文件移动到一个中心位置。让我们带上维基,我坚实的灰色小猫。管理员在服务器上创建了一个她需要访问的帐户,并允许她在禁用密码身份验证之前创建并向其传输密钥。因此,Vicky 现在在服务器的主目录中有她的authorized_keys文件,正如我们在这里看到的:

vicky@ubuntu-nftables:~$ cd .ssh
vicky@ubuntu-nftables:~/.ssh$ ls -l
total 4
-rw------- 1 vicky vicky 233 Oct  3 18:24 authorized_keys
vicky@ubuntu-nftables:~/.ssh$

Vicky 拥有这个文件,她对它有读写权限。所以,即使管理员禁用密码认证后,她无法正常向其传输其他密钥,她仍然可以手动传输密钥文件,并手动编辑authorized_keys文件以包含它们。为了挫败她的努力,我们无畏的管理员将在/etc/ssh/目录中创建一个目录来保存每个人的authorized_keys文件,如下所示:

sudo mkdir /etc/ssh/authorized-keys

我们无畏的管理员的完全管理权限允许他登录到根用户的外壳,这允许他们进入所有其他用户的目录:

donnie@ubuntu-nftables:~$ sudo su -
[sudo] password for donnie: 
root@ubuntu-nftables:~# cd /home/vicky/.ssh
root@ubuntu-nftables:/home/vicky/.ssh# ls -l
total 4
-rw------- 1 vicky vicky 233 Oct 3 18:24 authorized_keys
root@ubuntu-nftables:/home/vicky/.ssh#

下一步是将 Vicky 的authorized_keys文件移动到新位置,将其名称更改为vicky,如下所示:

root@ubuntu-nftables:/home/vicky/.ssh# mv authorized_keys /etc/ssh/authorized-keys/vicky

root@ubuntu-nftables:/home/vicky/.ssh# exit
donnie@ubuntu-nftables:~$

现在,我们有一个难题。这里可以看到,文件仍然属于 Vicky,她同时拥有读写权限。因此,她仍然可以在没有任何管理员权限的情况下编辑文件。删除写权限是行不通的,因为文件属于她,她可以将写权限添加回来。将所有权更改为 root 用户是答案的一部分,但这将阻止 Vicky 读取文件,从而阻止她登录。要查看整个解决方案,让我们看看我已经用自己的authorized_keys文件做了什么:

donnie@ubuntu-nftables:~$ cd /etc/ssh/authorized-keys/
donnie@ubuntu-nftables:/etc/ssh/authorized-keys$ ls -l
total 8
-rw------- 1 vicky vicky 233 Oct 3 18:24 vicky
-rw-r-----+ 1 root root 406 Oct 3 16:24 donnie
donnie@ubuntu-nftables:/etc/ssh/authorized-keys$

你们当中眼尖的人肯定注意到了donnie档的情况。您已经看到,我将所有权更改为根用户,然后添加了一个访问控制列表,如+符号所示。让我们为维基做同样的事情:

donnie@ubuntu-nftables:/etc/ssh/authorized-keys$ sudo chown root: vicky

donnie@ubuntu-nftables:/etc/ssh/authorized-keys$ sudo setfacl -m u:vicky:r vicky 

donnie@ubuntu-nftables:/etc/ssh/authorized-keys$

查看权限设置,我们看到 Vicky 拥有对vicky文件的读取权限:

donnie@ubuntu-nftables:/etc/ssh/authorized-keys$ ls -l 
total 8
-rw-r-----+ 1 root root 406 Oct 3 16:24 donnie
-rw-r-----+ 1 root root 233 Oct 3 18:53 vicky
donnie@ubuntu-nftables:/etc/ssh/authorized-keys$

在此过程中,让我们看看她的访问控制列表:

donnie@ubuntu-nftables:/etc/ssh/authorized-keys$ getfacl vicky
# file: vicky
# owner: root
# group: root
user::rw-
user:vicky:r--
group::---
mask::r--
other::---
donnie@ubuntu-nftables:/etc/ssh/authorized-keys$

Vicky 现在可以读取文件以便登录,但是她不能更改它。

最后一步是重新配置sshd_config文件,然后重启 SSH 服务。在文本编辑器中打开文件,并查找这一行:

#AuthorizedKeysFile     .ssh/authorized_keys .ssh/authorized_keys2

将其更改为:

AuthorizedKeysFile      /etc/ssh/authorized-keys/%u

行尾的%u是一个迷你宏,告诉 SSH 服务寻找一个与登录用户同名的密钥文件。现在,即使用户在他们自己的主目录中手动创建他们自己的authorized_keys文件,SSH 服务也会忽略它们。另一个好处是,如果需要的话,将所有的密钥放在一个地方会让管理员更容易撤销某人的访问权限。

请注意,管理 SSH 密钥的内容比我在这里介绍的要多得多。一个问题是,虽然有一些不同的管理公钥的免费开源软件解决方案,但没有任何管理私钥的解决方案。一个大公司可能在不同的地方有数千甚至数百万的私钥和公钥。那些密钥永远不会过期,所以除非被删除,否则它们将永远存在。如果错误的人获得了私钥,您的整个系统可能会受到损害。虽然我很不想说,但管理 SSH 密钥的最佳选择是采用商业解决方案,例如来自https://www.ssh.com/和赛博方舟的解决方案。

Check out the key management solutions from SSH.com here: https://www.ssh.com/iam/ssh-key-management/. Head here for CyberArk's: https://www.cyberark.com/solutions/by-project/ssh-key-security-management/. Full disclosure: I have no connection with either https://www.ssh.com/ or CyberArk, and receive no payment for telling you about them.

在这里,您已经学习了一些增强服务器安全性的很酷的技巧。现在,让我们看看如何为不同的用户和组创建不同的配置。

为不同的用户和组设置不同的配置

在服务器端,您可以使用Match UserMatch Group指令为某些用户或组设置自定义配置。要了解它是如何完成的,请看/etc/ssh/sshd_config文件最底部的例子。在那里,您将看到以下内容:

# Match User anoncvs
# X11Forwarding no
# AllowTcpForwarding no
# PermitTTY no
# ForceCommand cvs server

当然,这没有影响,因为它被评论出来了,但没关系。以下是我们对用户anoncvs的看法:

  • 他不能做 X11 转发。
  • 他不会做 TCP 转发。
  • 他不会使用指挥终端。
  • 他一登录,就会启动并发版本服务 ( CVS )服务器。通过不使用终端,anoncvs可以启动 CVS 服务器,但不能做其他任何事情。

您可以根据需要为任意多的用户设置不同的配置。您在自定义配置中输入的任何内容都将覆盖全局设置。要为组设置自定义配置,只需将Match User替换为Match Group,并提供组名而不是用户名。

为不同的主机创建不同的配置

为了改变节奏,我们现在来看看客户端。这一次,我们将看一个方便的技巧来帮助减轻登录到需要不同密钥或 SSH 选项的不同服务器的痛苦。你所要做的就是进入自己主目录中的.ssh目录,创建一个config文件。为了演示这一点,假设我们已经为我们的服务器创建了一个 DNS 记录或一个/etc/hosts文件条目,这样我们就不必记住这么多的 IP 地址。

假设我们已经为需要访问的每台服务器创建了一对单独的密钥。在~/.ssh/config文件中,我们可以添加一个类似如下的小节:

Host ubuntu-nftables
 IdentityFile ~/.ssh/unft_id_rsa
 IdentitiesOnly yes
 ForwardX11 yes
 Cipher aes256-gcm@openssh.com

细分如下:

  • IdentityFile:指定该服务器附带的密钥。
  • IdentitiesOnly yes:如果您的会话密钥环中恰好加载了多个密钥,这将强制您的客户端仅使用此处指定的密钥。
  • ForwardX11 yes:我们希望这个客户端使用 X11 转发。(当然,这只有在服务器配置为允许的情况下才会有效。)
  • Cipher aes256-gcm@openssh.com:我们要用这个算法,而只有这个算法,才能执行我们的加密。

要为其他主机创建自定义配置,只需在此文件中为每个主机添加一个小节。

保存文件后,必须将其权限设置更改为600值。如果不这样做,当您尝试登录文件中配置的任何服务器时,您将会得到一个错误。

现在您已经了解了定制配置,让我们来谈谈 SFTP,在那里我们将很好地利用我们刚刚看到的Match Group指令。

为 SFTP 用户建立一个客户环境

安全文件传输协议 ( SFTP )是执行安全文件传输的绝佳工具。有一个命令行客户端,但用户很可能会使用图形客户端,如 FileZilla。网站所有者将网络内容文件上传到网络服务器上适当的内容目录。使用默认的 SSH 设置,任何在 Linux 机器上拥有用户帐户的人都可以通过 SSH 或 SFTP 登录,并且可以浏览服务器的整个文件系统。对于 SFTP 用户,我们真正想要的是阻止他们通过 SSH 登录到命令提示符,并将他们限制在自己指定的目录中。

创建组并配置 sshd _ config 文件

除了用户创建命令略有不同之外,当我们到达动手实验室时,此过程适用于您的任何一台虚拟机。

我们将首先创建一个sftpusers组:

sudo groupadd sftpusers

创建用户帐户并将其添加到sftpusers组。我们将一步完成这两个操作。在您的 CentOS 机器上,创建 Max 帐户的命令如下:

sudo useradd -G sftpusers max

在您的 Ubuntu 机器上,它将如下所示:

sudo useradd -m -d /home/max -s /bin/bash -G sftpusers max

在你喜欢的文本编辑器中打开/etc/ssh/sshd_config文件。找到下面这句话:

Subsystem sftp /usr/lib/openssh/sftp-server

将其更改为以下内容:

Subsystem sftp internal-sftp

此设置允许您禁用特定用户的正常 SSH 登录。

sshd_config文件的底部,添加一个Match Group小节:

Match Group sftpusers
 ChrootDirectory /home
 AllowTCPForwarding no
 AllowAgentForwarding no
 X11Forwarding no
 ForceCommand internal-sftp

这里需要考虑的一个重要问题是ChrootDirectory必须归根用户所有,除了根用户之外的任何人都不能写。当麦克斯登录时,他将在/home目录中,然后必须将cd放入自己的目录中。这也意味着你希望你所有用户的主目录都有限制性的700权限设置,以便让每个人都远离其他人的东西。

保存文件并重新启动 SSH 守护程序。然后,尝试通过普通 SSH 以 Max 身份登录,就为了看看会发生什么:

donnie@linux-0ro8:~> ssh max@192.168.0.8
max@192.168.0.8's password:
This service allows sftp connections only.
Connection to 192.168.0.8 closed.
donnie@linux-0ro8:~>

好吧,所以他不能这么做。现在,让马克斯尝试通过 SFTP 登录,并验证他是否在/home目录中:

donnie@linux-0ro8:~> sftp max@192.168.0.8
max@192.168.0.8's password:
Connected to 192.168.0.8.
drwx------    7 1000     1000         4096 Nov  4 22:53 donnie
drwx------    5 1001     1001         4096 Oct 27 23:34 frank
drwx------    3 1003     1004         4096 Nov  4 22:43 katelyn
drwx------    2 1002     1003         4096 Nov  4 22:37 max
sftp>

现在,让我们看看他试图将cd/home目录中删除:

sftp> cd /etc
Couldn't stat remote file: No such file or directory
sftp>

所以,我们的监狱确实有效。

动手实验–为 sftpusers 组设置 chroot 目录

在本实验中,您可以使用 CentOS 虚拟机或 Ubuntu 虚拟机。您将添加一个组,然后配置sshd_config文件以允许组成员只能通过 SFTP 登录,然后将他们限制在自己的目录中。对于模拟客户端机器,您可以使用您的 macOS 或 Linux 桌面机器的终端,或者您的 Windows 机器上任何可用的 Bash shells。让我们开始吧:

  1. 创建sftpusers组:
sudo groupadd sftpusers
  1. 为 Max 创建一个用户帐户,并将其添加到sftpusers组。在 CentOS 上,执行以下操作:
sudo useradd -G sftpusers max

在 Ubuntu 上,执行以下操作:

sudo useradd -m -d /home/max -s /bin/bash -G sftpusers max
  1. 对于 Ubuntu,确保用户的主目录都被设置为仅具有目录用户的读、写和执行权限。如果不是这样,请执行以下操作:
sudo chmod 700 /home/*
  1. 在首选文本编辑器中打开/etc/ssh/sshd_config文件。找到下面这句话:
Subsystem sftp /usr/lib/openssh/sftp-server

将其更改为以下内容:

Subsystem sftp internal-sftp
  1. sshd_config文件的末尾,添加以下小节:
Match Group sftpusers
 ChrootDirectory /home
 AllowTCPForwarding no
 AllowAgentForwarding no
 X11Forwarding no
 ForceCommand internal-sftp
  1. 重新启动 SSH 守护程序。在 CentOS 上,执行以下操作:
sudo systemctl sshd restart

在 Ubuntu 上,执行以下操作:

sudo systemctl ssh restart
  1. 让 Max 尝试通过普通 SSH 登录,看看会发生什么:
ssh max@IP_Address_of_your_vm
  1. 现在,让马克斯通过 SFTP 登录。一旦他进入,让他尝试从/home目录中cd出来:
sftp max@IP_Address_of_your_vm

您已经到达了实验室的终点–祝贺您!

现在,您已经知道如何安全地配置 SFTP,让我们看看如何安全地共享一个目录。

与 SSHFS 共享一个目录

有几种方法可以在网络上共享目录。在企业设置中,您可以找到网络文件系统 ( NFS )、Samba 和各种分布式文件系统。SSHFS 在企业中的使用并不多,但它仍然可以派上用场。它的美妙之处在于,它的所有网络流量都是默认加密的,不像 NFS 或桑巴。此外,除了安装 SSHFS 客户端程序和创建本地装载点目录之外,它不需要任何超出您已经完成的配置。它对于访问基于云的虚拟专用服务器 ( VPS )上的目录特别方便,因为它允许您只在共享目录中创建文件,而不是使用scpsftp命令来传输文件。如果你准备好了,我们就开始吧。

动手实验–与 SSHFS 共享一个目录

在本实验中,我们将使用两个虚拟机。对于服务器,您可以使用 Ubuntu、CentOS 7 或 CentOS 8。客户端可以是 Ubuntu,也可以是 CentOS 7。(在撰写本文时,CentOS 8 仍然没有我们为此需要安装的客户端软件包。但是,正如我一直说的,当你读到这篇文章的时候,这可能会改变。)我们开始吧:

  1. 为服务器启动一个虚拟机。(这就是您需要为服务器端做的一切。)
  2. 在您将用作客户端的另一个虚拟机上,在您自己的主目录中创建一个装载点目录,如下所示:
mkdir remote
  1. 在客户端虚拟机上,安装 SSHFS 客户端。在 Ubuntu 上,执行以下操作:
sudo apt install sshfs

在 CentOS 7 上,执行以下操作:

sudo yum install fuse-sshfs
  1. 从客户机上,挂载服务器上自己的主目录:
sshfs donnie@192.168.0.10: /home/donnie/remote

Note that if you don't specify a directory to share, the default is to share the home directory of the user account that's being used for logging in.

  1. 使用mount命令验证目录安装是否正确。您应该会在输出的底部看到新的共享挂载:
donnie@ubuntu-nftables:~$ mount
. . .
. . .
donnie@192.168.0.10: on /home/donnie/remote type fuse.sshfs (rw,nosuid,nodev,relatime,user_id=1000,group_id=1004)
  1. cd进入remote目录并创建一些文件。验证它们确实出现在服务器上。
  2. 在服务器虚拟机的本地控制台上,在您自己的主目录中创建一些文件。验证它们是否出现在客户端虚拟机的remote目录中。

您已经到达了实验室的终点–祝贺您!

在本实验中,我刚刚向您展示了如何从远程服务器挂载您自己的主目录。您也可以通过在sshfs命令中指定其他服务器目录来挂载它们。例如,假设我想挂载/maggie_files目录,将~/remote3目录作为我的本地挂载点。(我选择这个名字是因为猫玛吉坐在我面前,我的键盘应该在那里。)只需执行以下操作:

sshfs donnie@192.168.0.53:/maggie_files /home/donnie/remote3

您也可以通过在/etc/fstab文件中添加一个条目,使远程目录在每次启动客户端机器时自动挂载。但是,这通常不是一个好主意。如果在引导客户机时服务器不可用,可能会导致引导过程挂起。

好了,您已经看到了如何使用 SSHFS 创建与共享远程目录的加密连接。现在让我们从 Windows 桌面机器登录到服务器。

从 Windows 桌面远程连接

我知道,我们所有的鹏人都想用 Linux,除了 Linux 什么都不用。但是,在企业环境中,事情并不总是这样。在那里,您很可能不得不从您办公桌上的 Windows 10 台式机上管理您的 Linux 服务器。在第 1 章在虚拟环境中运行 Linux中,我向您展示了如何使用 Cygwin 或新的 Windows 10 外壳远程连接到您的 Linux 虚拟机。您也可以使用这些技术来连接到实际的 Linux 服务器。

但是,一些商店要求管理员使用终端程序,而不是像 Cygwin 这样的成熟的 Bash Shell。通常,这些商店会要求您在 Windows 机器上使用 PuTTY

PuTTY is a free program that you can download from here: https://www.chiark.greenend.org.uk/~sgtatham/putty/latest.html.

安装简单。只需双击安装程序文件并浏览安装程序屏幕:

您可以从 Windows 10 开始菜单打开 PuTTY 用户手册:

连接到远程 Linux 机器很容易。只需输入机器的 IP 地址,然后点击打开:

请注意,这也为您提供了保存会话的选项。因此,如果您必须管理多台服务器,您可以打开 PuTTY,只需单击要连接的服务器的名称,然后单击打开:

如您所见,这比每次需要登录服务器时都必须手动键入ssh命令要方便得多,并且它可以防止您必须记住多个服务器的整个 IP 地址列表。(但是当然,您可以通过为需要管理的每台 Linux 机器创建一个登录 shell 脚本,用 Cygwin 或 Windows 10 shell 完成同样的事情。)

无论哪种方式,您都将在远程机器的 Bash Shell 中结束:

要设置密钥交换身份验证,请使用 PuTTYgen 创建密钥对。唯一的小问题是,您必须通过手动将密钥复制并粘贴到服务器的authorized_keys文件中,将公钥传输到服务器:

我已经向您介绍了 PuTTY 的基本知识。您可以阅读 PuTTY 手册来了解细节。

好了,我想我们对安全外壳套件的讨论到此结束。

摘要

在这一章中,我们已经看到了安全外壳的默认配置并不像我们希望的那样安全,并且我们已经看到了该怎么做。我们已经了解了如何设置基于密钥的身份验证,并且了解了许多可以锁定 SSH 服务器的不同选项。我们还研究了如何禁用弱加密算法,以及 RHEL 8/CentOS 8 上新的全系统加密策略如何让这变得非常容易。在此过程中,我们研究了设置访问控制,以及为不同的用户、组和主机创建不同的配置。在演示了如何将 SFTP 用户限制在他们自己的主目录之后,我们使用 SSHFS 来共享一个远程目录。我们在这一章的最后介绍了一种从 Windows 桌面机登录 Linux 服务器的简便方法。

他们的缺席引人注目的是你可能在其他地方看到推荐的几项技术。端口敲门和 Fail2Ban 是两种流行的技术,可以帮助控制对 SSH 服务器的访问。但是,只有当您允许对 SSH 服务器进行基于密码的身份验证时,才需要它们。如果您设置了基于密钥的身份验证,正如我在这里向您展示的那样,您就不需要增加其他解决方案的复杂性。

在下一章中,我们将深入研究自由访问控制的主题。到时候见。

问题

  1. 以下哪一项是正确的陈述?

a)安全外壳在其默认配置中是完全安全的。 B)允许根用户使用 Secure Shell 通过互联网登录是安全的。 C)安全外壳在其默认配置中是不安全的。 D)使用安全外壳最安全的方法是使用用户名和密码登录。

  1. 为了符合安全外壳的最佳安全实践,您会做以下哪三件事?

a)确保所有用户都使用强密码通过安全外壳登录。 B)让所有用户创建一个公钥/私钥对,并将他们的公钥传输到他们想要登录的服务器。 C)禁用通过用户名/密码登录的功能。 D)确保根用户使用的是强密码。 E)禁用根用户的登录能力。

  1. sshd_config文件中的以下哪一行将导致僵尸网络不扫描您的系统的登录漏洞?

a)。PasswordAuthentication noT4【B】)。PasswordAuthentication yes C)。PermitRootLogin yes D)。PermitRootLogin no

  1. 您如何将 SFTP 的用户限制在他或她自己指定的目录中?

a)确保在该用户的目录上设置了正确的所有权和权限。 B)在sshd_config文件中,禁用该用户通过普通 SSH 登录的能力,并为该用户定义一个chroot目录。 C)用 TCP 包装器定义用户的限制。 D)在服务器上使用全磁盘加密,这样 SFTP 用户只能访问他们自己的目录。

  1. 您会使用以下哪两个命令将您的私有 SSH 密钥添加到您的会话密钥环中?

a)ssh-copy-id B)exec /usr/bin/ssh-agent C)exec /usr/bin/ssh-agent $SHELL D)ssh-agent E)ssh-agent $SHELL F)ssh-add

  1. NIST 推荐算法列表中哪个不是?

a)RSAT3】B)ECDSAT4】C)Ed25519

  1. 以下哪一项是为卡特琳创建自定义配置的正确指令?

a)User Match katelyn B)Match katelyn C)Match Account katelynT6】D)Match User katelyn

  1. 创建~/.ssh/config文件时,该文件的权限值应该是多少?

a)600 B)640 C)644T6】D)700

  1. 以下哪种加密策略提供了 CentOS 8 上最强的加密?

a)遗产 B) FIPS C)违约 D)未来

  1. 以下哪个标准定义了 NIST 当前对加密算法的建议?

a)FIPS 140-2 b)FIPS 140-3 c)CNSA d)套房 b

进一步阅读