代理重加密

代理重加密

什么是代理重加密(PRE)

代理重加密(Proxy re-encryption)通过代理服务器将一个用户用自己公钥加密的密文转换为另一个用户可以用自己私钥解密的密文,且不泄露用户的私钥和明文信息,从而实现信息的共享。

代理重加密常用于云存储中,因为在云存储中,基于用户数据隐私性考虑,用户存放在云端的数据都是密文形式存在的。而云环境中存在着大量数据共享的场景。由于数据拥有者对云服务提供商并不完全信任,不能将解密密文的密钥发送给云端,由云端来解密并分享出去。数据拥有者自己下载密文解密后,再用数据接收方的公钥加密并分享,无疑给数据拥有者带来很大的麻烦,同时也失去了云端数据共享的意义。代理重加密可以在不泄漏数据拥有者解密密钥的情况下,实现云端密文数据共享。

具体过程

直观的理解:

假设 Alice 想要将消息 M 存储到云服务器上,并且 Bob 想要查看消息 M 。由于 Alice 不想让云服务器知道消息 M ,因此他可以使用代理重加密按照下面的过程安全的与 Bob 分享消息 M 。

  1. Alice: 将明文 M 用自己的公钥PKAPK_A加密,得到CPKA=EncPKA(M)C_{PK_A}=Enc_{PK_A} (M),其中的 M 就是 Alice 想要给 Bob 的明文内容。
  2. Alice:将CPKAC_{PK_A}发给半诚实代理商,并为其生成重加密密钥RKABRK_{A→B}
  3. Proxy:用 Alice 生成的重加密密钥 RKABRK_{A→B} 将密文 CPKAC_{PK_A} 转化为 Bob 的私钥能够解密的密文 CPKBC_{PK_B},其中Proxy只是提供计算转化服务,无法获取明文;
  4. Proxy:将生成好的CPKBC_{PK_B}发给Bob;
  5. Bob:解密获得 Alice 想要共享的明文 M;

该过程主要解放了A,A只需生成代理密钥,具体文件的传输,文件的转化,文件的存放都是半诚实代理商完成的。

形式化定义

代理重加密可由以下五个算法构成:

KeyGen:根据一个系统安全参数生成用户的密钥对。

Encrypt:用户是用自己的公钥加密消息 M 得到相应的密文 C,并将密文 C 上传给代理服务器。

ReGenKey:用户使用数据接收者的公钥生成重加密密钥rk,并发送给代理服务器。

ReEncrypt:代理服务器使用重加密密钥 rk 对密文C进行重加密,得到重加密密文C’ ,然后将C’发送给数据接收者。

Decrypt:数据接收者使用自己的私钥解密 C’ 得到明文 M 。

下面为图解:

具体实例

基于ElGamal的代理重加密

假设 Alice 想要将消息 M 存储到云服务器上,并且 Bob 想要查看消息 M 。由于 Alice 不想让云服务器知道消息 M ,因此他可以使用代理重加密按照下面的过程安全的与 Bob 分享消息 M 。

KeyGen

Alice 输入ElGamal加密的公共参数 pp ,然后生成用户 Alice 和 Bob 的公私钥对分别为 (skA,PKA)(sk_A,PK_A)(skB,PKB)(sk_B,PK_B)。其中 PKA=gskAPK_A=g^{sk_A} , PKB=gskBPK_B=g^{sk_B}

Encrypt

假设 Alice 想要将消息 M 存储到代理服务器上。Alice 使用自己的公钥使用 ElGamal加密算法加密消息 M 得到相应的密文 C=(C1,C2)=(gr,MpkAr)C=(C_1,C_2)=(g^r,M\cdot pk_A^r),其中 $r\in_R Z_p^* $是一个随机数。Alice 将密文 C 上传给代理服务器。

ReGenKey

Alice 使用数据接收者 Bob 的公钥生成重加密密钥 rk=skA/H(PKBskA)rk= sk_A / H(PK_B^{sk_A}),并将 rk 发送给代理服务器。

ReEncrypt

代理服务器使用重加密密钥 rk 对密文C进行重加密,得到重加密密文C=(C1,C2)=(C1rk,C2)C'=(C_1',C_2')=(C_1^{rk},C_2),然后将C’发送给数据接收者。

