불행하게도 내가 찾은 것은 단지 리디렉션의 구문이거나 리디렉션이 작동하는 방식에 대한 피상적인 정보뿐이었기 때문에 이것을 알아낼 행운이 없었습니다.
내가 알고 싶은 것은 파이프나 리디렉션을 사용할 때 bash가 실제로 어떻게 변하는가입니다 stdin
. 예를 들어 다음을 실행하는 경우:stdout
stderr
ls -la > diroutput.log
stdout
로 어떻게 바뀌 나요 ls
?diroutput.log
나는 이것이 다음과 같이 작동한다고 생각합니다.
- Bash가 실행되어
fork(2)
자체 복사본을 생성합니다. - bash 프로세스를 포크하고 다음 과 같은 것을 사용
stdout
하도록 설정하십시오 .diroutput.log
freopen(3)
- 분기된 bash 프로세스가 실행되거나
execve(2)
유사한 exec 기능이 자체적으로 교체되어ls
이제stdout
bash 설정을 사용합니다.
그러나 그것은 단지 내 경험에 근거한 추측일 뿐입니다.
답변1
strace -f
나는 이 문제를 해결하기 위해 C를 사용하고 간단한 개념 증명을 작성할 수 있었습니다 .
execve
내 생각대로 bash는 호출하기 전에 하위 프로세스의 파일 설명자를 조작하는 것 같습니다 .
작동 원리는 ls -la > diroutput.log
대략 다음과 같습니다.
- 배시 통화
fork(2)
- 분기된 bash 프로세스는 출력 리디렉션을 확인
diroutput.log
하고open(2)
. - 포크된 bash 프로세스는 파일 설명자를 시스템 호출
stdout
로 대체합니다.dup2(2)
execve(2)
bash는 이를 대체하는 실행 가능 이미지를 호출ls
한 다음 이미 설정된 이미지를 상속합니다 .stdout
관련 시스템 호출은 다음과 같습니다( strace
출력).
6924 open("diroutput.log", O_WRONLY|O_CREAT|O_TRUNC, 0666) = 3
6924 dup2(3, 1) = 1
6924 close(3) = 0
6924 execve("/bin/ls", ["ls", "-la"], [/* 77 vars */]) = 0