rsp-∞

[시스템 해킹/포너블] 스터디 1-5회차 이론 정리 본문

ACADEMY/system

[시스템 해킹/포너블] 스터디 1-5회차 이론 정리

portrait.kim 2024. 4. 6. 00:09

 

1. x86-64 아키텍처

 

- 명령어 집합 구조(Instruction Set Architecture) : CPU가 처리할 수 있는 명령어의 집합 구조로, 현재 가장 점유율이 높은 것은 x86-64 아키텍처

- 레지스터의 종류

 1) 범용 레지스터

이름 용도
rax 함수의 반환 값
rbx x64에서는 주된 용도 없음
rcx 반복문의 반복 횟수 / 연산의 시행 횟수
rdx x64에서는 주된 용도 없음
rsi 데이터를 옮길 때 원본을 가리키는 포인터
rdi 데이터를 옮길 때 목적지를 가리키는 포인터
rsp 사용 중인 스택의 위치를 가리키는 포인터
rbp 스택의 바닥을 가리키는 포인터

 

2) 세그먼트 레지스터

이름 용도
cs 코드 영역을 가리킴
ss 스택 메모리 영역을 가리킴
ds 데이터 영역 가리킴
es 범용
fs 범용
gs 범용

 

3) 명령어 포인터 레지스터

- rip (instruction pointer): 8바이트의 크기, CPU가 어느 부분의 코드 부분을 실행할지 가리킴

 

4) 플래그 레지스터

이름 용도
CF(Carry Flag) 부호 없는 수의 연산 결과가 비트 범위를 넘는 경우 설정
ZF(Zero Flag) 연산의 결과가 0일 경우 설정
SG(Sign Flag) 연산의 결과가 음수일 경우 설정
OF(Overflow Flag) 부호 있는 수의 연산 결과가 비트 범위를 넘는 경우 설정

 

 

2. 레지스터 호환

 

RAX -> EAX -> AX -> AH/Al과 같은 순서로 비트 수가 절반씩 줄어듦. 스터디를 진행하면서 여러 문제를 풀어 보니 RAX가 64비트인 것과 EAX가 32비트인 환경을 주로 접함.

 

 

3. 리눅스 메모리 레이아웃 : 세그먼트(적재되는 메모리의 용도별로 메모리 구획을 나눔, 구간마다 CPU 권한 상이)

세그먼트 역할 일반적인 권한 사용 예시
코드 세그먼트 실행 가능한 코드 읽기, 실행 main() 등의 함수
데이터 세그먼트 초기화된 전역 변수 / 상수 읽기, 쓰기 or 읽기 초기화된 전역 변수 / 상수
BSS 세그먼트 초기화되지 않은 데이터 읽기, 쓰기 초기화되지 않은 전역 변수
힙 세그먼트 동적으로 사용되는 영역 읽기, 쓰기 malloc(), calloc()
스택 세그먼트 임시 변수 저장 읽기, 쓰기 지역 변수, 함수의 인자

 

 

4. 어셈블리어 문법 구조

 

- (opcode) (operand1) (operand2)의 구조. operand는 피연산자로 보통 operand2를 operand1의 방향으로 진행시킴. 예를 들어, <mov eax, 3>은 3을 eax에 할당하는 명령문.

- 피연산자의 종류 : 상수, 레지스터, 메모리

     (1) 메모리 피연산자 표현법 : TYPE PTR [주소값 / 레지스터]

     *TYPE은 1바이트의 BYTE, 2바이트의 WORD, 4바이트의 DWORD, 8바이트의 QWORD

 

 

5. 어셈블리어 주요 명령어

명령 기능 명령 코드
데이터 이동 mov, lea
산술 연산 inc, dec, add, sub
논리 연산 and, or, xor, not
비교 cmp, test
분기 jmp, je, jg
*스택 push, pop
프로시저 call, ret, leave
시스템콜 syscall

*스택은 높은 주소에서 낮은 주소로 자람. rsp에서 어떤 값을 빼는 것은 값만큼의 공간을 마련(생성)하는 것이고, 더하는 것은 그만큼의 공간을 비우는(삭제하는) 것.

 

 

6. Tool

 

1) pwndbg

- gdb의 플러그인

-바이너리를 분석하기 위해 사용되며, gdb의 기능을 보완하여 추가적인 기능 제공

     (1) 내부 명령어

          - disassemble (함수명) : 함수 전체를 어셈블리 코드로 보여 줌

          - start : 프로그램 실행

          - run : 프로그램 실행

          - break *(함수명) : 해당 함수의 실행 직전 프로그램의 진행을 멈춤

          - continue : break 이후의 프로그램을 다시 재개

 

2) pwntools : 익스플로잇 과정에서 자주 구현하는 기능들을 파이썬 모듈로 제공

     (1) API 사용법 - 함수

          - send() : 데이터 보냄

          - revc() : 데이터 받음

          - packing & unpacking : 바이트 배열을 리틀 엔디언 방식으로 변경 & 그 반대

          - interactive() : 터미널에서 프로세스에 데이터 입출력

          - ELF() : 헤더에 기록된 각종 정보 보기

          - asm() : 주어진 코드를 기계어로 어셈블

 

 

7. Stack Buffer Overflow

 

1) Stack overflow(스택 영역 자체가 넘친 것) vs Stack Buffer Overflow(스택 영역에 할당된 특정 버퍼가 넘친 것)

2) Buffer(버퍼) : 데이터가 목적지로 이동하기 전에 보관되는 임시 저장소, 데이터가 저장될 수 있는 모든 단위

3) Buffer Overflow : 각 버퍼의 크기보다 더 큰 데이터가 들어가면 발생하는 오류, Memory Corruption으로 인한 보안 위협

4) 스택 버퍼 오버플로우를 이용하여 수행할 수 있는 공격

     - 중요 데이터 변조 : 다른 버퍼의 데이터를 덮어씀

     - 데이터 유출 : 다른 버퍼의 데이터를 읽어 버림 (Data Leak)

     - *실행 흐름 조작 :  return의 주소를 다른 주소로 덮어씀

*실행 흐름 조작은 스택 버퍼 오버플로우를 사용한 워게임/CTF 문제에서 가장 흔하게 등장하는 공격 목표임

5) 함수들의 입력값 길이 확인 여부

     - 길이 확인 X(취약점 발생) : gets(), scanf(), sprintf(), strcpy(), strcat()

     - 길이 확인 O : fgets(), snprintf(), strncpy(), strncat(), memcpy()

'ACADEMY > system' 카테고리의 다른 글

시스템 스터디 기초 이론 주요 정리  (0) 2024.09.15