×
Crocus
공부한 내용을 정리하는 블로그로 시작한
Crocus는 2014년 1월 14일 부터 시작하여
현재 월 6만명, 총 1,488,492명의 방문자 수를 기록하고 있습니다.
Donation
이제 많은 사용자들이 이용하는 만큼
더 다양한 서비스 개발/제공을 위해 후원금을 모금하고자 합니다.
후원을 해주시는 분들은 Donators 명단에 성명, 후원금을 기입해드리며
Crocus 블로그가 아닌 다른 곳에 정리해둔 저만의 내용을 공유해 드리고자 합니다.
Account
예금주 : 고관우
신한은행 : 110-334-866541
카카오뱅크 : 3333-01-7888060

👉 후원 페이지 바로가기 Donators
익명 : 5000원(Crocus응원합니다.)
busyhuman: 5000원(유용한 지식 감사합니다.)
익명 : 5000원(알고리즘 학습러)

프로세스(Process)


프로세스는 '실행 중인 프로그램'이라고 정의 할 수 있고 이는 메모리에 적재되어있는 프로세스(프로그램)이 OS에 의해 현재 제어 받고 있는 상태를 의미한다.

즉, 메인 메모리에 자신의 영역을 가지게 된 프로세스가 된다는 것이다.


** 알아두기 **

메인 메모리는 RAM이라 불린다.




프로세스 vs 프로그램


프로세스 :: 프로세스는 프로그램이 실행중인 상태가 됨을 의미한다. 이때 프로그램이 프로세스가 되려면 프로세서 점유 시간, 메모리, 파일, I/O 장치 같은 자원들이 필요로되고 OS는 프로세스를 생성, 실행 할 때 자원을 할당해준다.

그리고 프로세스는 PC, 레지스터 내용들도 포함하게 된다.


아래 그림이 프로세스가 메모리를 할당 받으면 메모리에 생성되는 영역들이다.



Code(Text) 부분

텍스트 영역은 실행 명령을 포함하는 코드들이 들어가는 부분이다.

프로그램을 시작 할 때 컴파일한 프로그램이 저장되어 있고, 읽기 전용 영역이기에 프로세스가 함부로 변경 할 수 없고 변경 시 오류를 발생시킨다. 그리고 이 영역은 변경되지 않는 불변의 부분이므로 공유 할 수 있는 영역이다.


Data 부분

데이터 영역은 프로그램의 가상 주소 공간이다.

정적(static) 변수 혹은 전역(Global) 변수를 저장하고 할당하며 실행전 0으로 초기화 한다.

이 데이터 부분은 전역 변수의 값이 변경 될 수 있으므로 읽기/쓰기 영역 이나 읽기 영역으로 초기화가 가능하다.


Heap(BSS) 부분

힙 영역은 코드 영역과는 별도로 유지되는 영역이다. 동적으로 메모리를 할당 (c에서 malloc 혹은 cpp에서 new) 하려 할 때 사용하고 해제하는 부분이다. 이때 프로세스 공유 라이브러리와 동적으로 적재도니 모듈이 서로 공유하며 있다.

메모리 할당이 동적으로 일어날 때 스택과 반대로 위로 커진다.(메모리 주소 가장 아래가 0x00000일 경우)


Stack 부분

스택 영역은 데이터를 일시적으로 저장하는 부분이다.

이 스택 영역은 지역변수, 호출한 함수의 반호나 주소, 반환 값, 매개변수 등등에 사용하고 이 부분은 힙과 반대로 밑으로 커진다.

이때 스택영역과 힙 부분이 만나면 메모리가 소진되었다는 의미가 된다.




프로세스 상태 천이(변화)



프로세스는 크게 실행 상태, 비실행 상태로 구분이 가능하다.


1. OS가 프로세스를 생성(Enter)하면 초기화를 진행 후 비실행 상태에서 대기한다.

2. 이때 실행 중인 프로세스가 종료되거나 인터럽트가 발생하면 비실행 상태 프로세스중 하나는 실행 상태로 변한다.(dispatch)

