포크와 exec는 어떻게 작동합니까?


17

경험이 많지 않고 사용자 수준에서 하드웨어로 해석하는 방법에 프로세스에 참여하려고합니다.

따라서 명령이 셸에서 시작되면 명령 fork()의 자식 프로세스를 상속하고 자식 프로세스를 exec()메모리에로드하고 실행합니다.

  1. 하위 프로세스에 상위 프로세스의 모든 속성 (원래 프로세스)이 포함 된 경우이 하위 프로세스의 필요성은 무엇입니까? 원래 프로세스도 메모리에로드되었을 수 있습니다.
  2. 이 개념 forkexec개념 이 UNIX의 모든 실행 프로그램에 적용됩니까? 쉘 스크립트 또는 명령에만 해당합니까? 쉘 내장 명령에도 적용됩니까?
  3. 명령 / 스크립트를 실행할 경우 copy on write 개념 은 언제 사용됩니까?

한 번에 많은 질문을 한 것은 유감이지만 명령 실행에 대해 생각할 때이 모든 질문이 한 번에 떠 오릅니다.


나는 이것이 중복이라고 말하지는 않지만 귀하의 질문 중 일부는 여기에 대답되어 있다고 생각합니다 : unix.stackexchange.com/questions/136637/…
goldilocks

답변:


22

따라서 명령이 셸에서 시작되면 fork ()는 자식 프로세스를 상속하고 exec ()는 자식 프로세스를 메모리에로드하고 실행합니다.

좀 빠지는. fork()현재 프로세스를 복제하여 동일한 자식을 만듭니다. exec()새로운 프로그램 을 현재 프로세스에 로드하여 기존 프로그램 을 대체합니다.

내 질문은 :

자식 프로세스에 부모 프로세스의 모든 속성 (원래 프로세스)이 포함되어 있으면이 자식 프로세스의 필요성은 무엇입니까? 원래 프로세스도 메모리에로드되었을 수 있습니다.

부모 프로세스가 아직 종료되기를 원하지 않기 때문입니다. 새로운 프로세스가 진행되고 동시에 실행되는 무언가를 원합니다.

이 포크와 실행 개념은 UNIX의 모든 실행 프로그램에 적용됩니까? 쉘 스크립트와 마찬가지로 명령에만 적용됩니까? 쉘 내장 명령에도 적용됩니까?

외부 명령의 경우, 쉘은 fork()명령이 새 프로세스에서 실행되도록합니다. 내장은 쉘에 의해 직접 실행됩니다. 또 다른 주목할만한 명령은이며 exec, 먼저 쉘을 exec()외부 프로그램에 알리지 않습니다 fork(). 이것은 쉘 자체가 새로운 프로그램으로 교체되어 더 이상 종료 될 때 해당 프로그램으로 돌아 오지 않음을 의미합니다. 당신이 말한다면, exec true다음 /bin/true은 종료됩니다, 그래서 더 이상 터미널에서 실행 아무것도 남기지 않고, 쉘, 즉시 종료를 대체합니다.

명령 / 스크립트를 실행하면 copy on write 개념이 사용되는 경우

석기 시대에는 fork()실제로 호출 프로세스의 모든 메모리를 새 프로세스로 복사해야했습니다. 쓰기시 복사는 두 프로세스가 동일한 메모리를 모두 공유하기 시작하고 필요한 경우 두 프로세스가 기록한 페이지 만 복사되도록 페이지 테이블을 설정하는 최적화입니다.


4
"거의 모든 명령에서 쉘은 fork ()를 수행하여 명령이 새로운 프로세스에서 실행되도록합니다. 해당 명령이 내장 된 경우 하위 프로그램은 별도의 프로그램을 exec () 할 필요가 없습니다." 좋은 대답이지만이 부분을 편집해야합니다. 내장을 실행할 때 쉘은 포크되지 않습니다. 활성 쉘 프로세스에서 직접 실행합니다. 이것은 내장 이 작동 cd하거나 read작동 할 수 있는 유일한 방법 입니다. 포크가 없기 때문에 내장 명령이 외부 명령보다 훨씬 빠릅니다.
John Kugelman은 Monica

