SSH 简介

SSH(Secure Shell): 安全外壳协议,是一种加密网络传输协议,可在不安全的网络中为网络服务提供安全的传输环境;

  • SSH最常见的用途是远程登录系统;
  • SSH使用客户端-服务器(C-S)模型,标准端口为22;
  • SSH非对称加密实现身份验证;
  • 截至2005年,OpenSSH是唯一一种最流行的SSH实现,而且成为了大量操作系统的默认组件;

加密方式

SSH非对称加密实现身份验证的,我们来简单介绍一下,对称加密非对称加密

对称加密

加密流程

  • 对称加密:加密解密 使用同一个 秘钥;
  • 加密流程:
    • 客户端使用 秘钥A 对数据进行加密后发送给服务端;
    • 服务端收到数据后,同样使用 秘钥A 进行解密;

秘钥大小

  • 密钥的大小既要照顾到安全性,也要照顾到效率; 对称加密通常使用的是相对较小的密钥,一般小于256bit。因为密钥越大,加密越强,但加密与解密的过程越慢;

对称加密算法

  • 常见的对称加密算法:DESAES等。

优缺点

  • 优点:效率高;
  • 缺点:密钥管理与分配

note:如何把密钥发送到需要解密你的消息的人的手里是一个问题。在发送密钥的过程中,密钥有很大的风险会被黑客们拦截。现实中通常的做法是将对称加密的密钥进行非对称加密,然后传送给需要它的人。

非对称加密

加密流程:

  • 非对称加密 有两个秘钥:公钥私钥
  • 加密流程:
    • 使用 公钥 对数据进行加密;
    • 只能使用相对应私钥 才能解密;

加密算法:

  • 常见的非对称加密有 RSA;

SSH 应用场景

基于口令的认证

1
2
# 命令格式:ssh 客户端用户名@服务器ip地址
ssh admin@192.168.0.1
  • 如果客户端的用户名和服务端的用户名相同,登录时可以省略用户名。

    1
    ssh 192.168.0.1
  • SSH服务的默认端口是22,也可以通过 -p 来指定端口号

    1
    ssh -p 1234 admin@192.168.0.1

首次登录

当我们第一次登录对方主机,系统会出现如下的提示信息:

1
2
3
4
$ ssh user@host
The authenticity of host 'host (12.18.429.21)' can't be established.
RSA key fingerprint is 98:2e:d7:e0:de:9f:ac:67:28:c2:42:2d:37:16:58:4d.
Are you sure you want to continue connecting (yes/no)?

意思就是:无法确认远程host主机的真实性,只知道它的公钥指纹,是否继续连接?

  • 公钥指纹:由于公钥长度较长(这里采用RSA算法,长达1024位),难以比较,可以对其进行MD5等运算后进行比较;

输入yes: 会提示远程主机被添加到已知主机列表

1
Warning: Permanently added 'host,12.18.429.21' (RSA) to the list of known hosts.

然后会要求我们输入远程主机的密码,输入的密码正确就可以成功登录了;

known_hosts 文件

  • 客户端通过SSH首次连接到服务端后,服务端会将一个公钥(公钥1)传递给客户端;
  • 客户端收到这个公钥(公钥1)后将其存入known_hosts中;
  • 之后再次连接服务端时,服务端依然会返回一个公钥(公钥2);
  • 通过对比公钥1公钥2 是否相同来进行验证,如果不同就会发出警告Host key verification failed,并登陆失败;

macOS系统的中,known_hosts 文件位于/Users/用户名/.ssh/known_hosts

基于公钥认证

在上面的基于口令的认证方式中,我们每次都必须输入密码,非常麻烦,SSH还提供了基于公钥登录的方式,可以省去输入密码的步骤;具体步骤如下:

  • 客户端生成一对秘钥(公钥&私钥)
  • 将上述的公钥储存在服务端上(存放在服务端的authorized_keys文件中)
  • 客户端发起登陆请求,服务端收到后会生成一个随机的字符串,然后使用事先存储的公钥进行加密,然后将加密后的字符串发送给客户端
  • 客户端收到这个加密的字符串后,使用私钥进行解密,然后将解密后的数据再发送回服务端
  • 服务端收到客户端发送的解密数据后,进行校验,如果为同一个字符串,登陆成功;否则,登陆失败

note:上述仅仅是SSH公钥认证的大体流程。想要了解更详细的内容可以搜索 SSH sessionKey;

authorized_keys 文件

  • 将客户端公钥存储到服务端上,其实就是将客户端的公钥数据放到了服务端的authorized_keys文件中;
  • Linux系统中,authorized_keys 文件位于 ~/.ssh/authorized_keys

是不是想起我们在Github 设置中配置 SSH key 的场景了~