Сбой связывания CMake - PullRequest
       6

Сбой связывания CMake

2 голосов
/ 22 июля 2010

Я настраиваю свой проект для CMake, и у меня возникают проблемы со связыванием - все файлы проекта компилируются успешно, затем он говорит, что связывает и сообщает о всевозможных символах, не найденных

Эти символы в основном предоставлены моим собственным кодом, в то время как некоторые из них предоставлены BerkeleyDB, который правильно расположен и включен.

Вот мой высокоуровневый CMakeLists.txt:

cmake_minimum_required(VERSION 2.6)

project( rpdb C )

#   add local modules path for project
set( CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/cmake/Modules/" )

#   where to look for source files (headers and source)
include_directories( include src )

#   define sub-directories of source that cmake knows about as well a where their output will be put
add_subdirectory( src bin )

#   compiler-dependent flags:
if( CMAKE_COMPILER_IS_GNUCC )
    #   gcc
    add_definitions( -ggdb -fsigned-char -freg-struct-return -Wall -W -Wshadow -Wstrict-prototypes -Wpointer-arith -Wcast-qual -Winline -Werror )
else( CMAKE_COMPILER_IS_GNUCC )
    #   non-gcc (intended for clang)
    add_definitions( -ggdb -fsigned-char -Wall -W -Wshadow -Wstrict-prototypes -Wpointer-arith -Wcast-qual -Winline -Werror )
endif( CMAKE_COMPILER_IS_GNUCC )


#   distribution configuration
set(CMAKE_C_FLAGS_DISTRIBUTION "-O3")
set(CMAKE_CXX_FLAGS_DISTRIBUTION "-O3")

А вот мой CMakeLists.txt уровня src:

#   make sure we have libdb
find_package( BerkeleyDB REQUIRED )
include_directories( ${libdb_INCLUDE_DIRS} )
target_link_libraries( rpdb ${libdb_LIBRARIES} )

#   define variable specifying included source files - all .c files below this directory
file( GLOB rpdb_src "**/*.c" )

#   define shared library with sources
add_library( rpdb SHARED ${rpdb_src} )

Выход (частичный):

...
[100%] Building C object bin/CMakeFiles/rpdb.dir/RPDB_TransactionController/RPDB_TransactionController.c.o
Linking C shared library librpdb.dylib
Undefined symbols:
  "_RPDB_ReplicationVerbositySettingsController_displayMessageProcessingInformation", referenced from:
      _RPDB_SettingsController_internal_setVerbosity in RPDB_SettingsController.c.o
...

Все символы do фактически существуют. Кажется, что результат возникает для символов в объектных файлах, отличных от того, который он просматривает в данный момент.

Вывод из "cmake ../" (из install, каталог верхнего уровня):

=> cmake ..
-- Found BerkeleyDB: /usr/local/lib/libdb.dylib
-- Configuring done
-- Generating done
-- Build files have been written to: /Users/ahaig/Projects/RPDB/RPDB_C/install

Любая помощь высоко ценится.

Ответы [ 3 ]

2 голосов
/ 10 января 2011

Вместо GLOB, попробуйте GLOB_RECURSE ( CMake 2.8.3 docs, команда файла ), которую вы можете использовать так: file ( GLOB_RECURSE rpdb_src "*.c" )

Пример:

function (add_test_files)
    set ( src_files "" )

    ####################################################
    # Find all C/C++ files recursively from current dir
    ####################################################
    foreach ( ext IN ITEMS "cpp" "cxx" "cc" "c" )
        file ( GLOB_RECURSE _files "*.${ext}" )
        set ( src_files ${src_files} ${_files} )
    endforeach ()

    message ( STATUS "Found: ${src_files}" )

    add_executable ( test ${src_files} )
endfunction ()

add_test_files ()
0 голосов
/ 22 июля 2010

Моя проблема сводилась к проблеме с включением файла. Я включал файлы через glob, используя ** / *. C, который, очевидно, рассматривался как * / *. C. Возможно, я неправильно понимаю паттерны глобуса - я использовал их лишь минимально, в противном случае в глобальном разборе файлов в Ruby.

В любом случае, вот решение, которое я придумал:

#   function processes each sub-directory and then adds each source file in directory
#   each function should cascade back upward in setting variables so that the bottom directory
#   adds its source first, and then the level above it adds its source and passes both up, and so on...
function( recursively_include_source which_directory )

    #   get list of source from this directory
    file( GLOB this_directory_src "${which_directory}/*.c" )

    #   get list of all files for this directory
    file( GLOB this_directory_all_files "${which_directory}/*" )

    if( this_directory_all_files AND this_directory_src )

        #   remove source from list of files to get list of directories
        list( REMOVE_ITEM this_directory_all_files ${this_directory_src} )
        set( this_directory_directories ${this_directory_all_files} )

        #   for each sub-directory, call self with sub-directory as arg
        foreach( this_sub_directory ${this_directory_directories} )
            recursively_include_source( ${this_sub_directory} )
        endforeach( this_sub_directory ${this_directory_directories} )

    endif( this_directory_all_files AND this_directory_src )

    #   add source files to ${rpdb_src} in PARENT_SCOPE
    set( rpdb_src ${rpdb_src} ${this_directory_src} PARENT_SCOPE )

endfunction( recursively_include_source which_directory )

Сюда входят все файлы .c внутри и ниже текущего каталога.

Я вызываю функцию так:

recursively_include_source( ${CMAKE_CURRENT_SOURCE_DIR} )

Итак, окончательный src-dir CMakeLists.txt выглядит так:

#   make sure we have libdb
find_package( BerkeleyDB REQUIRED )
include_directories( ${DB_INCLUDE_DIRS} )
set(LIBS ${LIBS} ${DB_LIBRARIES})

recursively_include_source( ${CMAKE_CURRENT_SOURCE_DIR} )

#   define shared library with sources
add_library( rpdb SHARED ${rpdb_src} )
target_link_libraries( rpdb ${LIBS} )

И все, кажется, работает.

0 голосов
/ 22 июля 2010

make VERBOSE = 1

Также посмотрите на CMakeCache.txt

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...