6
  1. 일부 프로그램의 경우 자식 프로세스는 한 가지 작업 (직렬 포트에서 읽고 터미널에 쓰기)을 수행하고 부모 프로세스는 다른 작업 (터미널에서 읽고 직렬 포트에 쓰기)을 계속합니다. 또 다른 고전적인 예는 자식 프로세스가 오래 실행되는 계산에 대한 검사 점을 수행한다는 것입니다. 대부분의 자식 프로세스는 디렉토리 변경, 신호 처리기 재설정 또는 파일 설명자 재설정과 같은 일부 설정을 수행 한 다음 execve()다른 코드로 오버레이하도록 호출 합니다.
  2. fork()그리고 exec()모든 실행 파일에 적용 할 - 실제로는 argc와 argv를, 그리고 파이프와 함께 포크와 간부는 다른 운영 체제에서 유닉스를 구별 무엇입니까. fork()BSD vfork(), Plan 9 rfork()및 Linux와 같은 몇 가지 전문화 또는 일반화가 존재 clone()하지만 교장은 동일하게 유지됩니다.
  3. "쓰기시 복사"는 실제로 사용자에게 표시되지 않으며 하위 프로세스 작성을 최적화하고 실행하는 동안 더 많은 기술입니다. 호출 스택 및 힙 ( malloc()또는 정적 또는 전역 범위 변수로 할당 된 메모리 )은 "쓰기시 복사"일 수 있습니다. 하위 프로세스가fork()커널은 자식 프로세스가 부모 프로세스와 힙 및 스택과 정확히 동일한 메모리 페이지를 갖도록 자식 프로세스를 설정합니다. 하드웨어 (메모리 관리 장치)가 힙 또는 스택의 쓰기를 감지하면 커널은 새로운 물리적 메모리 페이지를 가져 와서 부모의 페이지를 새 페이지에 복사 한 다음 해당 새 페이지를 자식 프로세스의 스택 또는 힙에 매핑합니다. 이것은 자식 프로세스를 위해 스택과 힙을 완전히 복사하는 것보다 커널이 페이지 매핑을 설정하는 데 시간이 덜 걸리기 때문에 최적화를 구성합니다.

답변 주셔서 감사합니다 브루스. 그러나 당신이 여기에 말한 많은 것들이 내 머리 위로 가고 있습니다. 나는 이것들에 대해 많은 지식이 없다. 나는 당신이 언급 한이 기능들이 작동하도록 노력할 것이다. 정말 고맙습니다..!!
Prib

4
하위 프로세스에 상위 프로세스의 모든 속성 (원래 프로세스)이 포함 된 경우이 하위 프로세스의 필요성은 무엇입니까? 원래 프로세스도 메모리에로드되었을 수 있습니다.

이 질문은 메모리 제약이 심한 상황에서 작동해야하고 한 번에 메모리 / 주소 공간에서 실행 프로세스가 하나 뿐인 초기 Unix 구현을 살펴보면 매우 예시 적으로 대답 할 수 있습니다.

멀티 태스킹은 프로세스를 디스크로 교체하고 다른 프로세스를 교체하여 달성되었습니다.

이제 fork시스템 호출은 거의 동일했습니다. 프로세스를 디스크로 스왑했지만 다른 프로세스를 스왑하는 대신 인 메모리 사본에 다른 프로세스 ID를 부여하여 리턴했습니다. 그리고 이것은이 프로세스가 exec결국 다른 실행 파일로 결정하는 적절한 시점이었습니다 .

fork+ exec실제로 스폰에 비해 눈에 띄는 오버 헤드가 발생하지 않았습니다. 어쨌든 프로세스를 디스크로 교체해야했고, 어쨌든 실행 가능한 메모리 위치에 이전 프로세스 이미지가있었습니다.

사용 가능한 메모리 및 메모리 관리 장치의 양이 증가하고 메모리 내 프로세스가 여러 개 증가함에 따라 포크의 초기 무시할 수있는 비용은 일부 아키텍처에서 다소 성가신 요소가되었습니다 vfork.


2

이것을 이해하기 쉽게 만들기 위해 유추를 사용할 것입니다. 파이를 굽자!

우리는 레시피 북을 잡고 읽기 시작하고 수제 빵 껍질로 딸기 대황 파이 (내가 가장 좋아하는 것)에 정착합니다. 계란과 과일을 제외하고 우리가 필요한 거의 모든 것이 부엌에 있지만, 농장에 살고 과일이 계절이기 때문에 이것은 문제가되지 않습니다. 문제는 오븐이 고장 나서 모든 일을 할 시간이 충분하지 않다는 것입니다. 둘 이상의 사람을 갖는 것이 좋지 않습니까?

구조에 fork (). 이제 두 사람이 있습니다. 우리는 파이 크러스트를 만들기 위해 부엌으로 향합니다. 죄송합니다. 그래서 우리는 포크에서 돌아 오는 것을 봅니다. 나는 그가 0을 얻었던 큰 수를 얻었다. 그래서 그가 닭장과 정원에 밖으로 향하는 동안 나는 부엌에 향한다. 내가 오븐을 지나갈 때 다시 포크 (), 반환 값을보십시오 : bummer 0을 얻었습니다. 내가 깨진 오븐을 응시하면서 그는 밀가루를 계속합니다. 문을 열고 빛이 없으면 문을 닫습니다. 오븐을 고치는 법을 아는 사람이 있습니까?

구조에 exec (). 공구 벨트의 전압계에 도달하면 전구가 진단 될 수 있으므로 전원을 확인하고 실제로 차단기가 작동하며 쉽게 고칠 수 있습니다. 차단기 패널로 걸어 가면서 동료가 대황을 타는 것을 봅니다. 왝! 나는 초콜릿 실크 파이를 선호합니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.