Frame Pointer Overwrite란 SFP의 1Byte를 오버플로우 시켜 조작하여 eip를 변조하는 기법입니다.
발생 조건
취약한 코드와 스택 구조를 보면서 공격 과정을 따라가 보겠습니다.
void problem_child(char *src) // 서브 함수 존재
{
char buffer[40];
strncpy(buffer, src, 41); // buffer의 크기는 40Byte인데 41Byte 크기 값 복사
printf("%s\n", buffer);
}
main(int argc, char *argv[])
{
if(argc<2){
printf("argv error\n");
exit(0);
}
problem_child(argv[1]);
}
코드를 보면 서브 함수가 존재하고 strncpy() 함수 부분을 보면 buffer의 크기를 1Byte 큰 값을 복사하고 있어 SFP에 1Byte 오버플로우가 발생합니다.
1Byte면 매우 작은 값이 바뀌는 것이라고 생각할 수 있지만, 주소는 4바이트 밖에 안되기 때문에 한 바이트에 해당하는 부분만 바뀌어도 매우 큰 영향을 받게 됩니다.
1Byte가 오버플로우 되는 것만으로도 위에 그림처럼 buffer에 shellcode의 주소를 넣고 SFP의 값을 shellcode의 주소 - 4로 변조할 수 있습니다. (main 함수의 ebp → shellcode_addr - 4)
이렇게 되면 그 이후에 어떻게 될까요?
problem_child()의 에필로그가 끝나면 위 그림처럼 되고 main() 함수의 에필로그가 시작되면
위 그림 처럼 esp가 shellcode_addr로 가게 됩니다.
여기서 ret를 하면 어떻게 될까요?
pop eip를 하면 eip에 shellcode의 주소가 들어가게 되고 jmp eip를 하면 shellcode 위치로 가서 shellcode를 실행하게 됩니다.
이렇게 Frame Pointer Overwrite 공격은 단 1Byte의 오버플로우 만으로도 shellcode를 실행시켜 shell을 띄울 수 있는 강력한 공격입니다.