OpenSSH 的 101 个用途:第一部分

作者:Mick Bauer

在《偏执企鹅》专栏中,现在是讲故事时间。别担心——这个故事是为您在 LJ 中所期望的那种实际操作内容的序言。事实上,OpenSSH 中有太多可以玩弄的细节,以至于这篇文章将延续到下个月的期刊!

本月我们将介绍 ssh 的背景和架构、如何构建和/或安装 OpenSSH、如何使用 ssh 作为 Telnet 的加密替代品、如何设置一些基本的 ssh 配置选项,以及如何使用 scp 进行加密文件传输。下个月我将介绍 RSA/DSA 身份验证、本地端口转发、远程命令执行以及 ssh/OpenSSH 的其他更高级和极其强大的功能。

为了公正地对待这个出色的软件,我想先谈谈它是如何产生的,以及一些将其带给我们的人。

SSH 的故事

UNIX 最酷的事情之一是,有不止一种而是几种不同的方法可以从远程控制台管理系统。可悲的是,大多数这些方法(Telnet、rsh 和 X,仅举几例)都以明文形式通过网络发送所有内容,包括密码。我们对互联网的依赖以及脚本小子和其他数据包嗅探变态者的激增,使得管理性的明文网络应用程序变得过时。

但是几年前,芬兰超级黑客 Tatu Ylonen 创建了一个令人惊叹的工具,称为安全外壳,或 ssh。 ssh 是一套工具,大致对应于 Sun 的 rsh、rcp 和 rlogin 命令,但有一个非常重要的区别:偏执。 ssh 让您可以使用您选择的自由主义级加密和身份验证方法来完成 rsh、rcp 和 rlogin 所做的一切。但是等等——有一个问题——ssh 版本 1 严重依赖 RSA,这是一种优秀的,但正如我们所说,受限制(专利)的技术,它要求任何使用它的应用程序都必须获得许可(付费),除非它用于非商业环境(即使在非商业用途中,ssh 的合法性也一直很模糊,尤其是在美国)。但是等等,您说,RSA 的美国专利已于 2000 年 9 月到期——问题解决了,对吗? 几乎:Tatu 必须谋生,因此当 RSA 变得不那么受限制时,ssh 本身变得更加受限制,因为他的公司 F-Secure 收紧了许可缰绳。事实上,从 ssh 2.0 版开始,未经许可/免费的商业用途(无论 RSA 问题如何)不再被允许。尽管 Tatu 真诚地希望 ssh 成为互联网标准,但其中一项要求是至少有一个免费的实现可用。

Theo de Raadt 和 OpenBSD 团队加入了进来。当然,OpenBSD 是 NetBSD 的超安全分支,NetBSD 是 BSD UNIX 的免费版本。 Theo 和我们在 OpenBSD 项目中的开源兄弟们希望在 OpenBSD 2.6 中包含 ssh,但对 ssh 的各种限制持谨慎态度。当他们得知瑞典程序员 Bjoern Groenvall 发布了 ssh 的改进版本 1.2.12(Ylonen 的 ssh 的最后一个完全免费的,除了 RSA 版本)时,OpenBSD 的家伙们迅速开始工作,更新并调整它以适应更广泛的受众。 OpenSSH 从那时起就一直是 OpenBSD 的一部分,现在可以移植到大多数版本的 UNIX。

OpenSSH 基于 Groenvall 的工作(他的版本称为 OSSH,仍然可用),增加了对更高版本 ssh 协议的支持,并以模块化的方式模块化了其加密机制,从而可以在没有任何专利算法的情况下编译 OpenSSH(即,不支持依赖 RSA 的 ssh v.1 协议)。 OpenBSD 团队带来的另一个创新是将 OpenSSH 代码库分支为“干净”版本,该版本尽可能保持简单和平台独立,以及“可移植”版本,该版本可以为除 OpenBSD 之外的各种 UNIX 版本编译。