Decrypt

Bob 使用自己的私钥 skBsk_B 解密 C’ 得到明文 M=C2/C1H(PKAskB)M=C_2' / C_1'^{H(PK_A^{sk_B})}

正确性验证很容易,这里不再赘述。

代理重加密的优化

由于非对称公私钥加密的效率低下,对于较大文件的数据共享是不合适,所以需要对PRE流程进行优化。我们可以使用对称加密来保护数据,使用PRE来保护对称加密的密钥。详细流程如下所示。

解释如下:

  1. Alice生成 sk1,pk1sk_1, pk_1,Bob 生成 sk2,pk2sk_2, pk_2
  2. Alice生成辅助信息 AuxAux ,并结合自己的公钥 pk1pk_1 计算出对称密钥 K;用 K 加密大文件 M 得到密文 C ;然后将 (C,Aux)(C,Aux) 发送给代理Proxy
  3. 当 Bob 想要使用消息 M 时,他首先向Alice发送自己的公钥 pk2pk_2
  4. Alice根据Bob的公钥 pk2pk_2 和自己的私钥 sk1sk_1 生成重加密密钥 delkey 并将 delkey 发送给 Proxy
  5. Proxy 用delkey重加密密文C。得到newC,并将newC发送给Bob
  6. Bob用自己的私钥 sk2sk_2AuxAux 计算对称密钥 K,并用 K 解密 newC 得到 M .

基于对称加密的代理重加密

Setup

假设 g 是椭圆曲线群 G 的生成器,p 是一个大素数,也是 G 的阶。HiH_i,i=2, 3, 4是哈希函数。m 是 Alice 想要共享的消息或明文。Server 是第三方服务器。

KeyGen

对于任意一个用户,生成随机数 skRZpsk \in_R Z_p作为私钥,计算公钥 PK=gskPK=g^{sk}。我们假设Alice和Bob的密钥对分别是(skA,PKA=gskA)(sk_A,PK_A=g^{sk_A})(skB,PKB=gskB)(sk_B,PK_B=g^{sk_B})

Encrypt

假设 Alice 想要将消息 M 存储到代理服务器上。Alice 。执行下面的操作:

  1. 生成两个随机数 e,vRZpe,v\in_R Z_p 并计算 E=ge,V=gvE=g^e,V=g^v
  2. 计算 s=v+rH2(EV)s=v+r\cdot H_2(E||V)
  3. 使用AES的密钥生成算法 G\mathcal{G} 计算 K=G((PKA)e+v)K=\mathcal{G}((PK_A)^{e+v})
  4. 使用AES加密算法 E\mathcal{E} 计算消息 m 的密文为 c=EAES(m,K)c=\mathcal{E}_{AES}(m,K)
  5. Aux=(E,V,s)Aux=(E,V,s) , Alice 将 (Aux,c)(Aux,c)发送给代理服务器。

ReGenKey

Alice 使用数据接收者 Bob 的公钥生成重加密密钥:

  1. 生成随机数 xARZpx_A \in_R Z_p 计算 XA=gxAX_A=g^{x_A}
  2. 计算 d=H3(XApkBPKBXA)d=H_3(X_A||pk_B||PK_B^{X_A})
  3. rk=skAd1rk= sk_A \cdot d^{-1},并将 rk 发送给代理服务器。

ReEncrypt

代理服务器使用重加密密钥 rk 对密文C进行重加密如下:

  1. 判断 gs=VEH(EV)g^s=V\cdot E^{H(E||V)} 是否成立 ,
  2. 如果成立则计算 E=Erk,V=VrkE'=E^{rk},V'=V^{rk} , 令 Aux=(E,V,s)Aux'=(E',V',s)
  3. 代理服务器将 (Aux,c)(Aux',c) 发送给数据接收者 Bob。

Decrypt

Bob 使用 AuxAux' 和自己的私钥 skBsk_B 解密密文:

  1. 计算 d=H3(XAPKBSskB)d=H_3(X_A||PK_B||S^{sk_B})
  2. 计算 K=G((EV)d)K=\mathcal{G}((E'\cdot V')^d)
  3. 解密密文得到明文 m=DAES(c,K)m=\mathcal{D}_{AES}(c,K)

大佬Github上的实现: