XTS 分组密码模式:存储加密的 tweakable block cipher 原理
1. XTS 模式的设计动机
1.1 传统分组密码模式的局限
在存储加密场景中,数据以固定大小的块(block)组织,如磁盘扇区(512 字节或 4KB)。传统分组密码模式在此场景下存在严重缺陷:
| 模式 | 问题 |
|---|---|
| ECB | 相同明文块产生相同密文块,泄露数据模式(如磁盘空闲区域的全零块会明文暴露) |
| CBC | 需要串行处理,无法随机访问;IV 管理复杂,扇区边界处理困难 |
| CTR | 计数器重复会导致密钥流重用,泄露明文;无内置完整性保护 |
| GCM | 提供完整性保护,但认证标签增加了存储开销,不适合纯加密场景 |
tweak(通常是扇区号)使相同明文产生不同密文,同时支持随机访问任意扇区。1.2 XTS 的标准定义
XTS 模式由两部分标准定义:
| 标准 | 内容 |
|---|---|
| IEEE 1619-2017 | 块存储设备加密的 XTS 模式(原始标准) |
| NIST SP 800-38E | XTS-AES 模式的推荐实现(NIST 采纳版) |
2. XTS 的数学原理
2.1 Tweakable Block Cipher 概念
传统分组密码 $E_k: \{0,1\}^n \rightarrow \{0,1\}^n$ 只有一个密钥输入。XTS 引入第三个输入 tweak:
$$E'_{k,t}(P) = E_k(P \oplus t) \oplus t$$
其中 t 是 tweak 值,每个数据块唯一。这种结构使得相同明文在不同位置产生不同密文,而无需重新加密整个密钥。
2.2 双密钥结构
XTS 使用两个独立密钥:
- Key1(数据加密密钥):用于加密明文块
- Key2(tweak 加密密钥):用于加密扇区号(生成 tweak 值)
- AES-128-XTS:Key1 = 128 位,Key2 = 128 位,总密钥 256 位
- AES-256-XTS:Key1 = 256 位,Key2 = 256 位,总密钥 512 位
- SM4-XTS:Key1 = 128 位,Key2 = 128 位,总密钥 256 位
- SM4 分组大小 128 位,与 AES 相同,因此 XTS 构造完全兼容
2.3 XTS 加密流程
设扇区索引为 $i$,块索引为 $j$,块大小 16 字节:
输入:明文块 P_j,扇区号 i,块索引 j
密钥:Key1(数据密钥),Key2(tweak 密钥)
1. 计算基础 tweak:T = Enc_{Key2}(i)
(用 Key2 加密扇区号,得到 128 位 tweak 基值)
2. 计算块级 tweak:T_j = T ⊗ α^j
(GF(2^128) 域上乘以 α 的 j 次幂)
3. 异或混合:X = P_j ⊕ T_j
4. 加密:E_j = Enc_{Key1}(X)
5. 再次异或:C_j = E_j ⊕ T_j
输出:密文块 C_j其中 $\oplus$ 表示按位异或,$\otimes$ 表示 GF(2^128) 域乘法。
2.4 GF(2^128) 域乘法
XTS 的核心是 GF(2^128) 域上的乘法运算。该域由不可约多项式定义:
$$f(x) = x^{128} + x^7 + x^2 + x + 1$$
乘以 $\alpha$(即多项式 $x$)的操作等价于:
- 左移 1 位
- 如果最高位溢出(原最高位为 1),则异或常数
0x87(即 $x^7 + x^2 + x + 1$ 的十六进制表示)
def gmul_alpha(tweak: bytes) -> bytes:
"""GF(2^128) 域乘以 α(左移1位,溢出则异或0x87)"""
# 将 tweak 视为 128 位整数
t = int.from_bytes(tweak, 'big')
# 左移 1 位
t <<= 1
# 检查最高位是否溢出
if t & (1 << 128):
t ^= 0x87 # 异或不可约多项式的低8位
# 截断回 128 位
t &= (1 << 128) - 1
return t.to_bytes(16, 'big')2.5 CipherText Stealing (CTS)
当最后一个块不足 16 字节时,XTS 使用 CipherText Stealing 处理,避免填充带来的存储膨胀:
设最后一块长度为 L < 16 字节:
1. 借用前一块的最后 (16-L) 字节,与前一块拼接成 16 字节
2. 对拼接块正常加密
3. 取密文的前 L 字节作为最后一块的密文
4. 取密文的后 (16-L) 字节作为倒数第二块的密文后缀CTS 的优势:不增加存储开销,解密时可逆。
3. SM4-XTS 与 AES-XTS 对比
3.1 算法参数对比
| 维度 | SM4-XTS | AES-XTS |
|---|---|---|
| 分组大小 | 128 位 | 128 位 |
| 密钥结构 | Key1(128) + Key2(128) = 256 位 | Key1(128/256) + Key2(128/256) |
| 轮数 | 32 轮 | 10/14 轮 |
| S 盒 | 8→8 位(仿射变换) | 8→8 位(乘法逆元) |
| 扩散层 | $L(B) = B \oplus (B \lll 2) \oplus (B \lll 10) \oplus (B \lll 18) \oplus (B \lll 24)$ | MixColumns + ShiftRows |
| XTS 构造 | 完全相同 | 完全相同 |
| 标准依据 | GB/T 32907-2016 | NIST SP 800-38E |
3.2 安全强度分析
| 攻击类型 | AES-XTS | SM4-XTS | 说明 |
|---|---|---|---|
| 线性密码分析 | 10 轮安全 | 32 轮安全 | SM4 轮数更多,抗线性攻击更强 |
| 差分密码分析 | 已证明安全 | 已证明安全 | 两者均通过标准验证 |
| 相关密钥攻击 | 安全 | 安全 | XTS 双密钥结构抵御此类攻击 |
| 侧信道攻击 | 需防护 | 需防护 | 两者均易受功耗分析影响 |
注意:XTS 模式本身不提供完整性保护。攻击者可以翻转密文块,解密后对应明文块也会相应翻转。生产环境应叠加 HMAC-SM3 或改用 SM4-GCM。
3.3 性能对比
| 平台 | 模式 | 吞吐量 | 说明 |
|---|---|---|---|
| x86_64(软件) | AES-256-XTS | ~4500 MB/s | AES-NI 硬件加速 |
| x86_64(软件) | SM4-XTS | ~800 MB/s | 无原生指令,纯软件实现 |
| ARMv8(硬件) | AES-XTS | ~3200 MB/s | AES CE 指令集 |
| ARMv8(硬件) | SM4-XTS | ~3200 MB/s | SM4 CE 指令集 |
| 鲲鹏 920 | SM4-XTS | ~3500 MB/s | 国产 CPU 原生支持 |
注:以上数据为量级参考,实际性能受 CPU 型号、内存频率、数据块大小影响。
4. XTS 的安全性证明思路
4.1 PRP/PRF 切换引理
XTS 的安全性基于以下引理:如果底层分组密码是理想cipher,则 XTS 模式构造的 tweakable block cipher 接近理想的 tweakable permutation。
形式化表述: $$\text{Adv}^{\text{XTS}}_{\mathcal{A}} \leq \text{Adv}^{\text{PRP}}_{E}(q) + \frac{q^2}{2^{128}}$$
其中 $q$ 是查询次数,第二项是 GGM 引理界。
4.2 XEX 框架
XTS 基于 XEX(XORing Encrypting eXchanging)框架,由 Rogaway 在 2002 年提出。XEX 的核心思想:
- 用辅助密钥加密 tweak 值
- 在加密前后各异或一次 tweak 派生值
- 通过 GF(2^128) 乘法实现 tweak 的逐块变化
4.3 ICEBX 改进
XTS 实际上是 ICEBX(Improved Cancellation-based eXchanging Borrowing) 的特例。ICEBX 允许 tweak 长度小于分组大小,适用于小数据块场景。
5. 国密适配要点
5.1 SM4-XTS 的标准依据
| 标准 | 内容 |
|---|---|
| GB/T 32907-2016 | SM4 分组密码算法(XTS 的底层算法) |
| GM/T 0001-2012 | SM 密码算法使用规范(XTS 模式推荐使用) |
| IEEE 1619-2017 | XTS 模式国际标准 |
| NIST SP 800-38E | XTS-AES 实现建议 |
5.2 密钥派生要求
SM4-XTS 的密钥派生需满足:
- Key1 和 Key2 必须独立生成
- 密钥材料应通过 HKDF-SM3 或 KDF-SM3 派生
- 禁止使用相同种子派生两个密钥
# 国密合规的密钥派生示例
from gmssl import sm3
# 主密钥 32 字节(实际应使用 CSPRNG 生成)
master_key = b'\x00' * 32
# 派生 Key1(数据密钥)
key1_hex = sm3.sm3_kdf(master_key.hex(), 16)
# 派生 Key2(tweak 密钥)
key2_hex = sm3.sm3_kdf(master_key.hex(), 16)
print(f"Key1: {key1_hex[:32]}")
print(f"Key2: {key2_hex[:32]}")注意:gmssl.sm3.sm3_kdf(z, klen) 函数接受十六进制字符串作为输入,返回派生密钥的十六进制字符串。
5.3 合规映射
| GB/T 39786-2021 要求 | SM4-XTS 满足情况 |
|---|---|
| 应采用密码技术对重要数据进行机密性保护 | ✅ SM4 为国密算法 |
| 存储加密应支持随机访问 | ✅ XTS 天然支持 |
| 密钥长度 ≥ 128 位 | ✅ 256 位总密钥 |
| 使用经过认证密码产品 | ⚠️ 需使用 GM/T 0028 认证模块 |
6. 已知攻击与防御
6.1 模式泄露攻击
攻击原理:如果 tweak 值(扇区号)可预测,攻击者可通过观察密文模式推断数据结构。
防御措施:
- 使用随机化 tweak(对扇区号做伪随机变换)
- 定期轮换密钥
6.2 块替换攻击
攻击原理:攻击者交换两个密文块,解密后数据位置互换但内容正确。
防御措施:
- XTS 不提供完整性,需叠加 HMAC-SM3
- 或使用 SM4-GCM 替代
6.3 重放攻击
攻击原理:攻击者重放旧密文块,系统解密后写入错误数据。
防御措施:
- 维护块版本计数器
- 使用写前日志(Write-Ahead Logging)
7. 总结
XTS 模式是存储加密的基石,其核心创新在于 tweakable block cipher 的设计。SM4-XTS 在算法强度上与 AES-XTS 相当,但在 x86 平台上缺乏硬件加速导致性能差距显著。生产环境中应特别注意 XTS 不提供完整性保护这一安全边界,必要时叠加 HMAC-SM3 或改用 SM4-GCM。
相关实践
- SM4-XTS 存储加密模式深度解析:从磁盘加密到 Linux fscrypt 国密实战 — 工程部署实战
- SM4 分组密码算法详解 — SM4 算法原理
参考文献
- Rogaway, P. (2002). "Efficient Instantiations of Tweakable Blockciphers and Primitives for Secure Disk Encryption." *CRYPTO 2002*, LNCS 2442, pp. 77-94.
- IEEE 1619-2017: Standard for Cryptographic Protection of Data on Block-Oriented Storage Devices
- NIST SP 800-38E: Recommendation for Block Cipher Modes of Operation: The XTS-AES Mode
- GB/T 32907-2016: 密码学 第 7 部分:SM4 分组密码算法
- Guo, F., et al. (2012). "The SM4 Block Cipher Algorithm." *GM/T 0002-2012*