密码学之RSA
RSA 加密算法是一种非对称加密算法,加解密使用不同的密钥。RSA的安全性依赖于大数分解的难度。
RSA基本原理
公钥私钥的生成
1、找出两个大素数p,q
2、n=pq
3、根据欧拉函数可得:φ(n) = φ(p)φ(q) = (p-1)(q-1)
4、生成公钥e:1<e<φ(n),且e与φ(n)互素
5、计算私钥d:e*d ≡ 1(mod φ(n))
加密:c = me mod n
解密:m = cd mod n
RSA-CRT基本原理(CRT:中国剩余定理)
目的:降低指数加快RSA算法的解密过程。
公钥私钥的生成与基本RSA生成步骤一致。
计算额外的dp、dq、qlnv
dp = d % (p - 1) ##满足dp ≡ d(mod (p-1)) dq = d % (q - 1) ##满足dq ≡ d(mod (q-1))
qlnv * q ≡ 1(mod p) ##qlnv是q在模p下的逆
加密:c = me mod n
解密:m1 = cdp mod p
m2 = cdq mod q
h = qlnv * (m1 - m2) mod p
m = m2 + h * q
BUUCTF:RSA
在一次RSA密钥对生成中,假设p=473398607161,q=4511491,e=17
求解出d作为flga提交
解析:e*d ≡ 1 (mod φ(n)) 等价于 e*d ≡ 1 (mod (p-1)(q-1)),即计算e在模(p-1)(q-1)下的乘法逆元
使用sagemath计算
sage: p = 473398607161
sage: q = 4511491
sage: e = 17
sage: inverse_mod(e, (p-1)*(q-1))
125631357777427553
BUUCTF:rsarsa
Math is cool! Use the RSA algorithm to decode the secret message, c, p, q, and e are parameters for the RSA algorithm.
p = 9648423029010515676590551740010426534945737639235739800643989352039852507298491399561035009163427050370107570733633350911691280297777160200625281665378483
q = 11874843837980297032092405848653656852760910154543380907650040190704283358909208578251063047732443992230647903887510065547947313543299303261986053486569407
e = 65537
c = 83208298995174604174773590298203639360540024871256126892889661345742403314929861939100492666605647316646576486526217457006376842280869728581726746401583705899941768214138742259689334840735633553053887641847651173776251820293087212885670180367406807406765923638973161375817392737747832762751690104423869019034
Use RSA to find the secret message
解析:解密方程为:m = cd mod n,其中n=p*q,e*d ≡ 1(mod φ(n))
使用sagemath计算
sage:p=9648423029010515676590551740010426534945737639235739800643989352039852507298491399561035009163427050370107570733633350911691280297777160200625281665378483
sage:q=11874843837980297032092405848653656852760910154543380907650040190704283358909208578251063047732443992230647903887510065547947313543299303261986053486569407
sage:c=83208298995174604174773590298203639360540024871256126892889661345742403314929861939100492666605647316646576486526217457006376842280869728581726746401583705899941768214138742259689334840735633553053887641847651173776251820293087212885670180367406807406765923638973161375817392737747832762751690104423869019034
sage: e = 65537
##计算私钥
sage: d = inverse_mod(e, (p-1)*(q-1))
##解密出明文,模幂运算
sage: n = p * q
sage: power_mod(c, d, n)
5577446633554466577768879988
BUUCTF:RSA1
dp、dq泄露
已知
p = 8637633767257008567099653486541091171320491509433615447539162437911244175885667806398411790524083553445158113502227745206205327690939504032994699902053229 q = 12640674973996472769176047937170883420927050821480010581593137135372473880595613737337630629752577346147039284030082593490776630572584959954205336880228469 dp = 6500795702216834621109042351193261530650043841056252930930949663358625016881832840728066026150264693076109354874099841380454881716097778307268116910582929 dq = 783472263673553449019532580386470672380574033551303889137911760438881683674556098098256795673512201963002175438762767516968043599582527539160811120550041 c = 24722305403887382073567316467649080662631552905960229399079107995602154418176056335800638887527614164073530437657085079676157350205351945222989351316076486573599576041978339872265925062764318536089007310270278526159678937431903862892400747915525118983959970607934142974736675784325993445942031372107342103852
求明文
方法一:根据RSA-CRT的解密原理得到明文
sage:p=8637633767257008567099653486541091171320491509433615447539162437911244175885667806398411790524083553445158113502227745206205327690939504032994699902053229 sage:q=12640674973996472769176047937170883420927050821480010581593137135372473880595613737337630629752577346147039284030082593490776630572584959954205336880228469 sage:dp=6500795702216834621109042351193261530650043841056252930930949663358625016881832840728066026150264693076109354874099841380454881716097778307268116910582929 sage:dq=783472263673553449019532580386470672380574033551303889137911760438881683674556098098256795673512201963002175438762767516968043599582527539160811120550041 sage:c=24722305403887382073567316467649080662631552905960229399079107995602154418176056335800638887527614164073530437657085079676157350205351945222989351316076486573599576041978339872265925062764318536089007310270278526159678937431903862892400747915525118983959970607934142974736675784325993445942031372107342103852 sage: m1 = power_mod(c,dp,p) sage: m2 = power_mod(c,dq,q) sage: h = inverse_mod(q,p) * (m1 - m2) % p sage: m = m2 + h * q
11630208090204506176302961171539022042721137807911818876637821759101
##看writeup才知道要把十进制转为十六进制。额,还是经验不够!!
sage: s = hex(m) ##转为16进制
sage: ls = [chr(int(s[i:i+2], 16)) for i in range(2,len(s),2)] ##2个十六进制为一个字节,根据ASCII码转为对应字符
sage: "".join(ls)
'noxCTF{W31c0m3_70_Ch1n470wn}'
方法二:中国剩余定理求出d,再使用普通RSA的解密原理得到明文。
已知
dp ≡ d(mod (p-1)) dq ≡ d(mod (q-1))
可得
d ≡ dp(mod (p-1))
d ≡ dq(mod (q-1))
sage: d = crt(dp,dq,p-1,q-1)
sage: m = power_mod(c,d,p*q)
11630208090204506176302961171539022042721137807911818876637821759101
BUUCTF:RSA2
dp泄露
e = 65537 n = 248254007851526241177721526698901802985832766176221609612258877371620580060433101538328030305219918697643619814200930679612109885533801335348445023751670478437073055544724280684733298051599167660303645183146161497485358633681492129668802402065797789905550489547645118787266601929429724133167768465309665906113 dp = 905074498052346904643025132879518330691925174573054004621877253318682675055421970943552016695528560364834446303196939207056642927148093290374440210503657 c = 140423670976252696807533673586209400575664282100684119784203527124521188996403826597436883766041879067494280957410201958935737360380801845453829293997433414188838725751796261702622028587211560353362847191060306578510511380965162133472698713063592621028959167072781482562673683090590521214218071160287665180751
解析如下:
dp = d % (p-1) (1)
由dp = d % (p-1),得 dp = k1(p-1) + d (2)
由e * d ≡ 1(mod φ(n)) ,得 e * d = k2(p-1)(q-1) + 1 (3)
(2)带入(3),得 e * (dp + k1(p-1)) = k2(p-1)(q-1) + 1
两边对(p-1)取模即可消掉k1、k2,得到e * dp % (p-1) = 1
即 e * dp = k(p-1) + 1 (4)
根据(4)可以求解出p,p - 1 = (e *dp -1) / k
k = (e * dp - 1) / (p - 1)
由(1)知dp < (p-1),因此k < e
k遍历[1,e),查看(4)式是否正确,求出p,q,并检验p,q是否为素数
sagemath:
sage: for k in range(1,e):
....: p = ((e * dp -1) // k) + 1
....: if is_prime(p):
....: q = n // p
....: if is_prime(q):
....: print("p:{0}".format(p))
....: print("q:{0}".format(q))
....: print("n:{0}".format(p*q)) ##验证分解结果是否正确
....: break
知道了p、q、e,即可求出私钥d,进而解密出明文m。
sage: d = inverse_mod(e, (p-1)*(q-1)) sage: m = power_mod(c,d,p*q)
3670434958110785066911905751469631231338751225710158680692616521935747246580688484040488309932916523151997
sage: s = hex(m)
sage: ls = [chr(int(s[i:i+2], 16)) for i in range(2, len(s), 2)]
sage: "".join(ls)
'flag{wow_leaking_dp_breaks_rsa?_98924743502}'