ghc.mk
이것은 하스켈 소스 컴파일의 일부에서 발췌한 코드입니다. 저자가 한 줄에 펑션 블록을 작성하기로 결정했기 때문에 다르다는 것을 알았습니다. 이것이 makefile 작성에 대한 일반적인 관행입니까?
디버깅을 위해 각 케이스 핸들에 명령문을 넣는 것을 좋아 echo
하지만 현재 설정으로는 echo 명령문을 쉘 명령으로 해석할 수 없습니다.
define installLibsTo
$(call INSTALL_DIR,$2)
for i in $1; do \
case $$i in \
*.a) \
$(call INSTALL_DATA,$(INSTALL_OPTS),$$i,$2); \
$(RANLIB_CMD) $2/`basename $$i` ;; \
*.dll) \
$(call INSTALL_PROGRAM,$(INSTALL_OPTS),$$i,$2) ; \
$(STRIP_CMD) $2/`basename $$i` ;; \
*) \
$(call INSTALL_DATA,$(INSTALL_OPTS),$$i,$2); \
esac; \
done
endef
답변1
makefile의 구문에서 이를 요구하기 때문에 전체 쉘 명령은 단일 논리 행에 있습니다. makefile 규칙에서 각 레시피 행은 별도의 셸 인스턴스에서 실행됩니다. 파서가 이 지점에 도달하기 전에 백슬래시 개행 시퀀스가 제거되므로 바로 뒤에 오는 백슬래시 개행 문자는 개행 문자로 처리되지 않습니다. 즉, 다음과 같이 작성할 수 있습니다(탭 하나에 공백 8개를 사용했습니다).
target:
for x in $^; do \
somecommand $$x; \
done
다음과 같은 쉘 명령을 실행하여 빌드합니다 target
.
for x in dependency1 dependency2 dependency3; do somecommand $x; done
쉘은 여기서 개행 문자를 수신하지 않습니다(그래서 ;
before가 필수입니다 done
).
이 메이크파일을 작성한 경우:
target:
for x in $^; do
somecommand $$x;
done
그런 다음 각 for x in …; do
, somecommand $x;
및 는 done
별도의 셸에서 실행되지만 작동하지 않습니다.
표시되는 변수는 installLibsTo
동일한 제약 조건을 갖는 더 큰 예입니다. 사용되면 두 개의 논리적 레시피 라인으로 확장됩니다. 하나는 함수를 호출하여 구성된 명령을 실행 INSTALL_DIR
하고 다른 하나는 for 루프를 실행합니다.