티스토리 뷰

소스코드 바로 보겠습니다.

보시면 빨간색으로 네모친 부분에서 strncpy 함수로 할당한 버퍼보다 1 바이트 더 큰 값을 입력받습니다.
gdb를 이용해서 공격해보겠습니다.

ebp 값을 유지하기 위해서 39 바이트만 넣어봤습니다.(마지막 널값.)
그랬더니 0x42424242로 리턴해버리네요 ?? 왜 그럴까요 ? 왜 이와같은 결과가 나오는지 알기 위해서는 leave; ret 에 대해서 알 필요가 있습니다.

프로그램의 프롤로그 부분인 push ebp; mov esp, ebp(인텔기준)은 많이 보셨겠지만, leave; ret은 생소한(?) 분들도 계실겁니다.(사실 leave가 생소하죠...)
문제를 풀기 전에 leave; ret의 동작을 파악해보도록 하겠습니다.(그만큼 중요하고 앞으로는 설명안합니다.)

위와 같이 브레이크포인트를 걸어주었습니다. 바로 실행하면서 값을 살펴봅시다.

눈을 어지럽히는 빨간네모가 세 개 보이실텐데 그냥 실행 -> 레지스터 -> 다시 실행의 순서입니다.
첫 번째 부터 살펴보시면 push ebp 에서 브레이크포인트가 걸린 뒤 레지스터를 확인한 겁니다. 별로 중요한 부분은 아니죠 ?
그 다음 부분은 push ebp가 수행된 후 입니다. esp의 값이 4만큼 감소했죠 ?
0x80483c9가 실행된 후에는 mov ebp, esp가 수행된 후라서 ebp와 esp 값이 같아지는 것을 볼 수 있습니다.
leave의 동작을 보기 전에 먼저 스택에 어떻게 값이 존재하는지에 대해서 보겠습니다.

0xbffffb88이 ebp의 값이고, 0x400309cb가 리턴 할 주소입니다. 아직까지는 ebp와 esp 같죠 ?
이제 leave를 수행 해봅시다.

여기가 가장 중요합니다. 꼭 이해하셔야 되요.
leave를 수행하기 전의 스택 상황과 수행 후의 스택 상황을 동시에 보고 있는데요.
달라진 점이라면, esp의 값이 4만큼 증가한 것과 ebp의 값이 0xbffffb88로 바뀌었다는 것입니다. 이를 토대로 leave는 다음과 같이 동작한다는 것을 알 수 있습니다.
leave: mov esp, ebp; pop ebp -> 지금은 출력만 하기 때문에 스택을 사용하는 일이 없지만 함수 실행, 인자 전달 등등의 일로 인해서 원래는 esp의 값이 상당히 감소되어 있습니다.

위의 동작이 이해가 되셨다면 리턴은 어떤식으로 수행을 할까요 ?
바로, esp에 있는 값을 참조해서 수행합니다. 이번 명령은 먼저 알려드리겠습니다.
ret: pop eip; jmp eip -> eip에 주소를 받고, 받은 주소로 점프합니다 !
그렇다면 위의 esp의 값 0xbffffb6c의 값 0x400309cb의 주소를 바꾸면 어떻게 될까요 ?

ebp의 값은 그대로이고, esp 값은 4가 증가되었고(pop eip로 인해서), eip 값은 0x41414141로 변하면서 세그먼테이션 폴트가 발생했습니다.
이것이 leave; ret이 하는 모든 일입니다. 마지막으로 정리하면,
leave: mov esp, ebp -> pop ebp
ret: pop eip -> jmp eip
입니다. 이 부분은 꼭 ! 이해하고 넘어가셔야 합니다.
그럼 다음 페이지에서 문제를 풀어보겠습니다.


댓글
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크
«   2024/04   »
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
글 보관함