【问题标题】:Cmake error undefined reference to `pthread_create'Cmake错误未定义对`pthread_create'的引用
【发布时间】:2020-09-21 02:15:07
【问题描述】:

我对 cmake FindThreads 进行了测试。这是我的源代码 test.cpp 和 CMakeLists.txt:

#include <pthread.h>                                                                                                                                                                                                                          
void* test_func(void* data)                                                                                                                                                                                                                   
{                                                                                                                                                                                                                                             
  return data;                                                                                                                                                                                                                                
}                                                                                                                                                                                                                                             
                                                                                                                                                                                                                                              
int main(void)                                                                                                                                                                                                                                
{                                                                                                                                                                                                                                             
  pthread_t thread;                                                                                                                                                                                                                           
  pthread_create(&thread, NULL, test_func, NULL);                                                                                                                                                                                             
  pthread_detach(thread);                                                                                                                                                                                                                     
  pthread_cancel(thread);                                                                                                                                                                                                                     
  pthread_join(thread, NULL);                                                                                                                                                                                                                 
  pthread_atfork(NULL, NULL, NULL);                                                                                                                                                                                                           
  pthread_exit(NULL);                                                                                                                                                                                                                         
  return 0;                                                                                                                                                                                                                                   
}     
cmake_minimum_required(VERSION 3.5)                                                                                                                                                                                                           
                                                                                                                                                                                                                                              
project(test C CXX)                                                                                                                                                                                                                           
                                                                                                                                                                                                                                              
set(CMAKE_THREAD_PREFER_PTHREAD ON)                                                                                                                                                                                                           
set(THREADS_PREFER_PTHREAD_FLAG ON)                                                                                                                                                                                                           
find_package(Threads REQUIRED)                                                                                                                                                                                                                
add_executable(test test.cpp)                                                                                                                                                                                                                 
if(TARGET Threads::Threads)                                                                                                                                                                                                                   
  target_link_libraries(test PRIVATE Threads::Threads)                                                                                                                                                                                        
endif()

当我跑步时:

cmake .

我得到了输出:

-- Looking for pthread.h
-- Looking for pthread.h - found
-- Performing Test CMAKE_HAVE_LIBC_PTHREAD
-- Performing Test CMAKE_HAVE_LIBC_PTHREAD - Failed
-- Check if compiler accepts -pthread
-- Check if compiler accepts -pthread - yes
-- Found Threads: TRUE  

然后我检查 CMakeError.txt,发现:

gmake[1]: Entering directory '/home/hye/tmp/cmake-error/CMakeFiles/CMakeTmp'                                                                                                                                                                  
Building C object CMakeFiles/cmTC_55ab6.dir/src.c.o                                                                                                                                                                                           
/usr/bin/clang   -DCMAKE_HAVE_LIBC_PTHREAD   -o CMakeFiles/cmTC_55ab6.dir/src.c.o   -c /home/hye/tmp/cmake-error/CMakeFiles/CMakeTmp/src.c                                                                                                    
Linking C executable cmTC_55ab6                                                                                                                                                                                                               
/usr/bin/cmake -E cmake_link_script CMakeFiles/cmTC_55ab6.dir/link.txt --verbose=1                                                                                                                                                            
/usr/bin/clang  -DCMAKE_HAVE_LIBC_PTHREAD    CMakeFiles/cmTC_55ab6.dir/src.c.o  -o cmTC_55ab6                                                                                                                                                 
/usr/bin/ld: CMakeFiles/cmTC_55ab6.dir/src.c.o: in function `main':                                                                                                                                                                           
src.c:(.text+0x35): undefined reference to `pthread_create'                                                                                                                                                                                   
/usr/bin/ld: src.c:(.text+0x41): undefined reference to `pthread_detach'                                                                                                                                                                      
/usr/bin/ld: src.c:(.text+0x4d): undefined reference to `pthread_cancel'                                                                                                                                                                      
/usr/bin/ld: src.c:(.text+0x5f): undefined reference to `pthread_join'                                                                                                                                                                        
clang-9: error: linker command failed with exit code 1 (use -v to see invocation)                                                                                                                                                             
gmake[1]: *** [CMakeFiles/cmTC_55ab6.dir/build.make:107: cmTC_55ab6] Error 1                                                                                                                                                                  
gmake[1]: Leaving directory '/home/hye/tmp/cmake-error/CMakeFiles/CMakeTmp'                                                                                                                                                                   
gmake: *** [Makefile:141: cmTC_55ab6/fast] Error 2         

我的问题是为什么执行测试 CMAKE_HAVE_LIBC_PTHREAD - 失败了,既然它失败了,那就做了 真的找到Threads,我完全糊涂了。感谢您的回复!

【问题讨论】:

  • 你的 CMake 文件中的 src.c 在哪里?在您的 CMake 文件中,make 输出中提到的这个 cmTC_55ab6 目标在哪里?输出似乎与您的 CMake 代码不匹配...
  • @squareskittles 感谢您的回复,这些文件是临时文件,它们是cmake find_packge生成的,find_package生成的错误信息(Threads REQUIRED)
  • 基本上,我复制 FindThreads.cmake 中的 C 测试代码来做这个测试。我的cmake版本是3.17.4,系统Fedora 31

标签: c++ linux cmake


【解决方案1】:

有一点理由检查 CMakeError.txt,直到 CMake 报告编译器不工作或 CMake 报告不可用的功能(通过探针编译/链接检测到),但您期望该功能可用。

在您的情况下,您已成功配置 CMake(查看 CMake 输出中的最后几行),并且您已成功检测到与线程相关的库(见下文)。没有理由担心,也没有理由调查CMakeError.txt

真的找到线程了吗?

是的,主题已找到。例如,CMake 明确说明

-- Found Threads: TRUE  

其他推断方法,已找到线程:

  1. 您将REQUIRED 关键字与find_package(Threads) 一起使用。如果找不到线程,CMake 将报告错误并终止配置。

  2. 您可以在find_package(Threads) 调用之后检查Threads_FOUND 变量。 (使用 REQUIRED 关键字,此检查是多余的)。

  3. 您可以在find_package(Threads) 调用之后检查Threads::Threads 目标。 (使用 REQUIRED 关键字,此检查是多余的)。

【讨论】:

  • 感谢您的回答。你给了我更多关于cmake的细节,你和@fdk1342对我帮助很大。非常感谢
【解决方案2】:

FindThreads.cmake 会尽力确定编译器是否支持 pthreads 作为库、编译时开关或链接时开关等。

您看到的失败是pthreads 库是否存在。它没有。相反,您应该使用-pthreads 编译文件,这是您的编译器确实接受的编译时开关。这与clang 文档一致,该文档显示-pthreads 是编译器选项,而不是链接器选项。 https://clang.llvm.org/docs/ClangCommandLineReference.html#compilation-flags

那么,它找到线程了吗?不完全是,没有什么可找到的。它是否确定了如何使用 pthreads?是的。

在使用test.cpp 构建目标test 时没有显示任何错误。当pthreads 未作为单独的库实现时,您只发布了人们预期的错误。

【讨论】:

  • 感谢您的回答,所以您的意思是,在编译时它失败了,但在链接时它成功了,而且 -pthread 是编译时,所以我应该添加一个编译标志,实际上有使用 test.cpp 构建目标测试时没有任何错误。这就是为什么我很困惑,它在 cmake 构建时确实有错误。
  • 我尝试添加一个编译标志,它有效,错误消失了!你让我知道 Clang 的标志与我以前从未想过的 gcc 不同。非常感谢您
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-01-03
  • 2013-06-20
相关资源
最近更新 更多