사용하지 않을 경우 .ONESHELL
Makefile은 별도의 쉘에서 각 쉘 명령을 실행합니다. 이렇게 하면 어떤 이점이 있나요? makefile이 동일한 쉘을 사용하지 않는 이유는 무엇입니까?
답변1
단일 셸 인스턴스에서 영수증과 관련된 모든 명령을 실행하지 않는 한 가지 이유는 명령 중 하나의 실패를 감지할 수 없기 때문입니다 make
. 에는 셸의 최종 종료 상태만 부여됩니다 . 오류 발생 시 셸이 조기 종료 되도록 make
추가로 설정해야 합니다. (이는 다중 명령 셸 호출에 필요하며 존재하지 않더라도 필요합니다.).SHELLFLAGS
-e
.ONESHELL
필요첫 번째 오류에서는 실패합니다).
SHELL
POSIX 쉘의 경우에는 모두 괜찮습니다. Makefile은 SHELL
예를 들어 /usr/bin/perl
또는 /usr/bin/python
다른 명령 해석기 로 설정할 수도 있습니다 . 그렇다면 그 사용은 적절할 수도 있고 적절하지 않을 수도 있습니다 .ONESHELL
.
.ONESHELL
기본 동작으로 전환하면 make
이전 Makefile이 손상될 수도 있습니다.
이는 POSIX 표준이나 GNU의 표준 준수와 관련된 문제는 아니지만 make
,POSIX 사양make
현재 문제에 대한 내용은 다음과 같습니다.
일부 고급 버전의 기본값
make
은 대상에 대한 모든 명령줄을 그룹화하고 단일 셸 호출을 사용하여 실행하는 것입니다.System V 접근 방식은 각 라인을 개별적으로 별도의 쉘에 전달하는 것입니다.. 단일 셸 접근 방식은 성능상의 이점이 있으며 많은 연속 라인이 필요하지 않습니다. 그러나 이 새로운 접근 방식으로 전환하면 많은 역사적 makefile에서 이식성 문제가 발생했습니다.따라서 POSIX makefile 동작은 System V와 동일하도록 지정됩니다...ONESHELL
대상 또는 대상 집합의 단일 셸 그룹을 구현하기 위해 구현 확장으로 특수 대상을 사용하는 것이 좋습니다 .
GNU는 make
System V 동작을 구현하므로 이와 관련하여 POSIX를 준수합니다.그리고필요한 경우 .ONESHELL
대체 동작을 활성화하는 대상을 제공하세요. ...이것이 make
GNU가 현재 동작을 유지하는 또 다른 이유입니다.
답변2
.ONESHELL
이는 GNU 공급업체별 확장이며 이식성이 없으며 POSIX 표준의 일부도 아닙니다.
이것이 POSIX 표준에 없는 이유는 지금까지 단 하나의 구현만이 이를 지원하기 때문일 가능성이 높습니다.
이것이 표준 기본값이 아닌 이유는 설명하기가 더 쉽습니다.
POSIX는 기존 동작을 표준화하려고 시도하며 POSIX는 특정 동작이 명백한 설계 오류로 간주되지 않는 한 기존의 기본 UNIX 구현이 표준과 충돌하는 것을 좋아하지 않습니다.
1977년 Stuart Feldman의 원래 구현에서는 make
작업 목록의 각 행을 별도의 쉘로 호출했는데 sh -ce cmdline
, 이는 이후의 모든 구현에서 기본이 되었습니다 make
.
.ONESHELL
그러나 GNU 구현(별도 참조)도 적용에 있어서는 문제가 없는 것은 아닙니다. 그 이유는 GNU make가 -e
명령을 호출할 때 쉘 플래그를 설정하지 않기 때문입니다. 이로 인해 오류가 발생할 때 여러 줄의 셸 스크립트가 .ONESHELL
종료되지 않습니다.
그 외에는 별로 메리트는 없는 것 같아요 .ONESHELL
.
make
다중 라인 쉘 스크립트는 make 파일의 백슬래시 개행 시퀀스를 통해 내부적으로 사용될 수 있습니다.make
최신 구현에서는 명령줄에 셸 관련 메타 문자가 포함되지 않은 경우 셸 호출을 피하려고 하기 때문에 성능 매개변수는 최신 구현에 적용되지 않습니다 .내 구현에서는 이 명령이 한 줄의 첫 번째 명령이고 그 뒤에 세미콜론과 간단한 다른 명령이 오는 경우에 대비하여 이 명령에 대한 인라인 지원
smake
도 구현했습니다 . 이렇게 하면 90% 이상의 경우에 셸을 호출할 필요가 없습니다.echo
echo