passcode 문제를 풀 때 잠깐 등장했던 개념이다.
우리가 프로그래밍을 마치고나도 작성한 코드파일은 컴퓨터 입장에서 그저 텍스트 쪼가리에 불과하다.
그래서 '컴파일'이라는 과정을 거치는데 그 과정을 조금 자세히 설명하겠다.
(GNU_C 기준)
c파일 -> pre-compiler (*.i) -> compiler(*.s) -> assembler (*.o) -> 링킹과정 -> 실행파일
링킹과정에서는 오브젝트 파일에 실제 함수의 주소를 연결해주는 역할을 한다.
(오브젝트 파일은 함수를 호출했을때 실제로 실행해야할 코드가 들어있지 않음)
그런데 여기서 문제가 발생한다.
표준입출력같은 함수들은 하나의 프로그램에서 굉장히 많이 호출되는데 (printf, scanf, cout, cin 등등)
이 함수들의 실행코드들을 컴파일할때 일일이 실행파일에 다 집어넣자니 너무 비효율적이다.
실행파일의 크기가 커지는것은 둘째치더라도 이 바이너리를 실행할 때 같은 일을 하는 바이너리코드가 메모리상에 불필요하게 적재된다.
그래서 이 문제를 해결하려고 dll의 개념이 등장한 것이다. dll파일을 메모리에 로딩시키고 dll의 주소로 리다이렉트시켜주면 공간을 훨씬 절약할 수 있다.
하지만 바이너리가 무슨수로 dll의 메모리 주소를 유추해서 실행 시킬것인가?
이때 등장하는 개념이 바로 PLT와 GOT이다.
PLT -> Proceduler Link Table
GOT -> Gobal Offset Table
함수가 만약 처음 호출된다면 plt의 주소로 점프한 다음에 got에서 주소를 찾는다. 만약 got에 해당함수의 주소가 있다면 그 주소로 점프해서 그 함수를 실행하고
주소가 비어있다면 de_resolve라는 함수를 통해서 해당 함수의 주소를 got에 채워넣어준다.
'공부 > Pwnable' 카테고리의 다른 글
RTL (Return To Library) (0) | 2018.12.06 |
---|---|
ROP 개념 (0) | 2018.12.06 |