本文共 2842 字,大约阅读时间需要 9 分钟。
使用GDB进行多线程调试,查看互斥变量。
演示源码如下:
#include#include #include #include static void* thread_func(void* args);pthread_mutex_t g_mutex = PTHREAD_MUTEX_INITIALIZER;int sum = 0;#define MAX_NUM 10000int main(int argc, char** argv) { int seq = 0; pthread_t thread_handle; for ( seq = 0; seq < 5; seq++) { int* tmp_seq = (int*)malloc(sizeof(int)); *tmp_seq = seq; pthread_create(&thread_handle, NULL, thread_func, tmp_seq); } while ( 1 ) sleep(20); return 0;}static void* thread_func(void* args) { int thread_seq = *(int*)args; free(args); while ( 1 ) { sleep(thread_seq + 2); pthread_mutex_lock(&g_mutex); if ( sum < MAX_NUM ) sum++; else sum = 0; printf("in thread %d, sum is %d\n", thread_seq, sum); pthread_mutex_unlock(&g_mutex); }}
编译
gcc -o demo -g demo.c -lpthread
运行效果如下:
in thread 0, sum is 1in thread 1, sum is 2in thread 2, sum is 3in thread 0, sum is 4in thread 3, sum is 5in thread 4, sum is 6in thread 1, sum is 7in thread 0, sum is 8in thread 2, sum is 9
使用GDB进行调试
gdb ./demo
设置断点 gdb) br 32
查看运行的线程
gdb) info threads Id Target Id Frame 6 Thread 0xb5c9eb40 (LWP 914) "demo" 0xb7fdd416 in __kernel_vsyscall () 5 Thread 0xb649fb40 (LWP 913) "demo" 0xb7fdd416 in __kernel_vsyscall () 4 Thread 0xb6ca0b40 (LWP 912) "demo" 0xb7fdd416 in __kernel_vsyscall () 3 Thread 0xb74a1b40 (LWP 911) "demo" 0xb7fdd416 in __kernel_vsyscall ()* 2 Thread 0xb7ca2b40 (LWP 910) "demo" thread_func (args=0x804a008) at demo.cpp:32 1 Thread 0xb7ca4700 (LWP 906) "demo" 0xb7fdd416 in __kernel_vsyscall ()
查看当前线程的函数调用堆栈
gdb) bt full
查看哪个线程拥有互斥变量,首先需要知道pthread_mutex_t的具体结构是什么。
gdb) whatis g_mutextype = pthread_mutex_t gdb) set print pretty #让GDB输出效果排版的好看一些 gdb) ptype g_mutextype = union pthread_mutex_t { pthread_mutex_t::__pthread_mutex_s __data; char __size[24]; long __align;}
打印出g_mutex的具体内容:
gdb) p g_mutex$2 = { __data = { __lock = 1, __count = 0, __owner = 910, __kind = 0, __nusers = 1, { __spins = 0, __list = { __next = 0x0 } } }, __size = "\001\000\000\000\000\000\000\000\216\003\000\000\000\000\000\000\001\000\000\000\000\000\000", __align = 1}
各位看官,注意上述输出中,owner表示当前拥有g_mutex的线程。
那么谁是910呢,上面用”info threads"只输出了1,2,3,4,5,6无法对应,ok. 用点top小技巧,
top -H -p 906
906表示demo的进程ID,-H表示打印出所有的线程。
当前拥有g_mutex是910,那么应该是第二号线程,即thread_seq为0的线程。
如果想在程序运行的时候知道当前线程中类似于top输出的pid值,可以通过如下方法。
/*#method 1*/pid_t gettid(void);/***************************************#method 2 using the following system call **************************************/#includepid_t tid = (pid_t) syscall (SYS_gettid);
最后需要提醒的是,当设定断点停下来的时候,其它线程其实还是可以继续运行的。如果只想让当前线程可以运行,其它的全部停下来的话。请用下列的指令。
gdb) set scheduler-locking on
关于这个内容,可以参考链接
转载地址:http://bcntx.baihongyu.com/