2011-12-13 6 views
9

나는 꽤 오랫동안 이것을 고심하고 있었고, cmake에 대한 나의 모험은 내가 확실히 틀렸다는 확신을주는 해킹 된 해결책을 가져왔다. cmake를 사용하여 내 C++ 프로젝트를 구조화하는 올바른 방법은 무엇입니까?

-libfolder 
    -codepart1folder 
    -CMakeLists.txt 
    -codepart1.cpp 
    -codepart1.hpp 
    -codepart2folder 
    -codepart3folder 
    -lib.cpp 
    -lib.hpp 
    -CMakeLists.txt 

내가 (일부 실험 후) 라이브러리를 컴파일하는 CMakeLists 파일을 쓰고, 나는은 lib.a 파일을 생성 할 수 있습니다 : 다음과 같이

나는, 여러 개의 파일로 구성 라이브러리를 만들었습니다. 이제이 코드를 다른 프로젝트의 라이브러리로 포함시키고 lib.hpp의 인터페이스를 통해 액세스하려고합니다. 디렉토리 구조의 관점에서이 작업을 수행하는 가장 좋은 방법은 무엇이며 루트 프로젝트의 CMakeLists.txt에 넣어야하는 것은 무엇입니까?

나의 현재 시도가 명령을 내 현재 프로젝트에 하위 폴더로 -libfolder 추가하고 추가 할 수있다 :

include_directories(${PROJECT_SOURCE_DIR}/libfolder) 
link_directories(${PROJECT_BINARY_DIR}/libfolder) 
add_subdirectory(libfolder) 
target_link_libraries(project lib) 

내가 만들어 실행하면 라이브러리가 잘 컴파일하지만 project.cpp은 컴파일 할 때, 그것은 codepart1.hpp (project.cpp에서 포함 된 lib.hpp에 포함되어 있음)를 찾을 수 없다는 불평을합니다.

이것이 잘못된 방법이라고 생각하지만, CMake 문서를 보면서이 같은 프로젝트를 설정하는 좋은 지침서를 찾을 수는 없습니다. 도와주세요, CMake 구루!

+0

아마도 cmake per-see에는 도움이되지 않을지 모르지만 전 premake를 살펴 보도록 조언합니다. 그것은 성숙에 가까워지고 cmake에게 많은 이점을줍니다 (하나는 lua를 이미 알고있는 경우 특히 속도가 빨라지기 쉽습니다). http://industriousone.com/what-premake에서 확인할 수 있습니다. – Ylisar

+1

그래서 새 프로젝트에서 이전에 빌드 된 라이브러리를 사용하도록 설정 하시겠습니까? 아니면 sortof 메타 프로젝트에서 빌드 하시겠습니까? – moooeeeep

답변

2

좋아, 그래서 CMake 전문가입니다 내 동료 상담 후에는 3 옵션을 떠나, 내가 뭘하려고 오전를 지원하지 않는 CMake를 보인다

  1. 을 모두 추가 부모 프로젝트 CMakeLists.txt에 대한 의존성 - 매우 깨끗하지는 않지만 일을 할 수 있습니다. 코드를 추가하는 모든 프로젝트에 대해이 작업을 수행해야하며 라이브러리가 변경된 경우 되돌아 가서 수정해야합니다.

  2. 라이브러리 헤더를 정리하십시오. 이것은 일부 컴파일러 해커를 통해 수행됩니다. 아이디어는 모든 클래스를 forward-declare하고 포인터 또는 boost :: shared_ptr 만 사용하고 cpp 파일에만 종속성을 포함시키는 것입니다. 그렇게하면 모든 findpackage 항목을 사용하여 cpp 파일을 빌드 할 수 있으며 헤더 만 포함하고 라이브러리에 링크 만하면 lib를 사용할 수있는 보너스를 얻게됩니다.

  3. 빌드 시스템을 살펴보십시오. 복잡한 의존성을 가진 이식성있는 코드와 빠른 코드 컴파일은 문제가 해결되지 않았습니다! 내 조사 결과 꽤 복잡 해졌다. 나는 동료 직원을 채용하여 결국 Google에서 가져온 것을 사용하여 cmake에서 만든 시스템을 구축했습니다.

+0

+1, 3 rdparty include-dirs을 필요로하지 않는 인터페이스를 정리하는 것이 훨씬 좋습니다. –

5

하나의 CMake 프로젝트를 다른 프로젝트로 가져 오는 명확한 방법은 find_package 명령을 사용하는 것입니다. 패키지 선언은 export 명령을 사용하여 수행됩니다. find_package를 사용하면 패키지 파일에 대한 경로를 하드 코딩 할 필요가 없습니다.

누락 된 hpp 파일에 대해서는 codepart1folder가 포함되지 않았으므로 포함 경로에 없습니다.

+0

Ok ...이 대답에서 find_package와 export가이 경우에 사용할 올바른 것인가, 아니면 어떻게 할 것인가에 대한 것은 분명하지 않습니다. 제발 좀 더 자세히 설명해 주시겠습니까? – dlants

+0

include_directories ($ {PROJECT_SOURCE_DIR}/libfolder/codepart1folder) – LeDYoM

1

게시물을 보면 'codepart1folder'를 포함에 추가하지 않는 것 같습니다. 어떻게이 포함되어 codepart1.hpp는 같이

