蓝桥杯网络安全春秋赛 Crypto RSA

蓝桥杯网络安全春秋赛 Crypto RSA

题目

某公司为了保护其重要数据,使用了RSA加密算法。该公司以同一个N为模数,为Alice和Bob分别生成了不同的公钥和与之相应的私钥。Alice和Bob都使用自己的公钥对同一条明文m进行加密,分别得到密文c1和c2。假设你是一名密码安全研究者,你已获取了N值、两个密文和公钥,能否使用RSA的相关知识还原出明文m呢?

#!python3.9
from Crypto.Util.number import *
from flag import flag
import gmpy2
import random

random.seed(123456)

m = bytes_to_long(flag)
e1 = random.randint(100000000, 999999999)
e2 = 65537
n = 7265521127830448713067411832186939510560957540642195787738901620268897564963900603849624938868472135068795683478994264434459545615489055678687748127470957
c1 = pow(m,e1,n)
c2 = pow(m,e2,n)
print(c1)
print(c2)

# 3315026215410356401822612597933850774333471554653501609476726308255829187036771889305156951657972976515685121382853979526632479380900600042319433533497363
# 1188105647021006315444157379624581671965264301631019818847700108837497109352704297426176854648450245702004723738154094931880004264638539450721642553435120

根据题目提示,这是共模攻击
这道题与平常的共模攻击不太一样的就是e1是随机产生、未知的
我们可以通过爆破的方式得到e1
代码如下:

import gmpy2
import random

random.seed(123456)

n = 7265521127830448713067411832186939510560957540642195787738901620268897564963900603849624938868472135068795683478994264434459545615489055678687748127470957
c1 = 3315026215410356401822612597933850774333471554653501609476726308255829187036771889305156951657972976515685121382853979526632479380900600042319433533497363
c2 = 1188105647021006315444157379624581671965264301631019818847700108837497109352704297426176854648450245702004723738154094931880004264638539450721642553435120
e2 = 65537

while True:
    e1 = random.randint(100000000, 999999999)
    s = gmpy2.gcdext(e1, e2)  # 拓展欧几里得算法,计算s1和s2
    m1 = gmpy2.powmod(c1, s[1], n)
    m2 = gmpy2.powmod(c2, s[2], n)

    m = (m1 * m2) % n
    c = pow(m, e1, n)   # 爆破e1
    if c == c1:
        print(bytes.fromhex(hex(m)[2:]))  # 16进制转文本
        break
# flag为:flag{359a1693-7bce-4fbc-87fa-111cdffaa0e8}

共模攻击是指用两个及以上的公钥(n, e)来加密同一条信息m
c1 = pow(m, e1, n)
c2 = pow(m, e2, n)
当e1, e2互质,有gcd(e1, e2) = 1
根据扩展欧几里得算法,一定存在整数x, y使gcd(a, b) = ax + by
即,e1*s1 + e2*s2 = 1
公式推导:

两条幂运算性质:
(a * b) % p = (a % p * b % p) % p
a^b % p = ((a % p)^b) % p
因为,
c1 = m^e1 % n,c2 = m^e2 % n,e1 * s1 + e2 * s2 = 1
所以有,
m = m % n
  = m^1 % n
  = m^(e1 * s1 + e2 * s2) % n
  = (m^(e1 * s1) % n * m^(e2 * s2) % n) % n
  = (c1^s1 % n * c2^s2 % n) % n

你可能感兴趣的:(蓝桥杯,密码学)