SSH 的工作原理:从密钥交换到身份认证的完整通信机制
前言
这篇文章介绍了SSH的基本工作原理,列出了可能有用的参考资料,专业性可能会偏强,但我会在保留学术严谨表达的同时,使用通俗语气,让文章不会显得太过难以理解。
说不定会插入几张美图,毕竟学习很辛苦,营造归属感是很重要的

毕竟,总体来说,SSH的工作流本来就不难,是很容易理解的。接下来我会尝试以自己的话解释SSH的完整工作逻辑和使用SSH的原因
-はい! 始まるよ~
SSH的定义

SSH是主要应用于肿瘤研究的用于基因差异表达分析的实验方法
不对,什么鬼
SSH(Secure Shell),安全外壳协议,是一种加密的网络传输协议
作为一种协议,SSH存在多种实现,包括商业和开源实现(OSSH,OpenSSH)
SSH的核心在于,如何在完全不加密的网络通道上,建立起绝对安全的加密会话
SSH的通信原理
SSH的通信认证过程主要分为两个阶段:密钥交换和身份认证
第一阶段:密钥交换(Key Exchange / Handshake)
密钥交换后,可以根据 双方共有 且 仅双方共有 的数据,来加密信息流
所以如何获取符合要求的共享密钥是关键
1. 版本协商(明文传输)
SSH有很多版本,不同设备支持的版本可能不同,需要先进行版本协商,确定双方都能接受的版本方案
具体操作如下:
- 服务器端监听
- 服务器开放 TCP 端口 22,等待客户端连接
- 客户端发起连接
- 客户端向服务器端发起 TCP 初始连接请求
- 服务器发送版本标识
- 服务器向客户端发送第一个报文,包含版本标志字符串,格式为:
SSH-<主协议版本号>.<次协议版本号>.<软件版本号> - 其中,协议版本号 = 主版本号 + 次版本号,软件版本号主要用于调试和实现标识
- 服务器向客户端发送第一个报文,包含版本标志字符串,格式为:
- 客户端解析并选择协议版本
- 若服务器协议版本低于客户端版本,且客户端支持该低版本,则采用服务器端协议版本;
- 否则,使用客户端自身的协议版本。
- 客户端回应版本号
- 客户端向服务器发送报文,告知最终选定的协议版本号。
- 服务器确认协商结果
- 若协商成功,进入密钥交换与算法协商阶段;
- 若协商失败,服务器直接断开 TCP 连接。
参考资料:
具体数据字节可以参考这篇博客,解释的非常清楚
具体流程如下,参考了这篇博客:
2. 算法协商
双方交换支持的加密算法列表(如 Ed25519, AES-GCM 等),并选择最优解
- 服务器端与客户端分别向对端发送算法协商报文。
报文中包含各自支持的:- 公钥算法列表
- 对称加密算法列表
- MAC(Message Authentication Code,消息验证码)算法列表
- 压缩算法列表等。
- 服务器端与客户端根据双方支持算法的交集,协商并确定最终使用的算法组合。
参考文献:RHCE 作业2
3. 生成共享密钥
这里就是魔法的发生点,是涉及数学和密码学原理的核心
服务器端与客户端通过 Diffie–Hellman(DH)密钥交换,结合主机密钥对等参数,生成:
- 会话密钥(Session Key)
- 会话 ID(Session ID)
Diffie-Hellman密钥交换流程:
参数选择 → 密钥生成 → 公共值交换 → 共享密钥计算
具体的DH密钥交换操作主要是由 模幂运算 实现的
3.1 数学方式
- 运算技术: 模运算
- 安全性基础: 离散对数问题
基本流程:
- 约定参数:双方约定两个大质数 $g$(生成元)和 $p$(大质数模数)(均公开)
- 私有选择:亚澄选择一个随机大整数 $a$ 作为私钥;妃爱选择一个随机大整数 $b$ 作为私钥
- 计算并交换公钥:亚澄计算 $A = g^a \bmod p$,发送给妃爱;妃爱计算 $B = g^b \bmod p$,发送给亚澄
- 算出共享密钥 (K):亚澄计算 $K = B^a \bmod p$;妃爱计算 $K = A^b \bmod p$。
根据数学交换律:
\[K = (g^b \bmod p)^a \bmod p = (g^a \bmod p)^b \bmod p = g^{ab} \bmod p\]所以最后可以得出相等的密钥,且根据离散对数问题,仅由$g$、$p$、$A$、$B$是很难直接推出各自的私钥$a$、$b$,并进而很难推出会话的密钥$K$

