코드가 쭉 진행되다가 특정 프로시저가 호출되면, 프로시저가 실행되고 나서 다시 원래의 실행 흐름으로 돌아옵니다.
예시 코드
0x400000: call func: push & jmp
0x400005: mov esi, eax
...
0x401000: push rbp
0x401001: mov rbp, rsp
0x401004: sub rsp, 0x30
0x401008: mov BYTE PTR[rsp], 0x3
...
0x401020: leave: mov rsp, rbp & pop rbp
0x401021: ret: pop rip & jmp rip
빠르게 보는 전 과정의 메모리 변화
상세한 작동
1. 프로시저 호출
2. function prologue: 기존 상태의 기록, 새로운 stack frame의 마련
3. 호출된 프로시저가 새 stack frame을 사용함
4. function epilogue: 원래의 실행 흐름으로 복구
5. 다음 코드가 실행됨
✅ 0x400000: call func: push & jmp
➡️ return address (프로시저 호출이 없었다면 원래 흘러갔을 다음 코드의 주소: 0x400005)를 stack에 저장한 뒤, 호출한 프로시저의 첫 번째 코드 위치로 jump
✅ 0x401000: push rbp
➡️ 현재의 rbp를 stack에 저장
✅ 0x401001: mov rbp, rsp
➡️ 새 stack frame을 형성하기 위해, rbp를 rsp와 같은 곳을 가리키게 함
✅ 0x401004: sub rsp, 0x30
➡️ rsp에서 0x30만큼을 뺌으로써, 새 stack frame의 공간을 할당
✅ 0x401008: mov BYTE PTR[rsp], 0x3
➡️ 할당된 stack frame 공간에 지역변수 할당
✅ 0x401020: leave: mov rsp, rbp & pop rbp
➡️ rsp를 rbp와 같은 곳을 가리키게 함으로써 stack이 쪼그라들고,
현재 stack의 top에 있는 값 (= 이전 rbp)을 꺼내 rbp에 할당함으로써 rbp가 이전 위치로 복귀
✅ 0x401021: ret: pop rip & jmp rip
➡️ 현재 stack의 top에 있는 값 (= return address)을 꺼내 rip에 할당함으로써 rip가 return address를 가리키게 하고,
이 address로 jump함으로써 원래의 실행 흐름으로 복귀
✅ 0x400005: mov esi, eax
'IT > 시스템 보안' 카테고리의 다른 글
[Stack Buffer Overflow] Return Address Overwrite을 통한 실행 흐름 조작 (0) | 2024.03.01 |
---|---|
[Stack Buffer Overflow] 데이터 변조와 유출 (0) | 2024.02.29 |
[Shellcode] objdump을 이용한 byte code 추출 (0) | 2024.02.28 |
[Shellcode] execve (0) | 2024.02.28 |
[Shellcode] orw: open-read-write (0) | 2024.02.27 |