2021: corctf: 4096
This commit is contained in:
parent
e0173f270b
commit
29c5c5d48e
|
@ -0,0 +1,88 @@
|
||||||
|
# 4096
|
||||||
|
|
||||||
|
by [haskal](https://awoo.systems)
|
||||||
|
|
||||||
|
crypto / 360 pts / 219 solves
|
||||||
|
|
||||||
|
>I heard 4096 bit RSA is secure, so I encrypted the flag with it.
|
||||||
|
|
||||||
|
provided files: [source.py](source.py) [output.txt](output.txt)
|
||||||
|
|
||||||
|
## solution
|
||||||
|
|
||||||
|
inspecting the source you can see the provided source implements RSA. the weakness is it uses many
|
||||||
|
small primes instead of 2 large primes. this makes it extremely easy to factor the number
|
||||||
|
(factoring the public key in RSA leads to recovery of the private key)[^1]
|
||||||
|
|
||||||
|
```python
|
||||||
|
m = bytes_to_long(flag)
|
||||||
|
primes = [getPrime(32) for _ in range(128)]
|
||||||
|
n = prod(primes)
|
||||||
|
e = 65537
|
||||||
|
print(n)
|
||||||
|
print(pow(m, e, n))
|
||||||
|
```
|
||||||
|
|
||||||
|
i turned to my trusted factoring tool, [yafu](https://sourceforge.net/projects/yafu/) and _quickly_
|
||||||
|
discovered that in 2021 yafu is very crashy (at least on my system... i assume this is some glibc or
|
||||||
|
gmp ABI incompatibility)[^2]
|
||||||
|
|
||||||
|
yafu provides a shell in which you can invoke the `factor` operation
|
||||||
|
```
|
||||||
|
factor(50630448182626893495....)
|
||||||
|
```
|
||||||
|
|
||||||
|
this should complete in a few seconds even on old machines. it produces a list like
|
||||||
|
```
|
||||||
|
...
|
||||||
|
P10 = 3991834969
|
||||||
|
P38 = 66683226414537879762507759703783429499
|
||||||
|
C20 = 15613277632742914627
|
||||||
|
P10 = 3959814431
|
||||||
|
P10 = 3943871257
|
||||||
|
P10 = 2602521199
|
||||||
|
P10 = 3177943303
|
||||||
|
P10 = 3625437121
|
||||||
|
P10 = 2707095227
|
||||||
|
P10 = 3346647649
|
||||||
|
P10 = 2572542211
|
||||||
|
P10 = 2753147143
|
||||||
|
P10 = 3488338697
|
||||||
|
P10 = 2525697263
|
||||||
|
P10 = 3291377941
|
||||||
|
P10 = 4141964923
|
||||||
|
...
|
||||||
|
```
|
||||||
|
|
||||||
|
some of the output was not factored enough, there are still some composite numbers and incorrectly
|
||||||
|
identified primes -- we know from the source that all the primes are 32 bit so we're looking for all
|
||||||
|
`P10` lines. the solution is simple just run `factor(...)` again on any non-P10 outputs... and this
|
||||||
|
is where i wrote a quick script to do this automatically except for some reason yafu consistently
|
||||||
|
crashed when run under python (;___;) so i ended up doing it by hand (time wasted that could be
|
||||||
|
spent pwning but whatever)
|
||||||
|
|
||||||
|
anyway once you have all the primes you just need to calculate the private key and do decryption.
|
||||||
|
the private key is computed by `65537^{-1} mod phi`, where `phi` (the easier one to calculate) is
|
||||||
|
the product of all the primes minus 1. then do `{encrypted message}^d mod n` and you have the flag
|
||||||
|
|
||||||
|
```python
|
||||||
|
[ins] In [1]: import math
|
||||||
|
|
||||||
|
[nav] In [2]: factors = [int(x) for x in open("factors")]
|
||||||
|
|
||||||
|
[nav] In [3]: phi = math.prod([x - 1 for x in factors])
|
||||||
|
|
||||||
|
[nav] In [4]: [n, enc] = [int(x) for x in open("output.txt")]
|
||||||
|
|
||||||
|
[ins] In [5]: d = pow(65537, -1, phi)
|
||||||
|
|
||||||
|
[ins] In [6]: dec = pow(enc, d, n)
|
||||||
|
|
||||||
|
[ins] In [7]: dec.to_bytes(dec.bit_length()//8+1,"big")
|
||||||
|
Out[8]: b'corctf{to0_m4ny_pr1m3s55_63aeea37a6b3b22f}'
|
||||||
|
```
|
||||||
|
|
||||||
|
[^1]: i assume we are familiar with RSA but if not, wikipedia is a good reference:
|
||||||
|
<https://en.wikipedia.org/wiki/RSA_(cryptosystem)#Operation>
|
||||||
|
|
||||||
|
[^2]: time to get a new factoring tool of choice probably
|
|
@ -0,0 +1,2 @@
|
||||||
|
50630448182626893495464810670525602771527685838257974610483435332349728792396826591558947027657819590790590829841808151825744184405725893984330719835572507419517069974612006826542638447886105625739026433810851259760829112944769101557865474935245672310638931107468523492780934936765177674292815155262435831801499197874311121773797041186075024766460977392150443756520782067581277504082923534736776769428755807994035936082391356053079235986552374148782993815118221184577434597115748782910244569004818550079464590913826457003648367784164127206743005342001738754989548942975587267990706541155643222851974488533666334645686774107285018775831028090338485586011974337654011592698463713316522811656340001557779270632991105803230612916547576906583473846558419296181503108603192226769399675726201078322763163049259981181392937623116600712403297821389573627700886912737873588300406211047759637045071918185425658854059386338495534747471846997768166929630988406668430381834420429162324755162023168406793544828390933856260762963763336528787421503582319435368755435181752783296341241853932276334886271511786779019664786845658323166852266264286516275919963650402345264649287569303300048733672208950281055894539145902913252578285197293
|
||||||
|
15640629897212089539145769625632189125456455778939633021487666539864477884226491831177051620671080345905237001384943044362508550274499601386018436774667054082051013986880044122234840762034425906802733285008515019104201964058459074727958015931524254616901569333808897189148422139163755426336008738228206905929505993240834181441728434782721945966055987934053102520300610949003828413057299830995512963516437591775582556040505553674525293788223483574494286570201177694289787659662521910225641898762643794474678297891552856073420478752076393386273627970575228665003851968484998550564390747988844710818619836079384152470450659391941581654509659766292902961171668168368723759124230712832393447719252348647172524453163783833358048230752476923663730556409340711188698221222770394308685941050292404627088273158846156984693358388590950279445736394513497524120008211955634017212917792675498853686681402944487402749561864649175474956913910853930952329280207751998559039169086898605565528308806524495500398924972480453453358088625940892246551961178561037313833306804342494449584581485895266308393917067830433039476096285467849735814999851855709235986958845331235439845410800486470278105793922000390078444089105955677711315740050638
|
|
@ -0,0 +1,15 @@
|
||||||
|
from Crypto.Util.number import getPrime, bytes_to_long
|
||||||
|
from private import flag
|
||||||
|
|
||||||
|
def prod(lst):
|
||||||
|
ret = 1
|
||||||
|
for num in lst:
|
||||||
|
ret *= num
|
||||||
|
return ret
|
||||||
|
|
||||||
|
m = bytes_to_long(flag)
|
||||||
|
primes = [getPrime(32) for _ in range(128)]
|
||||||
|
n = prod(primes)
|
||||||
|
e = 65537
|
||||||
|
print(n)
|
||||||
|
print(pow(m, e, n))
|
Loading…
Reference in New Issue