Como excluo um único arquivo de um padrão cmake `file (GLOB…)`?

86

Meu CMakeLists.txtcontém esta linha:

file(GLOB lib_srcs Half/half.cpp Iex/*.cpp IlmThread/*.cpp Imath/*.cpp IlmImf/*.cpp)

e a IlmImfpasta contém b44ExpLogTable.cpp, que preciso excluir da compilação.

Como conseguir isso?

Berak
fonte

Respostas:

100

Você pode usar a listfunção para manipular a lista, por exemplo:

list(REMOVE_ITEM <list> <value> [<value> ...])

No seu caso, talvez algo assim funcione:

list(REMOVE_ITEM lib_srcs "IlmImf/b44ExpLogTable.cpp")
Lindydancer
fonte
1
além de lib_srcs em vez de lib_src e IlmImf em vez de IlmThread, isso resolveu o problema! muito obrigado!
berak
20
Nota: Ao remover o item da lista, certifique-se de que o valor que você está procurando corresponde exatamente ao que está na lista. Eu estava tendo problemas ao misturar $ {CMAKE_SOURCE_DIR} /src/file_to_remove.cpp com $ {CMAKE_CURRENT_SOURCE_DIR} /../ file_to_remove.cpp. Ele aponta para o mesmo local, mas não é a mesma string. mensagem ("$ {VARIABLE_NAME}") pode ajudá-lo a depurar esse conteúdo.
hbobenicio
Isso não ajuda se você estiver usando CONFIGURE_DEPENDSe precisar excluir um arquivo produzido pela construção. Um filtro na lista após a filechamada ainda aciona uma reconstrução que, no meu caso, estou tentando evitar.
simon.watts
É muito melhor usarlist(FILTER
hukeping de
2
A solução acima não funciona para mim com camke versão 3.10.2 Mas a solução abaixo: list(FILTER <list> <INCLUDE|EXCLUDE> REGEX <regular_expression>) funciona bem para mim.
MH Yip
42

FILTRO é outra opção que pode ser mais conveniente em alguns casos:

list(FILTER <list> <INCLUDE|EXCLUDE> REGEX <regular_expression>)

Esta linha exclui todos os itens que terminam com o nome de arquivo necessário:

list(FILTER lib_srcs EXCLUDE REGEX ".*b44ExpLogTable.cpp$")

Aqui está a especificação Regex para cmake:

The following characters have special meaning in regular expressions:

^         Matches at beginning of input
$         Matches at end of input
.         Matches any single character
[ ]       Matches any character(s) inside the brackets
[^ ]      Matches any character(s) not inside the brackets
 -        Inside brackets, specifies an inclusive range between
          characters on either side e.g. [a-f] is [abcdef]
          To match a literal - using brackets, make it the first
          or the last character e.g. [+*/-] matches basic
          mathematical operators.
*         Matches preceding pattern zero or more times
+         Matches preceding pattern one or more times
?         Matches preceding pattern zero or once only
|         Matches a pattern on either side of the |
()        Saves a matched subexpression, which can be referenced
          in the REGEX REPLACE operation. Additionally it is saved
          by all regular expression-related commands, including
          e.g. if( MATCHES ), in the variables CMAKE_MATCH_(0..9).
Eugene
fonte
Pode ser muito mais confiável do que mexer com
caminhos
1
Muito melhor do quelist(REMOVE_ITEM
ceztko 01 de
1
Observe que list(FILTER ...)foi introduzido no cmake v3.6: stackoverflow.com/a/42167646/3476780
yano
Esta é definitivamente uma resposta melhor, embora se você estiver tentando usar isso para excluir um diretório inteiro ou se seu regex estiver bagunçado, você pode excluir mais do que deseja. Por exemplo, tentar excluir .*test/.*pode excluir tudo se o seu projeto estiver dentro de uma árvore de diretórios onde um dos diretórios pai é denominado algo como mytest.
AnthonyD973
1

tente isto: CMakeLists.txt

install(DIRECTORY   ${CMAKE_SOURCE_DIR}/ 
            DESTINATION ${CMAKE_INSTALL_PREFIX}
            COMPONENT   copy-files
            PATTERN     ".git*"   EXCLUDE
            PATTERN     "*.in"    EXCLUDE
            PATTERN     "*/build" EXCLUDE)

add_custom_target(copy-files
            COMMAND ${CMAKE_COMMAND} -D COMPONENT=copy-files
            -P cmake_install.cmake)
$cmake <src_path> -DCMAKE_INSTALL_PREFIX=<install_path>
$cmake --build . --target copy-files
James
fonte