3. 만약 인터럽트가 발생했다면 인터럽트된 프로세스는 비실행 상태가 된다.

3-1. 이때 실행 상태인 프로세스가 새로운 자원을 할당받기위해 프로세서를 기다리는 비실행 상태가 되기도 한다.





좀더 깊게 보면 위의 5가지 상태 천이를 관찰 할 수 있다.


not running 상태로만 있다는건 자발적 not running인지(I/O TIME)또는 

프로세스 점유 시간 초과로 인한 수동적 not running인지 구분해야 되기에 ready stateblocked state로 나뉜다.


running - 현재 실행중이다.

ready - 어떤것때문인진 모르지만(2가지 원인) queue에 들어와있는 상태다.

blocked - I/O가 수행을 완료할때까지 또는 이용가능한 리소스가 생길때까지 기다려야 하는 상황에 blocked로 간다.

new - 프로세스가 생성되었을때

exit - 프로세스가 종료되었을때


5가지 상태 천이 프로세스 모델

new -> ready : 큐로 들어오게 한뒤 초기화 상태에서 cpu 스케줄러의 고려 대상에 포함된다.

ready - > running : cpu스케줄러에게 선택받은 프로세스는 dispatch가 되어 실행 상태로 변한다.

running -> ready : 프로세스는 자신이 가지고 있던 cpu 할당 시간을 모두 소진하여 timeout이 난 상황이다.

running -> blocked : 프로세스는 몇가지 발생한 이벤트를 기다린다( I/O 작동이 완료 되기까지 혹은 새로운 자원 할당 요구 등등)

blocked -> ready : I/O가 일을 마치고 wake up되어 다시 프로세스를 돌릴 수 있게되어 queue로 간다.




이때 프로세스가 생성되면 프로세스 제어 블록(PCB)가 생성되고 프로세스가 종료되면 PCB가 삭제된다.


그리고 이 PCB를 이용하여 프로세스가 실행됬다가 다시 queue에 들어갔을 때 정보를 저장했다가를 반복한다.


이러한 과정을 Context Switching이라 하는데 PCB와 함께 참고해보고자 한다면 아래 링크를 참조하자.





UNIX 9가지 상태 천이


1->2 과정은 user 프로세스가 돌다가 system call을 하고 trap을 통해 커널속으로 타고 들어온다는 과정이다.

그 커널속의 코드 수행하는 주체는 user 프로세스 자신이다. 그 자신이 커널속에 들어와서 커널을 라이브러리처럼 인식하고 수행한다.


2->7 과정은 preempted과정인데 자신은 아직 일을 덜끝내서 다끝내고 싶은데 CPU 시간이 다되어서 못돈 케이스이다.


7---3 이 점선은 사실상 7에 들어오는순간 3과 같은 상태가 된다는 것이다.

즉, CPU 사용 시간이 다되면 컨택스트 스위칭을 통해 pcb에 저장이 되고 

ready to run in memory가 된다.(3,7은 그림으로 구분 해 두었을 뿐)


3->2 과정은 ready queue에 있던 프로세스가 스케줄러에 의해 다시 cpu 이용 권한을 받게되면 다시 reschedule process를 하게 되는 과정이다.


2->4 과정은 I/O를 하게되면(ex: scanf) 다시 Asleep In memory가 된다. 이때는 메인메모리에서 돌다가 I/O를 하게되니 메인메모리에서 Sleep을 하게된다.


4->6 과정은 만약 I/O 시간이 엄청 길어서 메인 메모리에서 Sleep하는 시간이 길어진다면 disk로 보내야 한다. 이때 swap이 되고 쫒겨나서 disk에서 Sleep를 하게 된다. 이 swap을 1번 프로세스 swapper가 하게 된다.

이때 disk로 쫒아내도 I/O가 계속 이루어 지는 이유는 I/O는 다른 I/O 장치에서 하고 있기 때문에 가능하다.


