全局static变量,可以使用gdb的“info variables”找出,且可以列出变量所在文件(有符号库的情况下)。但是函数局部的static变量就比较麻烦了。
先看一个例子:
#include <sys/syscall.h> #include <stdio.h> void fun() { static int ls_pid1 = 0; // 初始化为0 int pid1 = syscall(SYS_gettid); ls_pid1 = pid1; printf("%d\n", ls_pid1); } int main() { int pid = syscall(SYS_gettid); static int ls_pid = 1; // 初始化非0 ls_pid = pid; printf("%d\n", ls_pid); fun(); return 0; }
以上代码有两个局部static变量:ls_pid1和ls_pid1。
使用-O0和-g编译:
[yz@test-4 ~]$ gcc ls_demo.c -lpthread -O0 -g -o ls_demo
使用gdb,可以找出static变量:
[yz@test-4 ~]$ gdb ./ls_demo (peda)$ info variables All defined variables: Non-debugging symbols: …… 0x000000000060103c ls_pid 0x0000000000601040 __TMC_END__ 0x0000000000601040 __bss_start 0x0000000000601040 _edata 0x0000000000601040 completed 0x0000000000601044 ls_pid1 0x0000000000601048 _end
本方法需要注意:
使用-O0和-g编译:
[yz@test-4 ~]$ gcc ls_demo.c -lpthread -O0 -g -o ls_demo
使用objdump,可以找出部分static变量:
[yz@test-4 ~]$ objdump ./ls_demo -t | grep ".\data" 0000000000400680 l d .rodata 0000000000000000 .rodata 0000000000601038 l d .data 0000000000000000 .data 000000000060103c l O .data 0000000000000004 ls_pid.2430 0000000000601038 w .data 0000000000000000 data_start 0000000000601040 g .data 0000000000000000 _edata 0000000000601038 g .data 0000000000000000 __data_start 0000000000400688 g O .rodata 0000000000000000 .hidden __dso_handle 0000000000400680 g O .rodata 0000000000000004 _IO_stdin_used 0000000000601040 g O .data 0000000000000000 .hidden __TMC_END__
本方法需要注意:
该方法也有好处: