진정한 프로그래머한테 필요한 자판은 단지 3개뿐!!!!!!!!!!!!!!!!!
버퍼 오버플로우에 대해 알려고 한다면 어셈블리어를 어느정도 간단히 알고 있어야 한다.
간단하게 어셈블리를 보자.
cpu에는 범용 레지스터라는게 있다.
|
범주 |
이름 |
내용 |
|
|
범용레지스터 |
EAX(AH,AL) |
Accumlaor |
누산기, 산술연산, 입출력 |
|
EBX(BH,BL) |
Base Register |
인덱스 로서 사용할 수 있는 범용 레지스터 | |
|
ECX(CH,CL) |
Count Register |
Loop의 반복 횟수나 좌우 방향으로 비트를 쉬프트할 숫자를 기억 | |
|
EDX(DH,DL) |
Data Register |
입출력 명령에 사용 큰수의 곱셉 및 나눗셈에서는 DX,AX 를 쌍으로 사용 | |
|
오프셋레지스터 |
ESI |
Source Index |
출발지 주소에 대한 값 저장 Memory 이동이나 데이터 복사 때 원본 주소 |
|
EDI |
Destination Index |
박사할 때 목적지의 주소 | |
|
ESP |
Stack Pointer |
스택의 가장 윗부분을 가진다. | |
|
EBP |
Base Pointer |
스택의 가장 아랫부분을 가진다. | |
|
IP |
Instruction Pointer |
다음 명령어의 오프셋을 저장 | |
|
세그먼트레지스터 |
EDS |
Data Segment Register |
변수의 기본 베이스 주소 저장 |
|
EES |
Extra Segment Register |
변수의 추가 베이스 주소 저장 | |
|
ESS |
Stack Segment Register |
스택의 베이스 주소 저장 | |
|
ECS |
Code Segment Register |
명령어 코드의 베이스 주소 저장 |
|
데이터 전송 명령 | |||
|
Mov |
데이터를 복사한다. |
||
|
사칙연산 명령 | |||
|
ADD |
덧셈 |
ABC |
덧셈 |
|
SUB |
뺄셈 |
SBB |
뺄셈 |
|
MUL |
곱셈 |
CBW |
바이트에서 워드로 부호확장 |
|
DIV |
나눗셈 |
CWD |
워드에서 더블워드로 부호확장 |
|
INC |
하나 증가 |
DEC |
하나 감소 |
|
논리연산. 쉬프트 명령 | |||
|
AND |
논리곱 |
OR |
논리 합 |
|
XOR |
배타적 논리 합 |
NOT |
부정 |
|
NEG |
부호 반전 |
||
|
SHL |
S는 Shift, H는 0을 넣을 것인가 L은 left |
ROR |
R은 Rotate |
함수호출규약
|
일반적 호출규약은 인수를 뒤에서부터 전달하며, 인수 전달에 사용된 스택 영역은 호출원이 정리하는데, 이는 C++의 기본 규약인 __cdcel의 수택 프레임 모양일 뿐임 호출규약이 변경되면 스택 프레임의 모양과 관리 방법도 달라짐 | ||||
|
호출규약 |
인수전달 |
스택정리 |
이름규칙 | |
|
__cdecl |
오른쪽 먼저 |
호출원 |
_함수명 | |
|
__stdcall |
오른쪽 먼저 |
함수 |
_함수명@인수크기 | |
|
__fastcall |
EXC, EDX에 우선 나머 지는 오른쪽 먼저 |
함수 |
@함수명@인수크기 | |
|
Naked |
오른쪽 먼저 |
함수 |
없음 | |
|
__cdecl 은 함수가 스택을 정리할 책임이 없다. 함수가 끝나고 나서 호출원이 스택을 정리한다. 함수를 호출하는 쪽에서 인수를 몇개나 전달했는지 알 수 있으므로, 실제 전달한 인수 크기만큼 스택을 정리할 수 있다는 장점이 있음. printf나 scanf 같은 가변인수를 지원하는 함수는 모두 __cdecl 호출 규약을 사용함. winAPI 함수의 대부분 규약이기도 하지만, wsprintf는 예외적으로 __stdcall 로 제작되어 있음 | ||||
__cdecl 같은 가변인수를 사용하는 함수가 공격대상이 된다.
아래 왼쪽 함수를 어셈블리로 바꾼것이 오른쪽이다. 기본호출 규약인 __cdecl 이다.
|
int fun(int b, int c) { b = b+c; return b; } int main(void) { int a; a = fun(2,3); return 0; } |
8: int fun(int b, int c) 9: { 00111000 push ebp 00111001 mov ebp,esp 10: b = b + c; 00111003 mov eax,dword ptr [b] 00111006 add eax,dword ptr [c] 00111009 mov dword ptr [b],eax 11: return b; 0011100C mov eax,dword ptr [b] 12: } |
|
int main() { 00111020 push ebp 00111021 mov ebp,esp 00111023 push ecx 16: 17: int a; 18: 19: a = fun(2,3); 00111024 push 3 00111026 push 2 00111028 call fun (111000h) 0011102D add esp,8 // 스택에 push 했던 3,2를 호출원쪽(main)에서 정리하고 있다. 00111030 mov dword ptr [a],eax 20: 21: return 0; 00111033 xor eax,eax 22: } 00111035 mov esp,ebp 00111037 pop ebp 00111038 ret |
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
스택에는 push에 의한 명령어로 값이 채워진다. 스택은 높은 주소에서 낮은 주소로 채워진다.
힙에는 사용자에 의해 값이 채워지며 Data는 전역변수, static 변수, 클래스 등이 채워지며 Code에는 코드들이 들어간다.
힙,data,code는 낮은 주소에서 높은 주소로 채워진다.
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------
저기 위에 어셈 코드를 보면 제일 아래에 ret 것이 있다. 그것은 리턴이라고 함수를 끝내고 호출원쪽으로 가겠다는건데.
호출원의 Instruction Pointer 가 있다. 함수가 끝나면 실행되어질 다음 명령어가 있는곳을 가리키고 있는것이다.
int main(int argc, char* argv[]) { char buff[4]; strcpy(buff,argv[1]); return 0; } 저것이 실행이 된다면 스택에는 ret가 제일 먼저 올라가고 다음 buff[4]가 올라갈 것이다. strcpy를 이용 argv에 있는 내용을 buff 에 복사를 하면 buff[4]를 넘어 ret 주소까지 바꾸게 될것이다.
근대 AAAA가 아닌 내가 만든 해킹프로그램의 메모리주소를 넣는다면.........................해킹프로그램이 실행되게 되는것이다.
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
Visual Studio 에는 보안옵션이 있는데 그것을 활성화 하면 컴파일 할때 버퍼 오버플로우를 방지하기 위해 아래 코드가 들어가게 된다.
013B339E mov eax,dword ptr [___security_cookie (13B7018h)] Data영역에 security_cookie 값이 랜덤한 값으로 들어가는데 이 값을 프로그램이 실행될때 스택에 올려 놓는다. ret 를 바꾸기 위해 오버플로우가 발생 했다면 security_cookie 값도 같이 바뀌게 될것이다. 함수가 종료될때 'Data 영역의 security_cookie 값과 Stack 의 security_cookie 값을 비교해서 같지가 않다면 버퍼 오버런 오류를 발생 시킨다.'


메모리 단편화(Memory Fragmentation)
int a = new int[5]; int b = new int[5]; int c = new int[5]; 메모리 상황(■ : 할당된 메모리 □ : 빈 메모리) a■■■■■ b■■■■■ c■■■■■ delete int [] b; 메모리 상황 a■■■■■ □□□□□... (2010-01-20)
버퍼 오버플로우(Buffer Overflow)
진정한 프로그래머한테 필요한 자판은 단지 3개뿐!!!!!!!!!!!!!!!!! 버퍼 오버플로우에 대해 알려고 한다면 어셈블리어를 어느정도 간단히 알고 있어야 한다. 간단하게 어셈블리를 보자. cpu에는 범용 레지스터라는게 있다. 범주 이... (2010-01-20)
안드로이드 (Android)
안드로이드(Android)는 휴대전화기를 비롯, 모바일 디바이스를 위한 운영체제와 미들웨어 그리고 핵심 어플리케이션을 포함하고 있는 소프트웨어 스택이다. 안드로이드는 개발자들이 자바(Java) 언어로 어플리케이션을 작성 할 수 있... (2010-01-06)
증강현실(Augmented Reality, AR)
[http://www.youtube.c-om/watch?v=APQ2OxgCNzE] 광고이기에 과장된 모습이긴 하지만 실제로 증강현실은 현실의 세계와 화면의 세계가 혼재할수 있는 새로운 기술이라고 할수 있다. 증강현실(Augmented Reality, AR)은 가상현실(Vi... (2010-01-05)
UX란 무엇인가? 
UX란 사용자가 원하는 제품이 아닌 시스템을 만드는 과정이다. 코닥이스트만은 1988년, 기존의 카메라에 혁명을 일으켰다. 그는 기존의 광각판을 통해 현상하던 카메라에서 필름카메라로의 전환을 통해 대량 생산이 가능하게 했다... (2009-12-10)
어포던스 (Affordance)
어포던스 (Affordance)의 뿌리말 Afford는 원래 '~할 여유가 있다, ~하여도 된다, ~을 공급하다, 산출하다'라는 뜻을 가지고 있으나 보통 사전에 없는 뜻으로 인간 컴퓨터 상호작용, 인지 심리학, 산업 디자인, 인터렉션 디자... (2009-08-11)
Usability
사용성(Usability, 유저빌리티)어떤 도구나 인간이 만든 물건, 서비스를 어떤 특정 목적을 달성하기 위해 사용할 때에 어느 정도 사용하기 쉬운가를 말하는 용어이다. 전자 제품이나 정보를 전달하기 위한 문서, 사람들이 일상생활... (2009-05-16)



