
这张图把 SSH 过程画成“先建安全隧道,再登录,再在隧道里跑命令/转发端口”。对应到 SSH 协议,其实就是 三层协议串起来:Transport(传输层)→ User Authentication(认证层)→ Connection(连接层)。
1)总体流程(对应图里的 1~16)
建立 TCP 连接(图 1):通常到服务器 (也可自定义端口)。
:22
版本号交换(图 2):双方发一行 ,确认都是 SSH-2。
SSH-2.0-...
算法协商(图 3):协商
密钥交换 KEX(如 curve25519 / ecdh / diffie-hellman)
主机密钥 HostKey(如 ed25519 / rsa)
对称加密 cipher(如 chacha20-poly1305 / aes-gcm / aes-ctr)
完整性/认证(MAC 或 AEAD、自带完整性)
压缩等
密钥交换 + 生成会话密钥(图里“calculate session key”):这一步在协议上属于 Transport,KEX 会产生 共享密钥材料,再派生出:
双向加密密钥、完整性密钥、IV/nonce 等
之后所有数据都在“SSH 隧道”里加密传输了。
用户认证(图 5~11 的“public key 登录”):在安全隧道里做登录认证,通过后才允许开 session/转发等。
会话与命令/数据传输(图 12~16):在同一条 TCP/SSH 连接上开“channel”,跑 shell/exec/sftp/端口转发等,数据都用会话密钥加密。
注意:图里把公钥认证画成“服务端发随机数→客户端用私钥解密→证明身份”。这是一种简化/类比。现代 SSH 的 publickey 认证更常见的形式是:客户端用私钥对握手相关数据做签名,服务端用
里的公钥去验签(本质一样:证明你持有私钥)。
authorized_keys
2)Transport Layer(SSH 传输层)负责什么?
Transport 层的目标:先把“不安全的 TCP”升级成“已加密、完整性保护、并且确认了服务器身份”的安全管道。
它主要做这些事:
A. 服务器身份认证(防 MITM)
服务器会用自己的 Host Key(主机密钥)参与握手并证明“我就是这台服务器”。
客户端会把服务器公钥与 里记录的指纹比对;不匹配就可能是中间人/服务器被替换。
~/.ssh/known_hosts
B. 密钥交换 + 会话密钥派生
通过 KEX(DH/ECDH/curve25519)得到共享秘密,然后派生出会话密钥。
从这一步开始,后续报文:
加密(confidentiality)
完整性/防篡改(MAC 或 AEAD)
防重放/序号(每个方向有序列号、与 MAC/AEAD 绑定)
连接过程中还能 rekey(传一段数据后重新换密钥)。
C. 可靠承载
它不负责“多路复用/开频道”(那是 Connection 层),但它提供了加密后的可靠数据流承载。
3)Authentication Layer(认证层)负责什么?
认证层目标:在已经加密的隧道里确认“你是谁,你是否有权限登录”。常见方法:
:最常用。服务器在
publickey 找到匹配公钥后,要求客户端证明自己持有对应私钥(通常是“签名→验签”)。
~/.ssh/authorized_keys
:密码登录(也在隧道里传,不会明文上网)。
password
:可对接 MFA/OTP/LDAP 等交互式挑战。
keyboard-interactive
还涉及账号、授权策略(允许/拒绝哪些 key、来源限制、强制命令等)。
这一层只负责“认证通过/失败”,并不定义“怎么开 shell、怎么转发端口”。
4)Connection Layer(连接层)负责什么?
Connection 层目标:在同一条 SSH 连接上,复用出多个逻辑通道(channels),并提供会话/转发等高级能力。
A. 多路复用:Channel
一个 SSH TCP 连接里可以同时有多个 channel:
:交互 shell、执行命令(exec)、SFTP(subsystem)
session
:本地端口转发用的通道
direct-tcpip
:远程端口转发用的通道
forwarded-tcpip
每个 channel 有窗口机制(flow control),避免某一条通道把另一个通道“堵死”。
B. 会话能力
/
pty-req:拿到交互终端
shell
:执行一次性命令
exec
:文件传输
subsystem sftp
C. 端口转发(图下半部分重点)
图里是 本地转发(Local Forwarding):
ssh -L p1:server:p2 remote
含义是:
在本机监听
localhost:p1
任何连接到 的流量,会被 SSH 客户端封装进加密隧道
p1
到达远端 SSH Server 后,由服务器去连接 (可能是远端本机 127.0.0.1:p2 或远端可达的内网地址)
server:p2
这样本地应用就像在连 ,实际上穿过 SSH 到了远端目标服务,常用于“穿防火墙/访问内网服务”。
localhost:p1
(类似地还有 远程转发、
-R 动态转发 SOCKS5。)
-D
5)把三层分工用一句话串起来
Transport:先“建隧道”——协商算法、验证服务器主机密钥、密钥交换、建立加密与完整性保护。
Authentication:再“验身份”——在隧道里用公钥/密码/MFA 等证明你是谁,决定你能不能登录。
Connection:最后“干活”——开多个 channel 跑 shell/exec/sftp/端口转发,多路复用且互不干扰。
用 PlantUML把每层的关键报文(KEXINIT/KEXDH/NEWKEYS、USERAUTH、HANNEL_OPEN 等)再对照讲一遍。