参考文献:OSChina:SSH传输层协议、Tencent:Diffie-Hellman密钥交换技术解析
图源引用自:一文搞懂Diffie-Hellman密钥交换协议
3.2 直观解释
基本流程:
- 双方公开选择一种底色(如蓝色)
- 亚澄随机选取一个只有自己知道的颜色(绿色);妃爱机选取一种只有自己知道的颜色(红色)
- 亚澄把公共蓝色和绿色(得到青色)混合;妃爱公共蓝色和红色(得到紫色)混合,互相交换颜色
- 亚澄拿到紫色,再和绿色混合;妃爱拿到青色,再和红色混合,两者都获得了一模一样的神秘深褐色
虽然第三方拿到了紫色和青色,但是也无法分离出红色和绿色
3.3 共享密钥的前向安全性
得到的共享密钥K仅在单次会话中有效,所以即使私钥泄露,也不会造成历史通信流量泄露
3.4 Diffie-Hellman的中间人攻击模式
攻击者截获计算得到的A和B,而是向亚澄和妃爱两者分别发送自己的C1,C2
这样就会在自己和亚澄、妃爱两者之间分别建立安全连接,而亚澄和妃爱都不知道通信被截获,信息劫持成功
结语
至此,双方获得相同的会话密钥和会话 ID。后续数据传输均使用该会话密钥进行加密与解密,以保证通信安全
第二阶段: 身份认证:挑战-响应机制
现在,我们已经有了一段安全的‘悄悄话通道’(对称加密)
但妃爱还得确认,对面坐着的真的是亚澄,而不是伪装成亚澄的黑客。
具体过程:
-
发送钥匙 ID: 亚澄告诉妃爱“我想用指纹为 SHA256:… 的这把钥匙登录。”
-
检查名单:妃爱在账户设置(Settings -> SSH keys)里查找。如果找到了匹配的公钥,它会生成一个随机数(Challenge)。
-
加密挑战:妃爱用你的公钥对这个随机数进行加密,然后发给亚澄。公钥加密的东西,只有对应的私钥能解开。
-
解密与签名:亚澄收到密文,动用保存在 ~/.ssh/id_ed25519 的私钥将其解开。
-
为了证明自己确实解开了,亚澄会将解出的随机数加上当前会话的 ID,再用私钥进行数字签名(Signature),发回给妃爱
-
最终验证:妃爱用公钥验证这个签名。如果签名有效,说明亚澄确实持有私钥。

