카테고리 없음
3. Process API?
HWAN JJ
2022. 5. 16. 17:37
Summary
Process API 들에 대해서.
- Process API는 System Call이다
- fork(), exec(), wait()란?
- fork()와 exec()를 분리한 이유는?
- IO redirection
- pipe
fork() 함수? 자식 프로세스를 생성하는 API
Child process는 Separate memory space를 할당 받는다. 부모 프로세스와 같은 메모리 요소들을 가지고 있다.
- Child process has its own registers, and program counter (PC)
- 자식 프로세스는 부모 프로세스의 메모리를 복사한 다른 메모리를 사용한다. (부모, 자식 사이의 공유 X)
fork() 함수는 부모 프로세스에 pid를 return하고 자식 프로세스에는 0을 return 한다.
- 부모 프로세스와 자식 프로세스는 다른 pid를 가지게된다
- rc == 0 , rc > 0을 통해서 부모, 자식을 구분하고 프로그래밍 가능하다
⇒ 문제는?
- 자식, 부모의 실행 우선순위를 보장할 수 없음
- 자식, 부모 process는 independent 하고, 사이에 dependency가 없음
위에 문제를 해결하기 위해 wait() 함수가 등장했다.
- wait() 함수는 부모 프로세스에서 실행되고, 자식 프로세스가 종료(exit())해서 자식의 pid를 return할 때까지 부모 프로세스를 대기시킨다.
- 이를 통해서, 부모, 자식 프로세스 사이의 우선순위와 의존성을 만들 수 있다.
그러면 exec() 는 무슨 함수인가?
- fork() 함수의 경우, 부모의 코드를 그대로 복사, 그런데 난 child에서 다른 프로그램을 실행하고 싶어⇒ Code를 새로운 Code으로 덮어씌우고, stack, heap 초기화해주는 exec() 함수
⇒ OS needs to load a new binary image, new stack, new heap... - 2개의 parameter 필요
- The name of binary file (실행하고자 하는 파일)
- The array of arguments (실행을 위한 인자들)
만약 exec()를 자식 프로세스에서 실행하면, 자식 프로세스의 그 이후의 실행문들은 실행되지 않아야한다.
exec()함수는 return 하지 않는다. 새로운 프로그램을 실행할 뿐이다.
Question. 그러면 forkandexec처럼 둘을 묶은 함수를 만들면 안 될까?
- 2가지 이유가 있다.
- To manipulate various settings before executing
- Make I/O redirection and pipe possible
I/O redirection : 프로세스의 결과를 전달하는 또 다른 방법
- file descriptor을 이용해서 program의 결과를 다른 파일에 저장할 수 있게해준다.
- cat w3.c > newfile.txt ⇒ 이 경우에는 w3.c의 내용이 newfile.txt에 저장된다.
- 반대로 프로그램의 입력을 파일로 받는 것도 가능하다.
- ./a.out < input.txt ⇒ input.txt가 a.out의 input으로 들어간다.
- How?
- close() 함수를 이용해 STDOUT_FILENO(1), STD_INFILENO(0)을 닫고
- open() 을 이용해 다른 파일들을 여는 방식으로 가능하다.
File descriptor
- 0 = STDIN, 1 = STDOUT, 2 = STEDERR ⇒ 기본으로 할당된 값들
- 각 fd마다 offeset이 있어서 offset 부터 읽는다.
- close(1) 을 하고 open하면 1부터 할당된다.
- file, pipe, directory, device 다 표현가능
- 어떤 파일에 대한 포인터라고 생각할 수 있다. 리눅스 OS의 경우 모든 file, pipe, directory, device 들을 파일로 간주해서 처리하기 때문에 굉장히 유용한 파일을 향한 포인터
System calls about fd
- open()
- Allocate new file object, fd, and set the fd에 새로 할당된 file object 연결
- fd를 할당할 때는 비어있는 값중 가장 작은 값부터 할당해서 연결해준다.
- close()
- fd 할당 해제
- 더이상 연결된 fd가 없으면 연결되어 있던 file object도 해제
- fork()
- 자식 프로세스는 부모의 fd table도 복제한다.
- offset 역시 복제한다.
- exec()
- retains file descriptor table (fd 유지)
- retains file descriptor table (fd 유지)
PIPE
- 한 프로그램의 ouput을 다른 프로그램의 input으로 줄 수 있다.
- "|" 을 사용
- Ex) echo hello world | wc
dup(), pipe() 함수..
- Ordinary pipe
- 그냥 "|" 사용
- Unidirectional byte stream
- No structured communication
- 프로세스가 사라지면 pipe도 사라진다.
- Anonymous Pipe - int pipe(int fd[2])
- 한계: 오직 하나의 pair의 프로세스 간의 communication을 지원
- Named Pipe
- mkfifo(), mknod로 생성
- 어떤 경로에 대한 pipe를 지정가능하다
pipe vs I/O redirection
- pipe는 자동으로 clean themselves up, I/O redirection은 임시 파일 사용시 따로 삭제 필요
- pipe 는 임의의 긴 data pass 가능, file redirection은 충분한 크기의 파일 필요
- pipe는 writer, reader 둘 다 parallel 하게 실행, io redirection은 순차적으로 실행