Linux Memory Layout

sy46·2023년 5월 12일
0

computer

목록 보기
2/4

세그먼트


리눅스에서는 프로세스의 메모리를 크게 5가지의 세그먼트(Segment)로 구분한다.

세그먼트란, 적재되는 데이터의 용도별로 메모리의 구획을 나눈 것이다.

크게 코드 세그먼트, 데이터 세그먼트, BSS 세그먼트, 힙 세그먼트, 스택 세그먼트로 구분



코드 세그먼트


코드 세그먼트는 실행 가능한 기계 코드가 위치하는 영역으로 텍스트 세그먼트라고도 불린다.

프로그램이 동작하려면 코드를 실행할 수 있어야 하므로 이 세그먼트에는 읽기 권한과 실행 권한이 부여된다. 반면 쓰기 권한이 있으면 공격자가 악의적인 코드를 삽입하기가 쉬워지므로, 대부분의 현대 운영체제는 이 세그먼트에 쓰기 권한을 제거한다.

아래 main함수가 컴파일되면, 554889e5b8697a00005dc3라는 기계 코드로 변환되는데, 이 기계 코드가 코드 세그먼트에 위치하게 된다.

int main() { return 31337; }



데이터 세그먼트


데이터 세그먼트에는 컴파일 시점에 값이 정해진 전역 변수 및 전역 상수들이 위치하고, CPU가 이 세그먼트의 데이터를 읽을 수 있어야 하므로 읽기 권한이 부여된다.

data 세그먼트 전역변수와 같이 프로그램이 실행되면서 값이 변할 수 있는 데이터가 위치
rodata(read-only data) 세그먼트 전역으로 선언된 상수

int data_num = 31337;                       // data
char data_rwstr[] = "writable_data";        // data
const char data_rostr[] = "readonly_data";  // rodata
char *str_ptr = "readonly";  // str_ptr은 data, 문자열은 rodata
int main() { ... }



BSS 세그먼트(Block Started By Symbol Segment)


컴파일 시점에 값이 정해지지 않은 전역 변수가 위치하는 메모리 영역이다.

즉, 초기화가 되지 않은 전역변수이고, 프로그램이 시작될 때 모두 0으로 초기화가 된다.

이 세그먼트에는 읽기 권한 및 쓰기 권한이 부여된다.



스택 세그먼트


프로세스의 스택이 위치하는 영역이다. 함수의 인자나 지역 변수와 같은 임시 변수들이 실행중에 여기에 저장된다.

스택 세그먼트는 스택 프레임(Stack Frame)이라는 단위로 사용된다. 스택 프레임은 함수가 호출될 때 생성되고, 반환될 때 해제된다. 그런데 프로그램의 전체 실행 흐름은 사용자의 입력을 비롯한 여러 요인에 영향을 받는다.

따라서, 어떤 프로세스가 실행될 때, 이 프로세스가 얼마 만큼의 스택 프레임을 사용하게 될 지를 미리 계산하는 것은 일반적으로 불가능하다. 그래서 운영체제는 프로세스를 시작할 때 작은 크기의 스택 세그먼트를 먼저 할당해주고, 부족해 질 때마다 이를 확장해준다. 스택이 확장될 때, 기존 주소보다 낮은 주소로 확장되기 때문에 ‘아래로 자란다'라는 표현을 종종 사용한다.

이 영역에는 CPU가 자유롭게 값을 읽고 쓸 수 있어야 하므로, 읽기와 쓰기 권한이 부여된다.



힙 세그먼트


스택과 마찬가지로 실행중에 동적으로 할당될 수 있다. 일반적으로 읽기와 쓰기권한이 부여된다.



정리


세그먼트 역할 일반적인 권한 사용 예
코드 세그먼트 실행 가능한 코드가 저장된 영역 읽기, 실행 main() 등의 함수 코드
데이터 세그먼트 초기화된 전역 변수 또는 상수가 위치하는 영역 읽기와 쓰기 또는 읽기 전용 초기화된 전역 변수, 전역 상수
BSS 세그먼트 초기화되지 않은 데이터가 위치하는 영역 읽기, 쓰기 초기화되지 않은 전역 변수
스택 세그먼트 임시 변수가 저장되는 영역 읽기, 쓰기 지역 변수, 함수의 인자 등
힙 세그먼트 실행중에 동적으로 사용되는 영역 읽기, 쓰기 동적으로 할당 받은 메모리

0개의 댓글