: 실행중인 프로그램. 디스크로부터 메모리에 적재되어 CPU의 할당을 받고, OS로부터 주소 공간, 메모리 등을 할당받는 것
Memory Section
- Data(BSS + DATA)
- 전역 변수(초기화 되지 않은 전역변수는 BSS영역에, 나머지는 DATA영역), static 변수 저장
- 프로세스 생성 시점에 위의 변수들을 이 곳에 저장
- Stack
- 로컬 변수, 함수의 매개변수, 복귀 주소 등 임시자료 저장.
- 초기화 시점에는 메모리만 할당
- 보통 높은 주소에서 낮은 주소로 할당(보통 Descending stack)
- Heap과 반대로
- Heap
- 동적 할당을 위한 메모리 영역.
- 초기화 시점에는 메모리만 할당
- 보통 낮은 주소에서 높은 주소로 할당(Stack과 반대로)
- Code
- 프로그램 실행 파일 내의 명령어들(소스코드) 저장
Stack과 Heap 메모리 영역
각각은 서로의 반대 방향으로 크기가 커진다.
Stack overflow는 stack이 heap 영역을 침범, Heap overflow는 heap이 stack 영역을 침범해 발생하는 overflow
같은 타입, 이름이라도 동적할당하냐 안하냐의 차이가 있다. 객체 인스턴스의 경우 동적으로 할당된 것이고, 할당 해제 or GC에 의해 언제든 없어진다. 항상 힙 영역으로 선언된다.
```c // c언어 기준 int foo[100]; // -> 정적으로 할당해서 stack에 저장
int* foo = malloc(sizeof(int) * 100); // 동적할당된 배열은 heap에 저장 // 해당 배열을 가리키는 포인터 foo는 stack에 저장
int* a; // stack에 포인터 저장
PCB(프로세스 제어 블록)
: 프로세스에 대한 중요한 정보들을 저장 하고있는 운영체제의 자료구조
- 프로세스 생성과 동시에 고유한 PCB 생성
- 프로세스 Context switch 발생 시 진행하던 작업을 PCB에 저장하고 switch.
- 다시 CPU 할당받으면 PCB로부터 저장되어있던 내용 불러와 작업 수행.
- PCB 내부 저장되는 것
- PID (a.k.a. Process ID) : 프로세스마다의 고유한 아이디
- 프로세스 상태(new, ready, blocked, running, terminated)
- 프로그램 카운터 : 다음으로 실행할 명령어 주소
- CPU 레지스터 : running 상태에서의 실행을 저장하기 위해 사용된다.
- PC 레지스터, AC 레지스터, IR 등등 존재
- CPU 스케줄링 정보 : 프로세스 우선순위, 스케줄 큐에 대한 포인터
멀티 프로세스
: 두개 이상의 CPU가 task 병렬적 처리.
- 한 프로그램을 실행한다 하더라도 n개의 프로세스가 실행될 수 있다.
- 메모리를 독립적으로 가지지만, 공유 메모리를 갖도록 할 수도 있다.(IPC)
IPC: 프로세스간 통신. 메시지 큐, RPC, 소켓, 공유 메모리 사용, 파이프, 세마포어 등등 다양한 방식이 있다.
장점
- 한 프로세스 장애 발생해도 다른 프로세스에 영향이 없음(안정성 높음)
- 임계영역에 대한 고민을 할 필요 없음
단점
- 자원 공유가 되지 않아 메모리 낭비
- context switch(CPU scheduling)시에 속도 저하
Reference)
https://github.com/JaeYeopHan/Interview_Question_for_Beginner/tree/master/OS
https://blockdmask.tistory.com/22
https://velog.io/@hoo00nn/%EB%A9%80%ED%8B%B0-%ED%94%84%EB%A1%9C%EC%84%B8%EC%8A%A4%EC%99%80-%EB%A9%80%ED%8B%B0-%EC%8A%A4%EB%A0%88%EB%93%9C
https://wooody92.github.io/os/%EB%A9%80%ED%8B%B0-%ED%94%84%EB%A1%9C%EC%84%B8%EC%8A%A4%EC%99%80-%EB%A9%80%ED%8B%B0-%EC%8A%A4%EB%A0%88%EB%93%9C/
http://tcpschool.com/c/c_memory_structure