ctf rsa2

RSA2
题目
e = 65537

n=248254007851526241177721526698901802985832766176221609612258877371620580060433101538328030305219918697643619814200930679612109885533801335348445023751670478437073055544724280684733298051599167660303645183146161497485358633681492129668802402065797789905550489547645118787266601929429724133167768465309665906113

dp=905074498052346904643025132879518330691925174573054004621877253318682675055421970943552016695528560364834446303196939207056642927148093290374440210503657

c=140423670976252696807533673586209400575664282100684119784203527124521188996403826597436883766041879067494280957410201958935737360380801845453829293997433414188838725751796261702622028587211560353362847191060306578510511380965162133472698713063592621028959167072781482562673683090590521214218071160287665180751

解题思路
题目给出了e,n,dp,c,求解明文

常规的思路是将n分解为p和q,但是这里给的n有309位之长,直接爆破求解显然难度很大

可以关注到题目所给的dp,看一下这个dp怎么用

进行一下公式推导:

dp = d % (p-1) ①

d = dp + k1 * (p-1) ②

d * e = 1 + k2(p-1)(q-1) ③

把②代入③,得到

e * (dp + k1(p-1)) = 1 + k2(p-1)(q-1)

为把系数k消掉,两边同时对(p-1)取模

e * dp % (p - 1) = 1

e * dp = 1 + k(p - 1)

由③就可以导出p与e、dp的关系

p - 1 = (e * dp - 1) / k ④

但是这里引入了一个系数k,这个k该怎么处理呢

④变形一下有

k = (e * dp - 1) / (p-1)

又由①,可以判断出dp < (p-1)

所以可以得到k = (e * dp - 1) / (p-1) < e

e = 65537,因此k的范围有了约束

至此,根据④式可以求解p

具体思路如下:

1.遍历k,k的范围是(1-65537)

2.判断(e * dp - 1)能否整除k,若能,则p = (e * dp - 1) / k + 1

3.判断n能否整除p,若能,则q = n / p

4.判断p,q是否都为素数,若都通过素性检验,则n成功分解出p和q

5.有了p、q之后,就可以计算出私钥d,进行解密得到flag

附上代码:

import gmpy2
import  binascii
    
e = 65537
n = 248254007851526241177721526698901802985832766176221609612258877371620580060433101538328030305219918697643619814200930679612109885533801335348445023751670478437073055544724280684733298051599167660303645183146161497485358633681492129668802402065797789905550489547645118787266601929429724133167768465309665906113
dp = 905074498052346904643025132879518330691925174573054004621877253318682675055421970943552016695528560364834446303196939207056642927148093290374440210503657

c = 140423670976252696807533673586209400575664282100684119784203527124521188996403826597436883766041879067494280957410201958935737360380801845453829293997433414188838725751796261702622028587211560353362847191060306578510511380965162133472698713063592621028959167072781482562673683090590521214218071160287665180751
 
tmp = e * dp -1
#根据联立条件有: e*dp = 1 + k(p-1),故求解p的式子为:(p-1) = (e*dp-1) / k
for k in range(1, e):#因为K上限只到e,故遍历求解
    if tmp % k == 0:#验证(p-1)是否为整除结果
        p = (tmp // k) + 1
        if n % p == 0:#验证p能否被n整除
            q = n // p
            if gmpy2.is_prime(p) and gmpy2.is_prime(q):#验证求解的p, q是否为素数
               # print(k)
                print("N的分解结果为 : ")
                print("%d = %d * %d" % (n, p, q))
                break

d = gmpy2.invert(e,(p-1)*(q-1)) # 求逆元,de = 1 mod fai(n)
m = gmpy2.powmod(c,d,n)# 幂取模,求明文

m = hex(m)[2:]     
print("密文数据为:0x" + m)
flag = binascii.unhexlify(m)
print(flag)

flag
flag{wow_leaking_dp_breaks_rsa?_98924743502}
 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值