-
Oneshot gadgetCTF/TOOL 2021. 1. 8. 20:24
PRELIMINARY 서론
oneshot gadget(magic gadget)이란 해당 gadget 하나만을 이용하여 shell을 획득할 수 있는 gadget이다. [1]
대표적으로는 execve("/bin/sh") 등이 이에 해당하는데,
신기하게도 rdi에 "/bin/sh"의 offset 주소를 전달하고 execve 함수를 실행하는 코드가 libc 내부에 존재한다.
위와 같이 "/bin/sh"의 주소를 레지스터에 전달하는 부분을 검색해보자.
만약 e6e73 부분의 코드를 실행한다면 함수의 처음 세 인자를 저장하는 rdi, rsi, rdx에 순서대로 값이 전달된 후 execve 함수가 실행될 것이다. 추가로, 위 코드를 통해 쉘을 취득하려면 r10과 r12가 NULL이어야 한다.
그렇다면 이러한 코드의 위치를 계산해주는 도구가 있지 않을까? 물론 있다.
one_gadget
libc 내부의 oneshot gadget을 찾아주는 one_gadget의 다운로드 방법은 다음과 같다.
$ cd ~ $ sudo apt-get install ruby $ git clone https://github.com/david942j/one_gadget.git $ cd one_gadget $ gem install one_gadget
위에서 확인한 것처럼 0xe6e73 offset으로 실행할 경우 [r10]과 r10, [r12]와 r12 각각에서 둘 중 하나가 NULL일 경우 shell을 취득할 수 있음을 알려준다. 이를 효율적으로 사용하기 위해서는 다음과 같이 배열에 offset을 미리 저장해두면 좋다.
oneshot_offset = [0xe6e73, 0xe6e76, 0xe6e79] oneshot = libc + oneshot_offset[i]
gadget마다 constraints가 다르고, 그로 인해 제대로 작동하지 않는 경우를 대비해 offset 배열을 만든 후 i를 바꿔가면서 다양하게 시도하는 것이 가능하다.
Reference