最后一个创新对我们 Linux 极客来说尤其值得注意:干净版本保持这种方式是为了最大限度地提高代码的“可审计性”,确保其从根本上是稳定和安全的。只有在 Theo(一个真正的偏执狂)祝福了这段代码之后,才会添加可移植性增强功能。因此,我们受益于一个既极其安全又 100% Linux 兼容的软件包。

顺便说一句,从 OpenBSD 团队发现 OSSH 到他们发布 OpenSSH 1.2.2 之间不到两个月的时间;仅过了六个半月,他们就发布了完全可移植且与 ssh v.2 兼容的 OpenSSH 2.0。 即使考虑到他们是基于 Ylonen 和 Groenvall 的工作进行构建,这仍然是一项了不起的成就,特别是考虑到最终产品的质量以及没有人为此付费的事实!

这就是到目前为止 ssh 和 OpenSSH 的故事。我希望您同意这是一个非常引人入胜的故事,与 OpenSSH 本身一样引人注目,OpenSSH 很可能将迅速成为开源版本 UNIX 的首选 ssh 版本。

您是否对 OpenSSH 感到兴奋并准备将其安装在您控制的每个 UNIX 系统上?很好。让我们开始忙碌吧!

顺便说一句:“ssh v.1.x”和“ssh 协议 v.1”分别指的是 ssh 的软件发布和协议,并非真正同义。但是由于软件包和协议的主要版本号 大致 对应,因此从现在开始,我将使用“ssh v.1x”来指代基于 RSA 的 ssh/OpenSSH 版本,使用“ssh v.2x”来指代支持 RSA 和 DSA 的版本。如果您不知道 RSA 和 DSA 之间的区别,那么只需说它们都做同样的事情,但 DSA 没有专利或许可限制。

SSH 的工作原理

安全外壳的工作方式与安全套接层 Web 事务非常相似(OpenSSH 使用的加密功能由 OpenSSL 提供,这是 Netscape 安全套接层源代码库的免费版本,这并非巧合)。两者都可以使用通用的“主机密钥”或已发布的凭据(数字证书)来设置加密通道,这些凭据可以由受信任的证书颁发机构(例如 VeriSign)验证。以下是连接的建立方式。

首先,客户端和服务器交换(公共)主机密钥。如果客户端计算机以前从未遇到过给定的公钥,则 ssh 和大多数 Web 浏览器都会询问用户是否接受不受信任的密钥。接下来,他们使用这些密钥协商一个会话密钥,该密钥用于通过诸如三重 DES (3DES)、blowfish 或 idea 之类的分组密码来加密所有后续会话数据。

然后,服务器尝试使用 RSA 或 DSA 证书对客户端进行身份验证。如果这不可能,系统将提示客户端输入标准的用户名/密码组合(可选地,可以使用“rhosts”基于主机 IP 的身份验证,无论是否使用 RSA 密钥;OpenSSH 还支持 KerberosIV 和 skey)。最后,在成功身份验证后,会话正式开始:远程 shell、安全文件传输、远程命令等,都在加密隧道上开始。

正如我之前提到的,ssh 实际上是一套工具

  • sshd—充当所有其他命令服务器的守护进程

  • ssh—主要最终用户工具:远程 shell、远程命令和端口转发会话

  • scp—用于自动文件传输的工具

  • sftp—用于交互式文件传输的工具—仅限商业 SSH

  • ssh-keygen—生成用于 RSA 和 DSA 身份验证的私钥-公钥对(包括主机密钥)

  • ssh-agent—用于自动化客户端 RSA/DSA 身份验证的守护进程

  • ssh-add—将私钥加载到 ssh-agent 进程中

  • ssh-askpass—ssh-add 的 X 界面

请注意,sftp 本质上是一个带有加密和强大身份验证功能的 ftp 客户端,仅在 F-Secure 商业版本的 ssh 版本 2 中可用——我在这里提到它只是因为您可能会在其他地方遇到对它的引用,并想知道为什么您只有 scp。

