TFHE-rs深度解析之三:密文操作和可编程自举
Chuck Chen
·
有限级密文操作
TFHE 支持在密文上直接进行线性运算(加法、减法、常数乘法),这些操作被称为“有限级(Leveled)”操作,因为它们不需要自举(Bootstrapping),但会增加密文中的噪声。
密文加法 (GLWE 同态加法)
给定两个分别加密消息 M 和 M′ 的 GLWE 密文 C 和 C′(使用相同的密钥 S),它们的同态加法可以通过将两个密文的对应分量相加来完成。结果密文 C⊞ 加密了和 M+M′,密钥保持不变,但噪声水平会增加(两个输入密文噪声之和)。
数学表达如下:
C⊞==C+C′(A0+A0′,…,Ak−1+Ak−1′,B+B′)∈GLWES(Δ(M+M′))
简化示例(GLWE 同态加法)
假设参数为:q=64,p=4 (即 Δ=16), N=4,k=2。
密钥 S=(X+X2,1+X2+X3)。
两个消息分别为:
M=−2+X−X3M′=X+X2−2X3
它们的和为
M⊞=M+M′=−2−2X+X2+X3∈Rq
假设加密后的密文分量如下(包含噪声):
-
C=(A0,A1,B),其中
A0A1B=17−2X−24X2+9X3=−14−X2+21X3=−31+5X−21X2+30X3
-
C′=(A0′,A1′,B′),其中
A0′A1′B′=−8+15X+3X2−30X3=23−16X+27X2−4X3=−25+12X2−12X3
-
最终得到的密文C⊞=(A0⊞,A1⊞,B⊞)。密文加法操作即对应多项式的加法:
A0⊞A1⊞B⊞=A0+A0′=9+13X−21X2−21X3=A1+A1′=9−16X+26X2+17X3=B+B′=8+5X−9X2+18X3
解密后即为 M⊞。
密文乘法 (GLWE 同态标量乘法)
注意:这里的“乘法”特指密文与一个已知的“小”常数多项式(或整数)相乘。如果是两个密文相乘,通常涉及更复杂的外部积(External Product)或需要自举。
给定 GLWE 密文 C 和一个小常数多项式 Λ,同态乘法是将密文的每个分量都乘以 Λ。结果 C⋅ 是加密了积 Λ⋅M 的新密文。噪声方差会随着 Λ 系数的大小放大。
数学表达如下:
C⊠=Λ⋅C=(Λ⋅A0,…,Λ⋅Ak−1,Λ⋅B)
简化示例(GLWE 同态标量乘法)
沿用上述参数和密文 C。我们选择一个小常数多项式 Λ=−1+2X2+X3。
我们的目标是计算积 M⊠=Λ⋅M=1+X+X2+X3。
运算过程如下(多项式乘法在模 XN+1 下进行):
A0⊠=Λ⋅A0A1⊠=Λ⋅A1B⊠=Λ⋅B=(−1+2X2+X3)⋅(17−2X−24X2+9X3)=−31+8X−15X2+4X3=(−1+2X2+X3)⋅(−14−X2+21X3)=16+23X+16X2+29X3=(−1+2X2+X3)⋅(−31+5X−21X2+30X3)=4+20X−7X2+13X3
密钥切换 (Key Switching)
密钥切换(Key Switching)是所有基于 (R)LWE 的同态加密方案中的核心操作。它的目标是将一个在一个密钥 S 下加密的密文,同态地转换为在另一个密钥 S′ 下加密同一消息的密文。
原理解析
给定一个 GLWE 密文 C=(A0,…,Ak−1,B),它在密钥 S 下加密了消息 M。根据定义:
B−i=0∑k−1Ai⋅Si≈ΔM
密钥切换的核心思想是“同态地”计算上述解密公式。具体来说,我们保留 B(常数项),并试图减去 ∑Ai⋅Si。由于我们不能直接知道 Si,我们需要提供 Si 在新密钥 S′ 下的加密版本,称为密钥切换密钥 (Key Switching Key, KSK)。
利用前面提到的密文与常数乘法(这里 Ai 视为常数,Si 的密文视为密文),我们可以计算出 ∑Ai⋅Si 的密文,然后从 B 中减去它。
数学公式
假设 KSK 包含了旧密钥分量 Si 在新密钥 S′ 下的 GLev 加密(GLev 是 GLWE 的一种分解形式,类似于 GGSW 之于 RLWE,用于控制噪声增长)。
KSKi∈GLevS′(Si)
密钥切换操作如下:
C′=(0,…,0,B)−i=0∑k−1⟨Decomp(Ai),KSKi⟩
其中 ⟨⋅,⋅⟩ 表示分解后的向量与 GLev 密文向量的内积(本质上是外部积的变体)。
结果 C′ 即为在新密钥 S′ 下加密 M 的 GLWE 密文。
应用场景
密钥切换不仅用于更改密钥,还常用于:
- 参数切换:从一组 LWE 参数(如大维度、小模数)切换到另一组(如小维度、大模数)。
- LWE 到 RLWE 转换:将 LWE 密文“打包”进 RLWE 密文的系数中。
- 自举的最后一步:在 TFHE 自举中,盲旋转后的密文通常具有较大的 LWE 维度(由 RLWE 维度决定),需要通过密钥切换转换回原始的 LWE 维度,以便进行下一轮运算。
有限级密文乘法与外部积
在全同态加密中,两个密文直接相乘通常会导致噪声呈现“二次方”增长,这会迅速消耗噪声预算并导致解密失败。为了解决这个问题,TFHE 引入了 外部积 (External Product) 的概念。
外部积的概念
外部积是一种非对称的乘法运算,记为 ⊡。它涉及两种不同类型的密文:
- GGSW 密文 CGGSW:通常加密一个“小”整数或多项式(例如密钥位或控制位)。这种密文结构较大,包含了消息在不同缩放因子下的多份副本。
- GLWE 密文 CGLWE:标准的同态密文。
运算结果是一个新的 GLWE 密文:
Cres=CGGSW⊡CGLWE
其核心优势在于:输出噪声的增长是加性的(Additive),而不是乘性的(Multiplicative)。这使得我们可以进行多次连续的乘法运算而不用立刻进行自举。
分解技术 (Decomposition)
为了实现低噪声增长,TFHE使用了**分解(Decomposition)**技术。
给定一个大常数(或 GLWE 密文的分量),我们将其按基数 β 分解为一系列“小”分量:
γ=j=1∑ℓγjβjq
其中 γj 很小。
在计算外部积时,我们不直接用大数相乘,而是将 GLWE 密文分解,然后与 GGSW 密文中预计算好的、对应于 βjq 的加密部分进行组合。
应用:CMUX 门
外部积最著名的应用是 CMUX (Controlled Multiplexer) 门,它是自举的核心组件。
CMUX(Csel,C0,C1)=Csel⊡(C1−C0)+C0
这里,Csel 是一个 GGSW 密文(加密了 0 或 1),用于在两个 GLWE 密文 C0 和 C1 之间进行选择。得益于外部积的低噪声特性,我们可以在盲旋转中连续执行数百次 CMUX 操作。
可编程自举 (Programmable Bootstrapping)
自举(Bootstrapping)是全同态加密中的圣杯,它允许我们在加密状态下刷新密文的噪声,从而支持无限深度的电路计算。在 TFHE 中,自举不仅能降噪,还能同时计算一个查表(Look-Up Table, LUT)函数,因此被称为“可编程自举”(PBS)。
TFHE 的自举过程主要由三个核心步骤组成:模数切换 (Modulus Switching)、盲旋转 (Blind Rotation) 和 样本提取 (Sample Extraction)。
模数切换 (Modulus Switching)
模数切换是将密文从一个大模数 q 转换到一个较小的模数 2N(其中 N 是多项式的度数)的过程。这一步是为了适应后续多项式乘法的需求。
原理与公式
给定一个 LWE 密文 c=(a0,…,an−1,b)∈Zqn+1,我们将其分量缩放并四舍五入到新的模数 2N:
a~i=⌊q2N⋅ai⌉∈Z2N
结果是一个新的 LWE 密文 c~∈Z2Nn+1。这个操作会丢弃低位信息(即噪声的一部分),但保留了消息所在的最高有效位(MSB)。虽然这引入了额外的舍入误差,但对于 LWE 密文来说,只要噪声足够小,消息就能被正确保留。
简单示例(模数切换)
假设 q=64,p=4 (Δ=16), n=4。密钥 s=(0,1,1,0)。
加密消息 m=1,得到密文 c=(−25,12,−3,7,26)∈Z645。
我们将其切换到模数 2N=32:
c~=(−13,6,−2,4,13)∈Z325
新密文解密后 b~−∑a~isi=13−(6−2)=9。
缩放回消息空间:⌊9/(32/4)⌉=⌊9/8⌉=1。消息保持不变。
盲旋转 (Blind Rotation)
这是自举中最昂贵但也最关键的一步。它的目标是将 LWE 密文中的相位(包含消息和噪声)转移到一个多项式的指数上。
核心思想
我们需要计算 X−φ~,其中 φ~=b~−∑a~isi 是模数切换后的近似相位。
由于 si 是加密的(作为自举密钥 BK 提供),我们不能直接计算 ∑a~isi。
我们从一个包含了查表函数的多项式 V(X) 开始,计算:
ACC=V(X)⋅X−b~⋅i=0∏n−1Xa~isi
这里 Xa~isi 的计算依赖于密钥位 si。如果 si=0,我们乘 1;如果 si=1,我们乘 Xa~i。
这正是 CMUX 门的作用!对于每个 i,我们执行:
ACC←CMUX(BKi,ACC⋅Xa~i,ACC)
经过 n 次迭代,累加器 ACC 将变成加密了 V(X)⋅X−φ~ 的 GLWE 密文。
多项式 V(X) 的常数项现在包含了 V(X) 在 −φ~ 处的取值。通过精心设计 V(X),我们可以让这个值等于我们想要的函数输出(例如去噪后的消息)。
盲旋转结束后,我们得到一个 GLWE 密文。我们需要从中提取出常数项,变回 LWE 密文。
过程
给定 GLWE 密文 C=(A0,…,Ak−1,B)∈Rqk+1,它加密了多项式 M(X)。
我们要提取 M(X) 的常数项 m0。
构造新的 LWE 密文 c=(a,b):
- b 直接取自 B 的常数项。
- a 的分量来自于 Ai 的系数,但顺序和符号需要调整(由于 XN=−1 的性质)。
具体来说,若 Ai=∑ai,jXj,则对应的 LWE 密钥部分为 (si,0,…,si,N−1)。
提取出的 LWE 向量部分为 (a0,0,−a0,N−1,…,−a0,1,…)。
这个操作是“免费”的(不增加噪声),它仅仅是系数的重排。
自举全流程
- 输入:LWE 密文 c,自举密钥 BK,查表多项式 TV。
- 模数切换:c→c~(模数 q→2N)。
- 初始化:ACC=(0,…,0,TV⋅X−b~)(平凡 GLWE 密文)。
- 盲旋转循环:
For i from 0 to n−1:
ACC=CMUX(BKi,ACC⋅Xa~i,ACC)
- 样本提取:从 ACC 中提取常数项,得到新的 LWE 密文 c′。
- 密钥切换(可选但通常需要):将 c′ 的密钥从大参数(盲旋转使用的)切换回原始 LWE 密钥,以便进行下一轮运算。
通过这个流程,TFHE 实现了在密文上计算任意函数并同时清除噪声的能力。