cmake e libpthread

188

Estou correndo RHEL 5.1e usogcc .

Como eu digo cmakepara adicionar -pthreadà compilação e vinculação?

dimba
fonte
1
Você pode escolher uma resposta para isso?
Jared Burrows
1
Cara, você tem que escolher @ Manuel como resposta.
A resposta de @Ehsan thehouse é muito melhor! :-)
Ela782 11/11

Respostas:

208

@Manuel fazia parte do caminho. Você também pode adicionar a opção de compilador, assim:

Se você possui o CMake 3.1.0+, isso se torna ainda mais fácil :

set(THREADS_PREFER_PTHREAD_FLAG ON)
find_package(Threads REQUIRED)
target_link_libraries(my_app PRIVATE Threads::Threads)

Se você estiver usando o CMake 2.8.12+, poderá simplificar isso para:

find_package(Threads REQUIRED)
if(THREADS_HAVE_PTHREAD_ARG)
  target_compile_options(my_app PUBLIC "-pthread")
endif()
if(CMAKE_THREAD_LIBS_INIT)
  target_link_libraries(my_app "${CMAKE_THREAD_LIBS_INIT}")
endif()

As versões mais antigas do CMake podem exigir:

find_package(Threads REQUIRED)
if(THREADS_HAVE_PTHREAD_ARG)
  set_property(TARGET my_app PROPERTY COMPILE_OPTIONS "-pthread")
  set_property(TARGET my_app PROPERTY INTERFACE_COMPILE_OPTIONS "-pthread")
endif()
if(CMAKE_THREAD_LIBS_INIT)
  target_link_libraries(my_app "${CMAKE_THREAD_LIBS_INIT}")
endif()

Se você quiser usar um dos dois primeiros métodos com o CMake 3.1+, será necessário set(THREADS_PREFER_PTHREAD_FLAG ON)também.

a casa
fonte
Parece que, por exemplo, o CMake 3.0.2 não definirá THREADS_HAVE_PTHREAD_ARG se a biblioteca pthread for encontrada ( NOT CMAKE_HAVE_THREADS_LIBRARY), por exemplo, no Ubuntu 15.04 :(
mlt
1
A versão fornecida para o CMake 2.8.12+ não funcionará conforme o esperado, por causa de como o código funciona /usr/share/cmake-2.8/Modules/FindThreads.cmake(por exemplo, veja aqui apt-browse.org/browse/ubuntu/trusty/main/all/cmake-data/… ) basicamente, THREADS_HAVE_PTHREAD_ARGé definido apenas se as outras variações da bandeira não foram encontrados (isto é. -lpthread, -lpthreadou -lthread)
j1elo
Isso fornece o erro "Não é possível especificar as bibliotecas de links para o destino" my_app ", que não é criado por este projeto." - como habilitá-lo universalmente sem precisar fazê-lo individualmente para cada alvo?
Chris Dodd
A primeira ainda é a maneira mais fácil em 2020 / cmake 3.17?
Jay
O que acontece se você não definir o sinalizador THREADS_PREFER_PTHREAD_FLAG, basta encontrar e vincular?
Jay
199

O seguinte deve estar limpo (usando find_package) e funcionar (o módulo de localização é chamado FindThreads):

cmake_minimum_required (VERSION 2.6) 
find_package (Threads)
add_executable (myapp main.cpp ...)
target_link_libraries (myapp ${CMAKE_THREAD_LIBS_INIT})
Manuel
fonte
2
Isso não funciona quando usado em um projeto somente CXX. Alguém conhece uma boa solução alternativa?
Simon
1
@Simon um pouco tarde, mas consulte este: stackoverflow.com/questions/15193785/...
congusbongus
@CongXu Thanks! Bom saber!
Simon
1
Esta solução funciona no Mac OS X, Centos 6 e Solaris 10. #
1015 Bernernn
26

Aqui está a resposta correta:

ADD_EXECUTABLE(your_executable ${source_files})

TARGET_LINK_LIBRARIES( your_executable
pthread
)

equivalente a

-lpthread
Nadir SOUALEM
fonte
Isso é equivalente. "-pthread" doa muito mais - na compilação é -D_REENTRANT, no tempo do link -lpthread. Em algum sistema no mesmo pode ser mais do que isso.
Dimba
2
SET (CMAKE_CXX_FLAGS_DEBUG "... -lpthread") SET (CMAKE_CXX_FLAGS_RELEASE "... -lpthread")
Nadir SOUALEM
21
essa solução funciona assim que você muda do linux para o freebsd ou windows.
7283 Alex
4
Não funciona, "target_link_libraries (your_executable pthread)" é como deve ser escrito.
Overv
6
Esta não é a resposta certa de forma alguma. Mesmo que você não goste da resposta da casa, e considerando que ela foi escrita em 2009, é uma plataforma completamente diferente. Use a resposta da casa - e, se você não gostar, escolha algo target_link_libraries(target "$<$<CXX_COMPILER_ID:GNU>:-pthread>$<$<CXX_COMPILER_ID:Clang>:-pthreads>")que seja pelo menos baseado em metas e que não falhe no Windows e em outras plataformas.
Ela782