gcc -lpthread和gcc -pthread的区别
在编译下面的代码时,碰到了undefined reference to `pthread_atfork'的错误:
代码来自《POSIX多线程程序设计》
-
/*
-
* atfork.c
-
* Demonstrate the use of "fork handlers" to protect data invariants
across a fork.
-
*/
-
#include <sys/types.h>
-
#include <pthread.h>
-
#include <sys/wait.h>
-
#include "errors.h"
-
-
pid_t self_pid; /* pid of current process */
-
pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
-
-
void fork_prepare(void)
-
{
- pthread_mutex_lock(&mutex);
-
}
-
-
void fork_parent(void)
-
{
- pthread_mutex_unlock(&mutex);
-
}
-
-
void fork_child(void)
-
{
- self_pid = getpid();
-
pthread_mutex_unlock(&mutex);
-
}
-
-
void *thread_routine(void *arg)
-
{
-
pid_t child_pid;
-
-
child_pid = fork();
-
if(child_pid == (pid_t)-1)
-
errno_abort("Fork");
-
-
pthread_mutex_lock(&mutex);
-
pthread_mutex_unlock(&mutex);
-
printf("After fork: %d (%d)\n", child_pid, self_pid);
-
if(child_pid != 0){ // parent
process
-
if ((pid_t)-1 == waitpid(child_pid, (int*)0, 0))
-
errno_abort("Wait for child");
-
}
-
return NULL;
-
}
-
-
int main(int argc, char *argv[])
-
{
-
pthread_t fork_thread;
-
int atfork_flag = 1;
-
-
if(argc > 1)
-
atfork_flag = atoi (argv[1]);
-
if(atfork_flag){
-
pthread_atfork(fork_prepare, fork_parent, fork_child);
-
}
-
self_pid = getpid();
-
pthread_mutex_lock(&mutex);
-
-
pthread_create(&fork_thread, NULL, thread_routine, NULL);
-
sleep(5);
-
pthread_mutex_unlock (&mutex);
-
pthread_join(fork_thread, NULL);
-
-
return 0;
- }
编译运行结果:
-
digdeep@ubuntu:~/pthread/learnthread$
gcc -Wall -lpthread -o atfork atfork.c /tmp/cckSrItT.o: In function `main':
-
atfork.c:(.text+0x195): undefined
reference to `pthread_atfork'
-
collect2: ld returned 1 exit status
-
digdeep@ubuntu:~/pthread/learnthread$
gcc -Wall -pthread -o atfork atfork.c
-
digdeep@ubuntu:~/pthread/learnthread$ ./atfork
-
After fork: 2637 (2635)
-
After fork: 0 (2637)
- digdeep@ubuntu:~/pthread/learnthread$
于是想搞清楚 -lpthread和-pthread的区别:
-
digdeep@ubuntu:~$ gcc
--version
-
gcc (Ubuntu/Linaro 4.5.2-8ubuntu4) 4.5.2
-
Copyright (C) 2010 Free Software Foundation, Inc.
-
This is free software; see the source for copying conditions. There is NO
-
warranty; not even for MERCHANTABILITY or FITNESS FOR A
PARTICULAR PURPOSE.
-
-
digdeep@ubuntu:~$ man
gcc | grep pthread
-
-mvxworks -G num -pthread
-
-mno-unaligned-doubles -mv8plus -mno-v8plus -mvis -mno-vis -threads -pthreads
-
-pthread
-
implies -pthread, and thus is only
supported on targets that have support for
-
-pthread.
-
implies -pthread, and thus is only
supported on targets that have support for
-
-pthread.
-
option and the -pthread option are
incompatible.
-
-pthread
-
Adds support for multithreading with the pthreads library. This option sets
flags for
-
-pthreads
-
-pthread
-
This is a synonym for -pthreads.
-
digdeep@ubuntu:~$
-
digdeep@ubuntu:~$ man
gcc | grep lpthread
-
digdeep@ubuntu:~$
- digdeep@ubuntu:~$
从上面的输出可以看到,目前gcc 4.5.2中已经没有了关于 -lpthread的介绍了。所以以后的多线程编译应该用
-pthread,而不是-lpthread。
仔细的阅读man gcc中的关于pthread的介绍:
-
-pthread
-
Adds support for multithreading with the pthreads library. This option sets
flags for
-
both the preprocessor and linker.
-
-
-pthreads
-
Add support for multithreading using the POSIX threads library. This option sets
-
flags for both the preprocessor and linker. This option does
not affect the thread
-
safety of object code produced by the compiler or that of libraries supplied with it.
-
-
-pthread
- This is a synonym for -pthreads.
从上面的 man gcc中的详细说明可以看出:
1)-pthread和-pthreads的含义是相同的。
2)-pthread或者-pthreads的编译选项是用于在编译时增加多线程的支持。该选项同时对“预处理器”和“链接器”产
生作用。
3)-pthread或者-pthreads的编译选项,即不影响编译器产生的目标代码的线程安全性,也不影响对提供的支持
多线程的函数库libraries(的选择).(gcc
会自动链接系统当前版本推荐的 thread lib 以及对应的 thread
safe 的 c func。 http://kasicass.blog.163.com/blog/static/395619200992410313759/)
但是,下面的输出却又说明,我们不能使用 -pthreads:
- digdeep@ubuntu:~/pthread/learnthread$ gcc -Wall -pthreads -o atfork atfork.c
-
gcc: unrecognized option '-pthreads'
-
/tmp/ccZZmWbD.o: In function `main':
-
atfork.c:(.text+0x195): undefined
reference to `pthread_atfork'
-
atfork.c:(.text+0x1cf): undefined
reference to `pthread_create'
-
atfork.c:(.text+0x1fb): undefined
reference to `pthread_join'
- collect2: ld returned 1 exit status
所以:一句话,我们现在应该使用 -pthread 而不是 -lpthread。
另:下面的英文文档详细说明了相关的情况。
该文档的摘要:
下面是摘录自命令 gcc -dumpspecs的输出:
-
*cpp:
-
%{posix:-D_POSIX_SOURCE} %{pthread:-D_REENTRANT}
-
-
*lib:
- %{pthread:-lpthread} %{shared:-lc} %{!shared:%{mieee-fp:-lieee} %{profile:-lc_p}%{!profile:-lc}}
%{pthread:-lpthread} 与上面的说明有点矛盾!!有点糊涂了。NND!