#include <codepart1.hpp> 
#include "codepart1folder/codepart1.hpp" 

나는 cmake 프로젝트를 구성하는 표준 접수 방법이라고 생각하지 않습니다. 나는 cmake repos의 무리를 보았고 그들은 차이점이있는 경향이있다. 개인적으로 나는 다음을 수행하십시오

-project 
    CMakeLists.txt 
    -build 
    -cmake 
     OptionalCmakeModule.cmake 
    -src 
     -Main 
      Main.cpp 
      Main.hpp 
     -DataStructs 
      SomeTree.hpp 
      SomeObject.hpp 
     -Debug 
      Debug.hpp 
     -UI 
      Window.hpp 
      Window.cpp 

기본적으로 그 모든 소스 코드는 1 디렉토리에 덤프를, 당신은 소스의 부족이 빌드 수행 'MKDIR은 & &이 CD & & cmake를 구축 구축 .. & & 메이크업을 '을 프로젝트 루트 폴더에 저장하십시오.

프로젝트의 일부로 별도의 libs가있는 경우 별도의 libs 디렉토리와 특정 lib의 다른 하위 폴더가 필요할 수 있습니다.

CMakeLists.txt 파일을보고 싶으면 https://github.com/dcbishop/에 내 리포지토리가 있습니다. 내 프로젝트 구조

주요 문제는 나는 그들이 포착되지 않습니다 당신이 실행 한 후 파일을 추가하는 경우 다음 'cmake ..을'(일을 할 수있는 '잘못된'방법은 분명히있는 FILE_GLOB를 사용하는 것이 있습니다 당신은 'make'라고합니다).나는 그것을 할 수있는 '올바른'방법이 무엇인지 알지 못했다. (내가 볼 수있는 것에서는 별도의 파일 목록을 유지하는 것이 포함된다.) 또한 CMakeLists.txt 파일을 1 개만 사용한다.

일부 프로젝트는 cpp 및 hpp 파일을 별도의 디렉토리로 분리하도록 선택합니다. 그래서 당신은 include와 src 폴더를 가질 것이다. (적어도 외부 적으로 사용되는 hpp 파일들에 대해서는). 나는 이것이 주로 큰 도서관 인 프로젝트를위한 것이라고 생각합니다. 또한 헤더 파일을 훨씬 쉽게 설치할 수 있습니다.

+0

을 사용하십시오. codepart1folder는 libfolder 내의 CMakeLists.txt 파일에 포함되어 있습니다. 프로젝트 폴더의 CmakeLists.txt에 모든 하위 폴더, include 및 링크를 추가해야하는 것은 잘못되었습니다. 왜냐하면 project.cpp는 그 중 하나에 의존하지 않기 때문에 lib.hpp만이 그렇습니다. 트리에서 라이브러리를 정의하는 project2가 있고 project2를 프로젝트의 하위 파트로 사용하고 싶다고 상상해보십시오. – dlants

+0

@ JohnSavage. 하지만 그것은 올바른 방법입니다 ... lib-project에 LIB_INCLUDE_DIRS 변수를 생성합니다. 필요한 모든 종속적 인 include-dir을 포함하는 CMakeCache에 "export"됩니다. 그런 다음 프로젝트를 만들 때 변수가 있다고 가정합니다. –

+0

github 링크 +1 +1 – hAcKnRoCk

0

당신은 아마 이러한 경우

include_directories(${PROJECT_SOURCE_DIR}/libfolder/codepart1folder) 

누락 당신은 포함 디렉토리 경로 변수에 모든 폴더를 추가 할 수 set(CMAKE_INCLUDE_CURRENT_DIR on) 할 수 있습니다.

올바른 include 폴더가 설정되었는지 여부에 관계없이 cmake의 출력을 명령 줄에서 확인하십시오. 또한 cmake 변수에 대해 항상 "인쇄 디버깅"으로 message()을 사용할 수 있습니다. 그러나 include 디렉토리의 경우 디렉토리 등록 정보를 읽어 실제로 include 디렉토리에 있는지 확인해야합니다.

get_property(inc_dirs DIRECTORY PROPERTY INCLUDE_DIRECTORIES) 
message("inc_dirs = ${inc_dirs}") 

이 정보가 도움이 되었기를 바랍니다.

편집

난 그냥 libfolder에 추가 codepart1folder에 대한 의견을 보았다. libfolder의 include_directory 경로에서만 사용할 수 있으며 루트 폴더로 전파되지 않습니다. include codepart1.hpp는 lib.hpp에 있기 때문에 프로젝트 경로에서도 사용할 수 있어야합니다. 그렇지 않으면 프로젝트를 빌드 할 때 누락 된 선언 오류가 발생합니다.

+0

좋아, 이것이 제 문제입니다. 부모 프로젝트에 하위 폴더를 모두 포함시켜야 할 필요가없는 것 같습니다. lib는 자체 CMakeLists.txt가있는 자체 포함 된 코드이며 lib.a로 잘 컴파일됩니다. 모든 프로젝트를 내가 사용하고자하는 모든 프로젝트에 연결하고 싶지는 않습니다. – dlants

+1

그러면 lib를 적절하게 인터페이스해야합니다. – Bort

관련 문제