6->5 과정은 Sleep 시간이 길었던 disk에서 wake up을 하는 과정이다.


4->3 과정은 Sleep 시간이 짧아서 바로 메인 메모리에서 wake up을 하고 ready queue에 들어가는 과정이다.

swap공간에서 wake up을 하여(현재 5번 위치는 disk 공간) 메인메모리 상태로 넣어준다.

그리고 swapper가 disk상태에서 메인 메모리 상태로 넣어주면 ready queue 상태로(3번) 들어갈 수 있다.


** 알아두기 **

swap 영역이란?0 

main memory와 disk가 있는데 disk 앞부분에 swap 영역을 잡는다.

그래서 메인 메모리에 커널영역과 유저 프로세스 영역중 유저 프로세스를 swap out 하겠다 하면 disk의 특정 정해진 영역(swap 영역)을 무조건 쓴다.


즉, swap영역은 disk에 있고 용도는 메인메모리에 있는 프로세스를 I/O하는 과정에서 Sleep를 하는데 

너무 오랜 시간동안 Sleep를 하면 메인메모리의 공간을 낭비하는 것이니 디스크에 넣는다.


이 용도로 쓰이는 것이 disk의 swap 영역이다.


또, 만약 swapped 되어 디스크 영역에 들어가면 사실상 디스크 영역에는 그 프로세스에 대한 정보(이미지)가 2개가 있다.

원래 process의 program 이미지와, swapped되어 swap 영역에 들어간 그 이미지 두가지가 있다.


만약 최초의 fork(빈 껍데기 프로세스를 만들어 줌) system call을 타고 들어온다면 (8번 과정)


8->3 과정 즉, 충분한 메모리가 있다면 ready to run in memory로 들어가게 되고


8->5 과정 증, 메모리가 부족하다면 디스크에 들어가서 기다리게 된다.

swapper가 메인 메모리에 빈 공간이 있는지 없는지 보고 스왑을 시켜줄 때 까지 디스크에서 기다린다.



디스크에는 프로세스가 1000개가 있다(돌고싶어서) 그런데 메인 메모리는 100개의 프로세스밖에 없다.

디스크는 (1TB) 메인 메모리는 (4GB)이런식이니 돌고 싶은 프로세스 중에서 우선순위가 높은, I/O가 끝난 즉, CPU time quantum만 있으면 바로 running할 수 있는 프로세스를 스케줄러가 지정해주면 스와퍼가 메인 메모리로 올려주는 역할을 한다.


2번 과정은 커널에 있다가 유저 프로세스로 가거나 아니면 계속 커널에서 수행하는 모습을 보여준다.


2번 반복, 1<->2 과정 이두개가 합쳐져서 running이라고 한다.



Context Switching & PCB


https://www.crocus.co.kr/1364?category=268776




프로세스 생성

운영체제나 응용 프로그램에서 프로세스를 생성하면 OS는 해당 프로세스의 PCB를 만들어주고 주소 공간을 할당한다.


예를들어 사용자가 게임 실행을 위해 프로그램을 실행하면 OS가 프로세스의 PID를 만들고, PCB를 생성 및 초기화를 하고 리소스를 할당해준 후 ready 상태로 큐에 넣게 된다.


이때 부모 프로세스가 자식 프로세스를 생성 할 때 fork를 이용했다고 생각했을 때는


부모 프로세스에게는 return 값이 자식 프로세스의 pid값이, 자식 프로세스에는 return 값이 0이 들어오게 된다.




프로세스 종료


프로세스를 종료하기 위해 인터럽트 혹은 시스템 호출로 중단 명령을 OS에 호출하게 된다.


이때 부모 프로세스는 다음과 같은 조건에서 자식 프로세스를 종료 할 수 있다.

1. 자식 프로세스가 할당된 자원을 초과하여 자원 사용 시

2. 자식 프로세스에 더이상 할당된 작업이 없을 때


혹은 부모 프로세스가 종료될 때 자식 프로세스가 종료되는데 이를 연속 종료라고 한다.