간단한 ASLR 우회/차단 기법

해킹/개념 정리 2016. 1. 16. 22:26

스택의 주소가 필요한 공격을 할때 상당히 짜증나는 보호기법중 하나가 aslr이다. 

ASLR의 개념: http://satanel001.tistory.com/60

위 글에서 설명했듯이 Imagebase를 랜덤하게 해줘서 주소 예측이 힘들게 하는 방식이다.


이 aslr에 대해서 사소하더라도 내가 알고있는 우회/차단 기법을 몇가지 소개한다.


1.0x90사용하기

쉘코드를 사용하기 위해서 많이 쓰는 방법이다. 0x90(nop)이라는 명령어는 프로그램에 아무런 영향도 끼치지 않고 그냥 eip를 다음 명령어로 넘겨버린다. 그러므로 이 0x90을 많이 늘어놓은 다음 뒷쪽에 쉘코드를 넣어서 프로그램이 랜덤한 주소로 리턴하거나 점프해도 0x90안에 eip가 떨어질 확률을 높히는 것이다.

여러개의 0x90중 한군데에만 떨어져도 eip는 0x90을 타고 끝까지 가서 쉘코드를 실행하게 된다. 많이 쓰이는 방법이긴 한데 버퍼의 크기가 한정되어있으면 0x90을 넣을 공간이 부족할 수 있다.


2.반복실행

0x90과 마찬가지로 확률을 높히는 방식이다. 원하는 주소가 어딘지는 모르지만 가능한 주소를 골라서 될때까지 계속 시도를 하다보면 랜덤의 특성상 언젠가는 해당주소에 걸릴 것이다. 0x90과 함게 사용하면 확률을 더 높힐 수 있겠다. 하지만 너무 반복적으로 실행하지 못하게 차단한다던지 하는 환경에서는 사용할 수 없는 방법이다.


3.ulimit -s unlimited

리눅스 소스의 mmap.c 부분에 32비트에 stack 크기가 unlimited일경우 이미지베이스에 랜덤값을 추가하지 않도록 되어있다.

그냥 소스 자체가 그렇게 쓰여있는 것이다.

아마도 Imagebase에 작은 숫자라도 랜덤한 값이 추가되면 가상메모리의 최대범위를 넘어갈 수 있기 때문이 아닐까 조심스레 추측만 해본다.


그런데 이게 내가 알고있던 것 처럼 항상 스텍영역의 주소를 고정해주는 것은 아닌듯 하다. 우선 기본적으로 64비트에서는 안되고...

간단한 코드로 실험을 해봤는데. 우분투 32비트에서도 실패했다.




이런식으로 스텍에 할당된 버퍼와 환경변수의 주소를 각각 출력하도록 test.c를 짜줬다.

그리고 이 프로그램을 그냥 5번 실행하는 runtest라는 프로그램을 작성해서 돌려봤더니..




캡쳐와 같이 ulimit -s가 unlimited인데도 다 다르게 나온다.

부모 프로세스의 ulimit에 따라 다르다고 해서 /etc/security/limits.conf에 기본 ulimit -s도 다 unlimited로 바꿔줬는데도 여전히 주소가 바뀐다.

하지만 분명히 사람들이 이 방식으로 aslr을 우회할 수 있다고 하고 나도 실제로 사용해본 경험이 있기에 일단 소개는 해놓았다..



4.setarch (아키텍쳐) -R

내경우에는 setarch linux32 -R다.



setarch의 옵션들인데 -R은 addr-no-randomize 옵션이라고 쓰여있다.

이 명령어를 실행하면 쉘이 하나 뜨는데 그 안에서 실행하는 프로그램의 aslr이 풀린다.




위 캡쳐처럼 주소가 통일되었지만... suid나 sgid가 걸린 파일에는 아래처럼 다시 랜덤해져버린다...

실제 suid가 걸린 파일을 익스플로잇 해야할때는 사용하기 힘들다는 뜻..



결론은 대부분의 경우 가장 기초적인 1, 2번 방법에 기대야 하고 3.ulimit -s unlimited는 분명이 써먹을 수 있었던거 같은데 공부가 좀더 되고 확인이 되면 다시 글을 쓰는걸로 해야겠다...




2016-01-20 추가: ulimit -s unlimited는 힙과 라이브러리 영역까지만 고정이 되고 스택영역은 고정이 안된다고 한다.

Tags
Social