2014-02-18 7 views
1

일반/패턴 특정 규칙이있는 큰 프로젝트의 gnu 메이크 파일을 수정하려고합니다.조건에 따라 특정 개체 재구성

메이크 파일은 별도의 규칙으로 컴파일 및 연결됩니다. 특정 조건이 링크 시간에 성공하면 다시 링크하기 전에 컴파일 규칙을 다시 호출해야한다는 특정 요구가 있습니다. 메이크 파일의 샘플 문제는 다음과 같습니다.

$(obj_dir)/%.o: $(src_base)/%.cpp 
    @echo Compiling: $< 
    $(q)$(CXX) $(CXXFLAGS) $(REV) $(CXX_INCLUDE_PATH) -o [email protected] $< 

    $(link_files) : 
    @echo Linking [email protected] 
    $(q)$(CXX) $(LINKFLAGS) -o [email protected] %.o 
    ifeq (1,1) 
    #condition pass so I want to call generic above ompilation rule again 
     ????? 
    else 
     $(warning Do Nothing) 
    endif 

제네릭 컴파일 규칙을 재귀 적으로 또는 다른 방법으로 다시 호출 할 수있는 방법에 대해 도움을받을 수 있습니까?

도움을 주시면 대단히 감사하겠습니다. 미리 감사드립니다.

+0

개체 파일을 연결 규칙의 전제 조건으로 사용하지 않으시겠습니까? 이 경우 컴파일 규칙을 다시 호출하면 오브젝트 파일이 이미 최신 상태가되므로 아무 작업도 수행하지 않습니다. – Beta

+0

감사합니다. 오브젝트 파일을 링크 규칙 종속성으로 추가 할 수 있거나 컴파일 규칙을 다시 호출하기 전에 링크 파일을 제거 할 수 있습니다. 링크 규칙 내에서 호출 컴파일 규칙을 다시 호출 할 수있는 방법에 대한 원래 질문을 도와 줄 수 있습니까? – Akamai

+0

Make가 어떻게 작동하는지 오해 한 것 같습니다. 원하는 오브젝트 파일의 목록이있는 경우 컴파일 규칙을 다시 호출하기는 쉽지만 그렇게하는 것으로는 어떤 의미도 보이지 않습니다. 개체 파일을 다시 빌드하려는 이유 *를 말씀해 주시겠습니까? – Beta

답변

0

나는 베타에 동의한다. 이것은 미친 듯하다.

하지만 어쨌든 그냥하고 싶다면 매우 간단합니다. 그렇지만, 여기에는 레시피 안에 테스트로 테스트를 작성해야합니다. make 테스트 (ifeq 등)를 사용할 수 없습니다. 그런 다음 재귀 적 make를 호출하여 파일을 빌드하고 -W 플래그를 사용하여 강제로 다시 빌드 할 수 있습니다. (당신이 다시 할 파일을 가정처럼 뭔가 foo.cpp입니다 :

$(obj_dir)/%.o: $(src_base)/%.cpp 
     @echo Compiling: $< 
     $(q)$(CXX) $(CXXFLAGS) $(REV) $(CXX_INCLUDE_PATH) -o [email protected] $< 

$(link_files) : 
     @echo Linking [email protected] 
     $(q)$(CXX) $(LINKFLAGS) -o [email protected] %.o 
     if [ 1 -eq 1 ]; then \ 
      $(MAKE) -W $(src_base)/foo.cpp $(obj_dir)/foo.o || exit 1; \ 
     else; \ 
      echo do nothing; \ 
     fi 
+0

고마워. 아직 테스트하지는 못했지만 이것에 작은 혼란이있다. 하나의 개체가 여러 .cpp 파일로 구성 될 수있는 곳에서 원본 파일을 명시 적으로 지정하고 있습니다. 재귀 적 make를하기 전에이 객체가 어떤 소스 파일로 구성되는지 알 수있는 방법이 있거나 링크 규칙을 호출하기 직전에 처리 된이 객체에 대한 부모 컴파일 규칙/s을 호출하는 방법이 있습니까? 나는 Makefile이 다른 객체들을 위해 스스로 실행되어야 할 필요가 있다고 요청한다. – Akamai

+0

나는이 질문을 이해할 수 있을지 잘 모르겠지만, 일반적으로 어떤 선행 조건으로 인해 다른 규칙을 만들지 결정하는 기본 제공 방법은 없습니다. 컴파일 할 때'$ (eval ...)'을 사용하는 것은 매우 어렵습니다. 컴파일 규칙에'$ (eval $ @ _ SRC : = $ <)'나중에 변수'$ ($ (obj_dir) /foo.o_SRC)'를 사용하여 검색 할 수 있습니다. – MadScientist

2

1 단계 : 얻을 기본 메이크 작업 어쩌면 당신은 이미이있다, 그러나 여기 개요입니다 :.

OBJECTS := $(obj_dir)/foo.o $(obj_dir)/bar.o $(obj_dir)/baz.o 
# You MUST have a list like this somewhere, constructed somehow. 

$(obj_dir)/%.o: $(src_base)/%.cpp 
    @echo Compiling: $< 
    $(q)$(CXX) $(CXXFLAGS) $(REV) $(CXX_INCLUDE_PATH) -o [email protected] $< 

$(link_files) : $(OBJECTS) 
    @echo Linking [email protected] 
    $(q)$(CXX) $(LINKFLAGS) -o [email protected] $^ 

하는 수는 계속 진행하기 전에 제대로 작동하는지 확인하십시오. 특히 다음과 같이 명령 행에서 REV의 값을 전달할 수 있는지 확인하십시오.

make REV=123 

2 단계 : 재귀 호출을 테스트하십시오. 처음에는 무조건 선택하십시오.

$(link_files) : $(OBJECTS) 
    @echo Linking [email protected] 
    $(q)$(CXX) $(LINKFLAGS) -o [email protected] $^ 
    $(MAKE) REV=$(NEWREV) $(OBJECTS) 

3 단계 : 시험 조건. 이 조건 출력 문이다

$(link_files) : $(OBJECTS) 
    @echo Linking [email protected] 
    $(q)$(CXX) $(LINKFLAGS) -o [email protected] $^ 
    $(MAKE) REV=$(NEWREV) $(OBJECTS) 
    if [ 1 -eq 2 ];\ 
     then echo Do Something; \ 
    else \ 
     echo Do Nothing; \ 
    fi 

주의가 아닌 조건부 확인 출력 문을합니다. (어떤 규칙을 실행하기 전에 make 문을 평가하는 경향이 있습니다.) if 앞에 TAB이 있지만 조건문의 다른 줄 앞에있는 공백은 공백입니다.

4 단계 :.

$(link_files) : $(OBJECTS) 
    @echo Linking [email protected] 
    $(q)$(CXX) $(LINKFLAGS) -o [email protected] $^ 
    $(MAKE) REV=$(NEWREV) $(OBJECTS) 
    if [ 1 -eq 2 ];\ 
     then $(MAKE) REV=$(NEWREV) $(OBJECTS); \ 
    else \ 
     echo Do Nothing; \ 
    fi 
+0

감사합니다 베타. 나는 당신의 솔루션을 테스트하지는 않았지만 비슷한 방법론을 따르는 비슷한 Makefile을 만들 수 있었지만 몇 가지 사용자 정의 규칙을 추가로 도입하여 특정 객체에 대한 새 개정판을 기반으로 특정 규칙을 재귀 적으로 호출 할 수있었습니다. – Akamai

관련 문제