Skip to content

Commit 5f0472c

Browse files
committed
Add WACon 2022
1 parent 4d1e67f commit 5f0472c

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

44 files changed

+35873
-0
lines changed

README.md

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,14 @@
11
# my-ctf-challenges
22

3+
## [WACon 2022 Finals](https://wacon.world/)
4+
5+
- [mcgonagall](WACon2022/Final/mcgonagall/) (Crypto)
6+
- [trinity](WACon2022/Final/trinity/) (Crypto)
7+
8+
## [WACon 2022 Quals](https://wacon.world/)
9+
10+
- [chukjibeop](WACon2022/Qual/chukjibeop) (Misc)
11+
312
## [GoN 2022 Spring Open Qual](https://dreamhack.io/ctf/24/)
413

514
- [trillionaire](https://dreamhack.io/wargame/challenges/475/) (BlockChain, Crypto)

WACon2022/Final/mcgonagall/.DS_Store

6 KB
Binary file not shown.

WACon2022/Final/mcgonagall/.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
__pycache__/
2+
*.sage.py

WACon2022/Final/mcgonagall/README.md

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
# mcgonagall
2+
3+
- Author : diff
4+
- Category : Crypto
5+
- Division : main
6+
7+
# Description
8+
9+
Again?
10+
11+
# Flag
12+
13+
`WACon{BKZ_with_nonce_bit_length_exposure}`
14+
15+
# Deployment Guide
16+
17+
`docker-compose up -d --build` at deploy directory
18+
19+
# Distribution Guide
20+
21+
Deploy tarball located at [deploy](./deploy)
22+
23+
# External Writeups
24+
25+
- [https://drive.google.com/file/d/1o0pkcq0YhV97FxTzxrHXRwYhtscATYfj/view](https://drive.google.com/file/d/1o0pkcq0YhV97FxTzxrHXRwYhtscATYfj/view)
6 KB
Binary file not shown.
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
FROM ubuntu:20.04
2+
RUN apt-get update
3+
RUN apt-get install socat python3 python3-pip -y
4+
RUN pip3 install pycryptodome ecdsa
5+
WORKDIR /app
6+
COPY ./chall.py /app
7+
COPY ./flag.py /app
8+
EXPOSE 13337
9+
CMD ["socat", "TCP-LISTEN:13337,reuseaddr,fork", "EXEC:python3 chall.py,nofork,stderr"]
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
import signal
2+
from hashlib import sha256
3+
from random import choice, randint
4+
from secrets import randbits, token_bytes
5+
from string import ascii_uppercase, digits
6+
7+
from ecdsa import SECP256k1, SigningKey
8+
9+
from flag import flag
10+
11+
12+
def PoW():
13+
s = "".join(choice(ascii_uppercase + digits) for _ in range(16))
14+
print(s)
15+
answer = input()
16+
hash = sha256((s + answer).encode()).hexdigest()
17+
assert hash[:6] == "000000"
18+
19+
20+
def main():
21+
trials = 30
22+
correct = 0
23+
for _ in range(trials):
24+
sk = SigningKey.generate(curve=SECP256k1)
25+
pk = sk.privkey.secret_multiplier
26+
print(sk.get_verifying_key().pubkey.point.x())
27+
print(sk.get_verifying_key().pubkey.point.y())
28+
29+
info = 0
30+
for _ in range(256):
31+
msg = token_bytes(32)
32+
klen = randint(250, 256)
33+
sig = sk.sign(msg, k=randbits(klen))
34+
info += 256 - klen
35+
print(msg.hex(), sig.hex(), klen)
36+
37+
assert info >= pk.bit_length()
38+
39+
pk_ = int(input())
40+
if pk_ == pk:
41+
correct += 1
42+
43+
assert correct / trials >= 0.7
44+
print(flag)
45+
46+
47+
if __name__ == "__main__":
48+
[signal.alarm(1200), PoW(), main()]
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
version: '2.4'
2+
services:
3+
mcgonagall:
4+
build: ./
5+
ports:
6+
- "13337:13337"
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
flag = b"WACon{BKZ_with_nonce_bit_length_exposure}"
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
import signal
2+
from hashlib import sha256
3+
from random import choice, randint
4+
from secrets import randbits, token_bytes
5+
from string import ascii_uppercase, digits
6+
7+
from ecdsa import SECP256k1, SigningKey
8+
9+
from flag import flag
10+
11+
12+
def PoW():
13+
s = "".join(choice(ascii_uppercase + digits) for _ in range(16))
14+
print(s)
15+
answer = input()
16+
hash = sha256((s + answer).encode()).hexdigest()
17+
assert hash[:6] == "000000"
18+
19+
20+
def main():
21+
trials = 30
22+
correct = 0
23+
for _ in range(trials):
24+
sk = SigningKey.generate(curve=SECP256k1)
25+
pk = sk.privkey.secret_multiplier
26+
print(sk.get_verifying_key().pubkey.point.x())
27+
print(sk.get_verifying_key().pubkey.point.y())
28+
29+
info = 0
30+
for _ in range(256):
31+
msg = token_bytes(32)
32+
klen = randint(250, 256)
33+
sig = sk.sign(msg, k=randbits(klen))
34+
info += 256 - klen
35+
print(msg.hex(), sig.hex(), klen)
36+
37+
assert info >= pk.bit_length()
38+
39+
pk_ = int(input())
40+
if pk_ == pk:
41+
correct += 1
42+
43+
assert correct / trials >= 0.7
44+
print(flag)
45+
46+
47+
if __name__ == "__main__":
48+
[signal.alarm(1200), PoW(), main()]
Lines changed: 108 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,108 @@
1+
#!/usr/local/bin/sage
2+
import os
3+
import time
4+
from hashlib import sha1, sha256
5+
6+
from Crypto.Util.number import long_to_bytes as l2b
7+
from tqdm import tqdm
8+
9+
os.environ["PWNLIB_NOTERM"] = "1"
10+
from pwn import *
11+
from sage.all import *
12+
13+
# context.log_level = "DEBUG"
14+
p = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F
15+
b = 0x0000000000000000000000000000000000000000000000000000000000000007
16+
a = 0x0000000000000000000000000000000000000000000000000000000000000000
17+
n = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141
18+
Gx = 0x79BE667EF9DCBBAC55A06295CE870B07029BFCDB2DCE28D959F2815B16F81798
19+
Gy = 0x483ADA7726A3C4655DA4FBFC0E1108A8FD17B448A68554199C47D08FFB10D4B8
20+
E = EllipticCurve(GF(p), [a, b])
21+
G = E(Gx, Gy)
22+
l = 256
23+
Z = Zmod(n)
24+
25+
26+
conn = remote("127.0.0.1", 13337)
27+
28+
# PoW
29+
s = conn.recvline().rstrip().decode()
30+
assert len(s) == 16
31+
for i in tqdm(range(1 << 26)):
32+
t = str(i)
33+
hash = sha256((s + t).encode()).hexdigest()
34+
if hash[:6] == "000000":
35+
conn.sendline(t.encode())
36+
break
37+
38+
39+
trial = 30
40+
success = 0
41+
for t in range(trial):
42+
Px = int(conn.readline(keepends=False))
43+
Py = int(conn.readline(keepends=False))
44+
45+
rs = [None for _ in range(l)]
46+
ss = [None for _ in range(l)]
47+
hs = [None for _ in range(l)]
48+
cs = [None for _ in range(l)]
49+
pubkey = E(Px, Py)
50+
for i in range(l):
51+
row = conn.readline(keepends=False).split()
52+
r, s = int(row[1][:64], 16), int(row[1][64:], 16)
53+
h = int.from_bytes(sha1(l2b(int(row[0], 16))).digest(), byteorder="big")
54+
klen = int(row[2])
55+
rs[i] = r
56+
ss[i] = s
57+
hs[i] = h
58+
cs[i] = klen
59+
60+
print([(cs.count(kk), kk) for kk in range(248, 257)])
61+
print(float(sum(cs) / l))
62+
63+
cs, rs, ss, hs = zip(*sorted(zip(cs, rs, ss, hs)))
64+
65+
ts = [None for _ in range(l)]
66+
us = [None for _ in range(l)]
67+
ls = [None for _ in range(l)]
68+
69+
for i in range(l):
70+
sinv = int(1 / Z(ss[i]))
71+
ts[i] = sinv * rs[i]
72+
us[i] = (-sinv) * hs[i]
73+
ls[i] = 256 + 1 - cs[i]
74+
75+
B = Matrix(ZZ, l + 2, l + 2)
76+
77+
for i in range(l):
78+
li = ls[i] + 1
79+
B[i, i] = (2 ^ li) * n
80+
B[l, i] = (2 ^ li) * ts[i]
81+
B[l + 1, i] = (2 ^ li) * us[i]
82+
B[l, l] = 1
83+
B[l + 1, l + 1] = n
84+
85+
beta = 15
86+
pk = 0
87+
88+
st = time.time()
89+
print(f"BKZ with beta = {beta}")
90+
B = B.BKZ(block_size=beta)
91+
for row in B:
92+
guess = row[-2] % n
93+
d1, d2 = guess, n - guess
94+
if pubkey == d1 * G:
95+
pk = d1
96+
break
97+
if pubkey == d2 * G:
98+
pk = d2
99+
break
100+
print("Duration", time.time() - st)
101+
print("pk: ", pk)
102+
if pk != 0:
103+
success += 1
104+
print(f"# Success: {success} / {t + 1}")
105+
conn.sendline(str(pk).encode())
106+
107+
# flag
108+
print(conn.recvline())
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
FROM ubuntu:20.04
2+
RUN apt-get update
3+
RUN apt-get install socat python3 python3-pip -y
4+
RUN pip3 install pycryptodome ecdsa
5+
WORKDIR /app
6+
COPY ./chall_updated.py /app
7+
COPY ./flag.py /app
8+
EXPOSE 13337
9+
CMD ["socat", "TCP-LISTEN:13337,reuseaddr,fork", "EXEC:python3 chall.py,nofork,stderr"]
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
import signal
2+
from hashlib import sha256
3+
from random import choice, randint
4+
from secrets import randbits, token_bytes
5+
from string import ascii_uppercase, digits
6+
7+
from ecdsa import SECP256k1, SigningKey
8+
9+
from flag import flag
10+
11+
12+
def PoW():
13+
s = "".join(choice(ascii_uppercase + digits) for _ in range(16))
14+
print(s)
15+
answer = input()
16+
hash = sha256((s + answer).encode()).hexdigest()
17+
assert hash[:6] == "000000"
18+
19+
20+
def main():
21+
trials = 30
22+
correct = 0
23+
for _ in range(trials):
24+
sk = SigningKey.generate(curve=SECP256k1)
25+
pk = sk.privkey.secret_multiplier
26+
print(sk.get_verifying_key().pubkey.point.x())
27+
print(sk.get_verifying_key().pubkey.point.y())
28+
29+
info = 0
30+
for _ in range(256):
31+
msg = token_bytes(32)
32+
klen = randint(250, 256)
33+
sig = sk.sign(msg, k=randbits(klen))
34+
info += 256 - klen
35+
print(msg.hex(), sig.hex(), klen)
36+
37+
assert info >= pk.bit_length()
38+
39+
pk_ = int(input())
40+
if pk_ == pk:
41+
correct += 1
42+
43+
assert correct / trials >= 0.7
44+
print(flag)
45+
46+
47+
if __name__ == "__main__":
48+
[signal.alarm(1200), PoW(), main()]
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
version: '2.4'
2+
services:
3+
mcgonagall:
4+
build: ./
5+
ports:
6+
- "13337:13337"
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
flag = b"WACon{BKZ_with_nonce_bit_length_exposure}"

WACon2022/Final/trinity/.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
__pycache__/
2+
*.sage.py

WACon2022/Final/trinity/README.md

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
# trinity
2+
3+
- Author : diff
4+
- Category : Crypto
5+
- Division : main, junior
6+
7+
# Description
8+
9+
Push it to the limit.
10+
11+
# Flag
12+
13+
`WACon{Factoring_with_only_a_third_of_the_bits}`
14+
15+
# Deployment Guide
16+
17+
None. Local challenge to help saving the earth.
18+
19+
# Distribution Guide
20+
21+
Deploy tarball located at [./deploy]
22+
23+
# External Writeups
24+
25+
- [https://yunseok.notion.site/WACon-2022-2829178f13f04323acbf66da2e17740e](https://yunseok.notion.site/WACon-2022-2829178f13f04323acbf66da2e17740e)
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
#!/usr/bin/env python3
2+
from Crypto.Cipher import PKCS1_OAEP
3+
from Crypto.PublicKey import RSA
4+
from Crypto.Util.number import GCD, getPrime
5+
6+
from flag import flag
7+
8+
SIZE = 1024
9+
key = RSA.generate(SIZE, e=getPrime(SIZE // 12))
10+
n, e, p, q = key.n, key.e, key.p, key.q
11+
dp, dq = pow(e, -1, p - 1), pow(e, -1, q - 1)
12+
cipher = PKCS1_OAEP.new(key)
13+
assert GCD(2 * e, (e * dp - 1) // (p - 1)) == 1
14+
15+
print(n)
16+
print(e)
17+
print(dp % (1 << 200))
18+
print(dq % (1 << 200))
19+
print(cipher.encrypt(flag).hex())

WACon2022/Final/trinity/public/output

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
150521291786162634207005525778169708708522720074345927077420731185600563387046639806238339255757863868699490815776623273376348175253988894743885370764780600900302789673531599439459445183505805277387459741112034759427671859796591301689098407566045632882616152019038756129184959273344103972335895300046311701809
2+
30510532618964464063517147
3+
1277251830107045061098265337744483546719636547425635587593463
4+
230441702892751221228737480414520264502429400074470159039659
5+
9118ecc4581f2f200a07a34f64ec91caca2a2adbead4509311af96e76ccecbd042ea284c382b2caf40528c3c86d98f6e9c62c5f72d6e12a8a932f26ac2e32ab86ab85c64919c86a8c2632f5a625d6292947b5f59fb443f672a4e9047e2cb9e6d90e0fd81ac016ea03ed79269b8fbe9c442bd7d77e9278b15dde31f2adc920bd1

0 commit comments

Comments
 (0)