n00bzCTF SEETF2022

n00bz CTF 与 SEETF 2022的一些题。

这两个都没有怎么打,写了几道简单的就润了。n00bz的服务器炸了一天才好,还有附件编码错误的问题, 😦

n00bz CTF

2022/6/5

好,听名字就非常适合我。

这题全部都是用Discord发的,一开始找了半天没找到题目附件… 后面看discord里面讨论好像是网站出问题没法显示链接。

Crypto

Playing with xor

这题题目其实讲的不太清楚。

1
2
3
4
5
6
7
8
9
10
from Crypto.Util.number import *
from pwn import xor
flag = b'n00bz{pREDACTED}'
key1 = b'REDACTED'
enc = b''
for i in range(len(flag)):
enc += xor(key1[i],flag[i])
print(enc)
# _\x03\x03U\x11\x1e\t]\x07J\x06\x05\x02&F\x02G_4\x1dICl^\x07\x19V&]\x02X\x044\x15\x15\x05J\x02Y\x0c:\x0e\x00G[h\rT\x0b\x02N

通过一开始的明文 b’n00bz{p‘ 可以解出一个 1337key。然后循环用这个进行异或即可得到结果。

一开始我还以为是新接出来的key会用到下一段明文的加密,没想就这一个密钥,他这个加密函数搞得好像key和flag一样长一样。属实有些迷惑。

1
2
3
4
5
6
7
8
9
10
11
from Crypto.Util.strxor import strxor

out = b'_\x03\x03U\x11\x1e\t]\x07J\x06\x05\x02&F\x02G_4\x1dICl^\x07\x19V&]\x02X\x044\x15\x15\x05J\x02Y\x0c:\x0e\x00G[h\rT\x0b\x02N'

flag = [b'n00bz{p']
for i in range(1,len(out)//7):
flag.append(strxor(b'1337key', out[7*i:7*i+7]))
flag.append(strxor(b'13', out[49:]))
print(b''.join(flag))

# n00bz{pl4y1ng_w1th_x0r_m0r3_l1k3_pl4y1ng_w1th_f1r3}

RSA

附件网站崩了拿不到代码。先放着。

后面从discord里面看到别人发了这个文件。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
# ct = 68915718021581205938132340378
# n = 22964326243465188806208175092817347325223751455203934839482603060029805229708465878030254819573089332477084079330445929855173787412006349904864930449245982063200060526847746608051441362052994064461426109292644943462306467765210530381760387813568149905672759271878822092979239650360475796179311415340966347044401497301347973838444826544061998479163636946750265778097717211762208385963205388216125639236403616607313423716206061201112615302831337395011064188536794425701313580122604533837935452384701344503773605128479669035610395170026350607423780797383865621285538151344219282466601404674101508588637419153433890102137
# s = 6747770137526404810839680591618349902868945426501581276399132116507818856417271976886226143238796548185022079396435297411063351895882402872038955136430497260880818613647851713479263986391308789043197324119239260033630040630976512064481721240642729114116561261667588426398515959668695454587899042998666589705506998832917739337175589667828567571421541128057015371328723095841794613223799998429126797512729366352049800447550388154359724453576012916007310993864290045596969157854816882402679820492333445924724199994952395214639223249892224753494733720946542351810699104265693993026233289328344375145590992008664182919067
from Crypto.Util.number import *
p = getPrime(1024)
q = getPrime(1024)
n = p*q
e = 65537
flag = b'REDACTED'
flag_int = bytes_to_long(flag)
phi = (p-1)*(q-1)
ct = pow(flag_int,e,n)
#assert ct = 0xdeadbeefdeadbeefdeadbeef + 1337 + 1337 + 1337
d = inverse(e,phi)
s = pow(flag_int,d,n)
print(f's = {s}')
print(f'n = {n}')
print(f'ct = {ct}')

这里给出了m对e的加密和m对d加密。

那么我们有

me=ctmodnmd=smodned=1mod(p1)(q1)m^e = ct \, mod \,n \\ m^d = s \, mod \,n \\ ed = 1 \, mod \,(p-1)(q-1)

emm, 想了一下没想出来怎么写,但是这个s实际上m的签名啊。那么我们只需要直到公钥e就行了。一般来说公钥基本上都是0x10001也就是65537。所以我就试了一下直接用0x10001对s进行验证。没想到还真是。

1
# n00bz{pl34s3_s1gn_h3r3_4nd_h3r3_4nd_h3r3...}

SEETF 2022

2022/6/5

最后四个小时看看。

Crypto

Close Enough

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
from Crypto.Util.number import getPrime, bytes_to_long
from Crypto.PublicKey import RSA
from secret import flag, getNextPrime

p = getPrime(1024)
q = getNextPrime(p)
n = p * q
e = 65537

key = RSA.construct((n, e)).export_key().decode()

with open("key", "w") as f:
f.write(key)

m = bytes_to_long(flag.encode())
c = pow(m, e, n)
print(f"c = {c}")

素数是两个相邻的素数。

n使用证书格式给出的。用以下网站进行读取。

https://the-x.cn/zh-cn/encodings/Asn1.aspx

1
2
3
4
5
6
7
8
9
10
11
12
13
14
import gmpy2
import sympy
import libnum
n = 0x4A4BFC4EB9E6FC4B2858B242F09B60D38687DC7970EAEF7A4D96EEC20307F5AD36057D85206E268AAA439FC930EEACB3955E15A7C1C982468F47C14504C871B7B305D2E4EA121A61C7A6532FF1CAD32E563EFE10A91059CB48F0DC9E5EC723B6BFA29ACAA4281E8993A9844888866F31510AA2BD6A99BC6CDE57D11F8DE68068F973B6EDE7B91C9F71C323AA8CEB794DB47FC48D49AF700FABCAAAD020BE3BF755AA6F95154745F3EF9560ABD3D544F16D6ACDD5AF9345D69F28A177EDECB0280A057A62AF29404F5596664E9DDD1CAA6E1EDB893A5E56ACE8BC4159A50AE6D93F189BA4CC4646C898BA3D39B10EC95BCFDD3C94394B5A9600E1D626AA1D6927
e = 0x10001
sqrt = gmpy2.iroot(n,2)[0]
p = sympy.nextprime(sqrt)
q = sympy.prevprime(sqrt)
assert p*q == n

c = 4881495507745813082308282986718149515999022572229780274224400469722585868147852608187509420010185039618775981404400401792885121498931245511345550975906095728230775307758109150488484338848321930294974674504775451613333664851564381516108124030753196722125755223318280818682830523620259537479611172718588812979116127220273108594966911232629219195957347063537672749158765130948724281974252007489981278474243333628204092770981850816536671234821284093955702677837464584916991535090769911997642606614464990834915992346639919961494157328623213393722370119570740146804362651976343633725091450303521253550650219753876236656017
print(libnum.n2s(int(gmpy2.powmod(c, gmpy2.invert(e, p-1), p))))

# SEE{i_love_really_secure_algorithms_b5c0b187fe309af0f4d35982fd961d7e}

其他的应该没时间写了。


本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!