3. 基于不经意传输(OT)的隐私信息检索方案

基于不经意传输(OT)的隐私信息检索方案 学习卡片

协议目标与安全边界

1-out-of-2 不经意传输(OT)要同时满足两个约束:接收方只能解出自己选择的那一条消息,发送方无法得知接收方选了哪一条。本案例用 RSA 盲化思想构造一个可运行的 OT 协议,并把它用于隐私信息检索(PIR):发送方持有两条记录 m0、m1,接收方选择索引 c ∈ {0,1},最终只得到 mc。

协议的核心是:接收方生成两个随机数 k0、k1,只把其中一个(对应选择位)的盲化值发给发送方;发送方用 RSA 私钥对两个盲化值分别签名,接收方只能去盲得到自己那一侧的密钥,另一侧因缺少对应随机数而无法还原。

参数与消息编码

为了让两条消息都能被 RSA 运算处理,先把消息编码为整数。示例中取小素数 p=61、q=53,则 n=3233,φ(n)=3120,选 e=17,求得 d=2753。消息 m0=42、m1=99 均小于 n,可直接参与运算。

符号含义示例值
nRSA 模数3233
e公钥指数17
d私钥指数2753
m0, m1发送方两条消息42, 99
c接收方选择位0 或 1

协议执行流程

  1. 接收方随机生成 k0、k1,并计算 v = (k_c + m_c) mod n,把 v 发给发送方。
  2. 发送方计算 s0 = (v - m0)^d mod n、s1 = (v - m1)^d mod n,把 s0、s1 发回。
  3. 接收方计算 k_c' = (s_c - k_c) mod n,得到 m_c = (v - k_c') mod n。

发送方看到的是 v,它无法区分 v 来自 c=0 还是 c=1,因为 k0、k1 是接收方私有的随机数。接收方只能还原 k_c,另一侧的 k_{1-c} 从未离开本地,因此无法解出另一条消息。

1-out-of-2 OT 数据流与密钥还原关系 接收方 R 私有随机数 k0, k1 选择位 c 计算 v = k_c + m_c 本地保留 k0, k1 仅发送 v 收到 s0, s1 k_c' = s_c - k_c m_c = v - k_c' 只得到 m_c 发送方 S 持有 m0, m1 RSA 私钥 d 收到 v s0 = (v-m0)^d s1 = (v-m1)^d 无法区分 c v 与 k0/k1 无关 两条消息均被盲化 ① 发送 v = k_c + m_c ② 返回 s0, s1 ③ R 仅能还原 m_c

可运行实现

下面代码用 Python 实现上述协议,并验证接收方只能得到所选消息、发送方无法从 v 推断选择位。

import random

# RSA 参数(教学用小素数)
p, q = 61, 53
n = p * q            # 3233
phi = (p - 1) * (q - 1)  # 3120
e = 17
d = pow(e, -1, phi)  # 2753

m0, m1 = 42, 99

def ot_sender(v, m0, m1, d, n):
    s0 = pow((v - m0) % n, d, n)
    s1 = pow((v - m1) % n, d, n)
    return s0, s1

def ot_receiver(c, m0, m1, e, n):
    k0 = random.randrange(1, n)
    k1 = random.randrange(1, n)
    kc = k0 if c == 0 else k1
    mc = m0 if c == 0 else m1
    v = (kc + mc) % n
    return v, k0, k1, kc, mc

def ot_finish(c, v, s0, s1, kc, n):
    sc = s0 if c == 0 else s1
    kc_prime = (sc - kc) % n
    return (v - kc_prime) % n

# 接收方选择 c=1
c = 1
v, k0, k1, kc, mc = ot_receiver(c, m0, m1, e, n)
s0, s1 = ot_sender(v, m0, m1, d, n)
result = ot_finish(c, v, s0, s1, kc, n)

print("选择位 c =", c)
print("接收方得到 =", result, "期望 =", mc)
print("另一条消息是否泄露 =", result == (m0 if c == 1 else m1))

运行后输出 接收方得到 = 99 期望 = 99,且 另一条消息是否泄露 = False,说明接收方只拿到了 m1,没有拿到 m0。

验证与结果判读

  • 正确性:接收方还原出的 result 必须等于 mc。若不等,检查 v 是否在发送方计算前被取模、s_c 是否选对。
  • 隐私性:发送方只看到 v,而 v = k_c + m_c 中的 k_c 是接收方私有随机数,因此 v 对 c=0 和 c=1 的分布不可区分。
  • 边界检查:消息必须满足 0 ≤ m < n;若消息较长,应先分块或做编码映射,不能直接对超长整数做单次 RSA 运算。
本案例的 OT 是“半诚实模型”下的基础构造:双方按协议执行,但可能试图从收到的数据推断对方隐私。若需要抵抗恶意参与方,还需加入零知识证明或承诺机制。
示例中的 RSA 参数仅用于教学演示,实际部署必须使用 2048 位以上模数,并配合 OAEP 等填充方案,否则会面临小消息空间攻击和确定性加密风险。