在这些工具中,大多数用户只关心 ssh,因为“加密 Telnet”是 ssh 最简单的用途。然而,scp、ssh-agent 和 ssh-add,以及 ssh 本身强大的身份验证和 TCP 端口转发功能,使 ssh 比这灵活得多。由于我们很偏执,并且希望尽可能加密我们在网络上抛出的东西,因此我们真的很喜欢这种灵活性。

获取和安装 OpenSSH

OpenSSH 网站(请参阅资源)是获取最新版本 OpenSSH(源代码和 RPM 形式)以及 OpenSSH 所需的 OpenSSL 的地方。 还需要 zlib,可在 freesoftware.com 网站上找到(请参阅资源)。

请注意,您可能无法通过 RPM 软件包来解决问题。 当我尝试在我的笔记本电脑上安装来自 OpenSSH.com 的 RPM 时(运行 SuSE Linux),除 sshd 外一切正常,sshd 由于 SuSE 缺少“chkconfig”软件包而无法安装。 您首选的 Linux 版本可能有也可能没有相同的问题(除非它有 chckconfig),或者它可能有自己的 OpenSSH RPM(就我所知,当您阅读本文时,可能有人已经发布了 SuSE 的 RPM)。

如果 RPM 无法工作,您需要从源代码构建 OpenSSH(以及可能的 OpenSSL 和 zlib)。 对于 Linux 老手来说,“滚动您自己的”软件安装是老生常谈,但如果您不属于这一类,请不要绝望。 所有这三个发行版都使用“.configure”脚本,消除了大多数用户编辑任何 Makefile 的需要。 假设您的系统具有 gcc 和正常的系统库,并且这些库相当新,则构建过程既快速又简单。

就我个人而言,在安装 OpenSSL 0.9.5a 和 zlib-1.1.3 之后(顺便说一句,所有版本号在您阅读本文时可能都已过时!),我按照以下步骤构建和安装 OpenSSH 2.1.1p4

tar -xzvf openssh-2.1.1p4.tar.gz
cd openssh-2.1.1p4
./configure --sysconfdir=/etc/ssh
make
make install

根据文件“INSTALL”提供的说明,我向 configure 脚本提供了一个自定义选项:与其将所有配置文件安装在 /etc 中,我指示它创建并使用一个子目录 /etc/sshd。 由于此版本的 OpenSSH 同时支持 RSA 和 DSA 密钥,因此最大限度地减少 ssh 添加到 /etc 的混乱是有意义的。

对于仅客户端安装,这就是您需要做的全部工作。 请注意,上面引用的一个或多个版本号在您阅读本文时可能已经过时; 请务必查看 OpenSSH 和 zlib 网站以获取最新版本。

如果您希望运行安全外壳守护进程 sshd(即,您希望接受来自远程主机的 ssh 连接),您还需要创建启动脚本,并且对于 SuSE,编辑 /etc/rc.config。 这也为您考虑到了:源代码发行版的“contrib”目录包含一些有用的好东西。

Red Hat 目录包含“sshd.init”,可以将其复制到 /etc/rc.d 并链接到相应的运行级别目录(/etc/rc.d/rc2.d 等)。 它还包含“sshd.pam”,如果您使用可插拔身份验证模块 (PAM) 和“openssh.spec”,则可以将其安装在 /etc/pam 中,该文件可用于创建您自己的 OpenSSH RPM 软件包。 这些文件显然旨在用于 Red Hat 系统,但也可能在 Red Hat 派生的系统(Mandrake、Yellow Dog 等)上工作。

suse 目录还包含一个“openssh.spec”文件,用于为 SuSE 创建 OpenSSH prpm 软件包,以及一个“rc.sshd”文件,用于安装到 /etc/rc.d(实际上是 SuSE 中的 /sbin/init.d)。 此外,它还包含“rc.config.ssd”,其内容必须添加到 /etc/rc.config 中,以便 rc.sshd 脚本正常工作。 这可以通过简单地输入命令来实现