数学背景:
- 核心概念:陷门函数
- RSA加密:基于大数分解
- ECC(椭圆曲线算法):基于几何轨迹
由于技术比较成熟,而且网络文献比较多,我就不详细介绍了,可以去B站或者Bing查
可以参阅这篇文章:椭圆曲线加密算法(ECC)
图源引用自:知乎:SSH 密钥身份验证和管理
后期通信
在获得共享密钥$K$之后,后期信息流都是通过加密算法加密传输的
目前最主流、最安全的对称加密算法是 AES(高级加密标准),可以参考 知乎:高级加密标准(AES)
在 SSH 连接中,通常配合 GCM(伽罗瓦/计数器模式) 或 ChaCha20-Poly1305 使用。它的特点是:加密和解密用的是同一个密钥 $K$
加密传输过程:
- 分组与填充:数据被切成固定大小的数据块。如果最后一块不够大,会填入一些随机数。
- “异或”运算与置换:将数据块和密钥$K$进行一次异或运算,再进行字节代换和行移位、列混淆生成密文
- 解密:只需要使用共享密钥$K$进行反向操作即可
数据的加密传输过程中,加密和解密的速度都是非常快的,能保证数据传输的效率
AES 如此之快,是因为现代 CPU(包括树莓派 4B 搭载的 ARM 处理器)通常都有专门的硬件指令集来加速这些逻辑运算,它不像 RSA 那样需要消耗大量 CPU 周期去算大数的幂次方
至此,SSH通信的基本原理和流程就讲清楚了。我们可以使用现成的OpenSSH进行各种远程信息传输了(虽然其实没搞懂也能轻松使用SSH就是了,不过能搞懂原理总是对使用有利无害)
为什么要从HTTPS切换到SSH?
拿Github来讲,我之前的Git操作都是通过HTTPS协议完成的
比如,我的远程仓库就是https://github.com/Eganchiyu
那么我就直接push到这个网址就行了,握手后,服务器会做一系列操作,本次请求就算完成
但是在中国用过github的都知道,github的网络是何等的不稳定,一旦dns污染了,就根本完成不了这些基本的操作了
HTTPS和SSH协议比对
| 特性 | HTTPS (HyperText Transfer Protocol Secure) | SSH (Secure Shell) |
|---|---|---|
| 底层协议 | 建立在 TLS/SSL 之上,运行在 443 端口。 | 独立的 SSH 协议,通常运行在 22 端口。 |
| 身份验证 | 主要是基于证书颁发机构(CA)。客户端验证服务器的证书是否由受信任的机构签发。 | 基于非对称加密。客户端将公钥给服务器,服务器通过挑战/响应机制验证客户端持有的私钥。 |
| 连接过程 | 涉及复杂的 TLS 多次握手(Client Hello、Server Hello、交换证书等)。 | 相对简洁的密钥交换和身份验证流程。 |
| 主要用途 | 网页浏览、通用 API 调用。 | 远程管理服务器、代码托管同步(Git)。 |
为什么SSH更稳定?
我们常遇到的 GnuTLS recv error (-110) 本质上是连接重置(Connection Reset)或握手超时
SSH 能够解决这个问题,主要有以下几个原因:
1. 规避深度包检测 (DPI) 的干扰
HTTPS (443端口) 流量巨大且复杂。国内网络环境会对 TLS 握手包进行高强度的扫描和检测(为了识别 SNI 信息)
如果检测过程中出现丢包或延迟,握手就会失败
SSH (22端口) 的流量特征与网页浏览完全不同,其流量相对“纯粹”,受到的针对性协议干扰有时比 HTTPS 略小。
2. 状态保持与重连机制
HTTPS 是无状态的短连接,每次 git push/pull 都要重新经历完整的 TLS 握手流程,任何一次握手失败都会报错
SSH 在建立连接时,验证的是你预先存放在 GitHub 上的公钥。只要 RSA/Ed25519 的密钥交换完成,连接就会非常稳固
对于 Git 操作,SSH 的处理逻辑更直接,减少了因证书校验失败导致的意外中断。
3. 绕过过载的 Web 代理/网关
很多运营商或校园网会对 443 端口(网页流量)进行复杂的流量整形(Traffic Shaping)或代理缓存
由于 SSH 流量通常被视为“运维/管理”流量,往往能避开这些针对普通网页访问的限速或过滤规则(装大佬这一块)
局限性:HTTPS和SSH都无法解决DNS污染
在正常的网络环境下,DNS 服务器会返回 GitHub 真实的 IP(比如 20.205.243.166)。但在受污染的环境下,中间节点返回一个错误的、无法访问的、甚至是虚假的 IP 地址。
这在HTTPS和SSH中都会有表现:
-
HTTPS 表现:获取Ip错误,浏览器尝试去跟这个错误 IP 建立 TLS 连接。由于 IP 根本不对,握手会直接超时,或者报错“证书不匹配”
-
SSH 表现:解析出的 github.com 错误,ssh -T git@github.com 会连接失败
结语
辛苦读了这么久文章,现在起身去活动一下吧。一直坐在电脑桌前总是对身体不好的。
身体是革命的本钱。搞好身体才能用现有技术去创造全新的技术,并更好地服务大众。
作为知识的拓荒者,要深入到生活中,或者工业、军事、国际等,去了解,到底现在需要什么,然后看准了就不怕麻烦、有节奏地去做好
作为百姓,我们也不能因为技术的发展而完全依赖。要开动自己的脑子,去做更多有意义的事情。作为人类,有意义的事情莫过于和重要的人一起待着,去给世界提供更多的感动,去为自己和重要的人创造更多美好的回忆,让这一生至少值得被自己记住
所以,想一想吧,现在开始,能做些什么,让你的今天变得值得回忆呢?
去外面走走,去邂逅猫猫狗狗,去和家人逛街,精心准备礼物,用相机镜头记录下一切,或者是听歌、唱歌
这个世界很简单,简单到人与人的沟通其实不需要通讯加密。但是好多人都忘记了。网络梗、没必要的博弈在包装着情感。当然,这也是有必要的,只不过应该在需要用它的时候再启用。
如果找到了心有灵犀的伙伴,就把公钥给他一份,然后创造一个安全通信空间,用真心对待和珍惜

接下来我会记录在笔记本与树莓派、树莓派与github之间的SSH认证和通信的过程,写成一篇新的博客,敬请期待!
附:会有一些我折腾词典笔的珍贵记录
留下评论