cat ./rc.config.ssd >> /etc/rc.config

在 rc2.d 和/或 rc3.d 中创建一个符号链接,您的 SuSE 系统就可以提供安全 shell 了! 重新启动或键入 /etc/rc.d/rc.sshd start 以启动守护进程。

面向大众的 SSH:执行“加密 Telnet”操作

如果您只需要远程系统上的交互式 shell 会话 Telnet 一样怎么办? 即使不查看配置文件,您也可能只需要输入

ssh remote.host.net

系统将提示您输入密码(ssh 将假定您希望在远程系统上使用与您当前本地登录的用户名相同的用户名),如果成功,您就进去了! 这可以说比 Telnet 更简单,而且无疑更安全。

如果您需要在远程系统上使用与您本地登录的用户名不同的用户名,您需要添加标志 -l,后跟您的远程用户名。 例如,如果我以“mick”身份登录到我的笔记本电脑,并希望以用户“mbauer”身份 ssh 到 kong-fu.mutantmonkeys.org,我将使用命令

ssh -l mbauer kong-fu.mutantmonkeys.org

这对我有什么作用? 似乎与 Telnet 没有什么不同。 我可能会被询问是否接受远程服务器的公钥,会话启动可能需要更长的时间,并且根据网络状况、服务器负载等,会话可能看起来比 Telnet 稍慢,但在大多数情况下,我不会注意到太多差异。

但我将登录,而不会以明文形式通过网络发送我的用户名和密码,并且所有会话数据也将被加密。 我可以做任何我需要做的事情,包括 su -,而无需担心窃听者。 而我所付出的只是极小的延迟!

深入研究配置文件

配置 OpenSSH 也不复杂。 要控制 ssh 客户端和服务器的行为,只需编辑两个文件:ssh_configsshd_config。 根据您安装的软件包或您创建的构建,这些文件要么位于 /etc 中,要么位于您使用 .configure-sysconfdir 目录指定的其他位置。

ssh_config 是从本地主机启动的 ssh 客户端会话的全局配置文件。 它的设置会被命令行选项和用户的个人配置文件(如果存在,则保存在 $HOME/.ssh/config 中)覆盖。 例如,如果 /etc/ssh/ssh_config 包含行

Compression no

但文件 /home/bobo/.ssh/config 包含行

Compression yes
那么,每当用户“bobo”启动 ssh 会话时,压缩将默认启用,即使对于没有在其自己的 $HOME/.ssh/config 文件中进行此设置的用户,压缩也将关闭。 另一方面,如果 bobo 使用命令调用 ssh
ssh -o Compression=no remote.host.net
那么该会话将不会启用压缩。

换句话说,ssh 选项的优先级顺序是,按降序排列,ssh 命令行调用、$HOME/.ssh/config/etc/ssh/ssh_config

ssh_config 由参数列表组成,每个参数一行,格式为

parameter value(s)

某些参数是布尔值,可以具有“yes”或“no”的值。 其他参数可以具有以逗号分隔的值列表。 大多数参数都是不言自明的,并且都在 ssh(1) 手册页中进行了解释。 表 1 显示了一些最有用和/或最重要的参数(斜体文本表示可能的值)。

表 1. ssh_config 的一些基本客户端选项

除了这些之外,还有许多其他选项; 其中一些将在本文的第二部分中介绍。 有关完整列表,请参阅 ssh 手册页。

配置和运行安全外壳守护进程 sshd

如果您连接到的主机由其他人管理,那么这一切都很好。 但我们还没有讨论如何配置您自己的主机以接受 ssh 连接。 碰巧的是,这非常简单。

与 ssh 客户端一样,sshd 的默认行为在单个文件“sshd_config”中配置,该文件位于 /etc 或您指定的 ssh 配置目录中的任何其他位置。 与 ssh 客户端一样,其配置文件中的设置会被命令行参数覆盖。 但是,与 ssh 客户端不同,守护进程在各个用户的主目录中没有配置文件; 普通用户无法决定守护进程的行为方式。

表 2 描述了可以在 sshd_config 中设置的一些内容。

表 2. 在 sshd_config 中设置参数

sshd_config 中可以设置许多其他参数。 我们将在下个月介绍其中的一些参数,但了解以上内容足以开始使用(假设您的直接需求是替换 Telnet 和 ftp)。

使用 scp 进行加密文件传输

在本月休会之前,我们将介绍一个 ssh 主题。 scp 命令在大多数方面等同于旧的 rcp 实用程序,用于将文件或目录从一台主机复制到另一台主机。 (实际上,scp 是基于 rcp 的源代码。)如果您不熟悉其中任何一个,它们都是非交互式的:每个都使用单个命令行调用,您必须在其中指定您要复制的内容的名称和路径以及您希望将其复制到的位置。

这种非交互式特性使 scp 比 ftp 的用户友好性稍差:无论您是否喜欢,要使用 scp,您都需要阅读其手册页(或像本文这样的文章)并记住一些标志。 但是,与大多数其他命令行实用程序一样,scp 在脚本中比交互式工具更有用。 但是,“即时”使用 scp 很容易学习。 scp 命令的基本语法是

scp [ options ] sourcefilestring destfilestring

其中源文件和目标文件字符串可以是普通的 UNIX 文件/路径字符串(例如,"./docs/hello.txt"、"/home/me/mydoc.txt" 等)或格式为

username@remote.host.name:path/filename
例如,假设您已登录到主机“crueller”,并且想要将文件“recipe”传输到远程主机“kolach”上的主目录。 进一步假设您在两个系统上都有相同的用户名。 会话将如下所示(用户输入以粗体显示)
crueller: > scp ./recipe kolach:~
mick@kolach's password: *******
recipe         100% |**************>| 13226    00:00
crueller: >
键入 scp 命令行后,系统提示我们输入密码(我们的用户名,因为我们没有指定,所以使用我们登录到 crueller 的用户名自动为我们提交)。 然后 scp 将文件复制过来,并在复制过程中向我们显示一个方便的进度条。 就是这样!

假设您以“mick”身份登录到 crueller,但在 kolach 上具有用户名“mbauer”,并且希望将文件写入 kolach 的目录 data/recipes/pastries。 然后我们的命令行将如下所示

crueller: > scp ./recipe mbauer@kolach:/data/recipies/pastries/

现在让我们转换一下。 假设我们要从 kolach 检索文件 /etc/oven.conf(我们仍然登录到 crueller)。 那么我们的命令行如下所示

crueller: > scp mbauer@kolach:/etc/oven.conf.
明白了吗? 要记住的重要事情是,源必须在目标之前。

尽管大多数用户使用 ssh 和 scp 分别进行简单的登录和文件传输,但这只是 ssh 功能的冰山一角。 下个月,我们将研究如何使用 RSA 和 DSA 密钥使 ssh 事务更加安全,如何使用“空密码”密钥允许在脚本中包含 ssh 命令,如何在 RAM 中缓存 ssh 凭据以避免不必要的身份验证提示,以及如何通过加密的 ssh 连接隧道传输其他 TCP 服务。

资源

The 101 Uses of OpenSSH: Part I
Mick Bauer (mick@visi.com) 是 ENRGI 明尼阿波利斯分局的安全实践主管,ENRGI 是一家网络工程和咨询公司。 他自 1995 年以来一直是 Linux 爱好者,自 1997 年以来一直是 OpenBSD 狂热者,特别喜欢让这些尖端的操作系统在过时的垃圾上运行。 Mick 欢迎提问、评论和问候。
加载 Disqus 评论