7个Debug linux程序的Strace 列子

Strace是一个能帮助你解决问题的debugging工具

Strace监控指定程序系统调用和信号,在你没有源代码又想dubug程序的执行时是会用到的。Strace会以程序的开始到结束来顺序执行的

你可以从这个7个Strace 例子开始起步了解Strace

 1.跟踪可执行程序的执行

你可以使用strace命令的跟踪任何可执行程序,接下来的例子展示linux ls命令的的strace输出

[tony@oc4443573018 python]$ strace ls
execve("/bin/ls", ["ls"], [/* 52 vars */]) = 0
brk(0)                                  = 0x2172000
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f5c88a90000
access("/etc/ld.so.preload", R_OK)      = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY)      = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=99825, ...}) = 0
mmap(NULL, 99825, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7f5c88a77000
close(3)                                = 0
open("/lib64/libselinux.so.1", O_RDONLY) = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0\320X\340\366=\0\0\0"..., 832) = 832
fstat(3, {st_mode=S_IFREG|0755, st_size=124624, ...}) = 0
mmap(0x3df6e00000, 2221912, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x3df6e00000
mprotect(0x3df6e1d000, 2093056, PROT_NONE) = 0
mmap(0x3df701c000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x1c000) = 0x3df701c000
mmap(0x3df701e000, 1880, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x3df701e000
close(3)                                = 0
open("/lib64/librt.so.1", O_RDONLY)     = 3

.....
.....

2.使用option -e参数来追踪执行指定程序的系统调用

默认情况下,strace展示指定可执行程序的所有系统调用,使用strace -e选项只输出指定系统调用

[tony@oc4443573018 Videos]$ strace -e open ls
open("/etc/ld.so.cache", O_RDONLY)      = 3
open("/lib64/libselinux.so.1", O_RDONLY) = 3
open("/lib64/librt.so.1", O_RDONLY)     = 3
open("/lib64/libcap.so.2", O_RDONLY)    = 3
open("/lib64/libacl.so.1", O_RDONLY)    = 3
open("/lib64/libc.so.6", O_RDONLY)      = 3
open("/lib64/libdl.so.2", O_RDONLY)     = 3
open("/lib64/libpthread.so.0", O_RDONLY) = 3
open("/lib64/libattr.so.1", O_RDONLY)   = 3
open("/usr/lib/locale/locale-archive", O_RDONLY) = 3
open(".", O_RDONLY|O_NONBLOCK|O_DIRECTORY|O_CLOEXEC) = 3
Webcam
[tony@oc4443573018 Videos]$ 

The above output displays only the open system call of the ls command. At the end of the strace output, it also displays the output of the ls command.

上面只输出指定ls命令的系统调用,在strace输出的最后面同时也输出了ls命令的结果

If you want to trace multiple system calls use the “-e trace=” option. The following example displays both open and read system calls.

如果想trace多个系统调用,可以使用"-e strace="选项,下面展示了open和read命令的系统调用

[tony@oc4443573018 ~]$ strace -e trace=open,read ls /home
open("/etc/ld.so.cache", O_RDONLY)      = 3
open("/lib64/libselinux.so.1", O_RDONLY) = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0\320X\340\366=\0\0\0"..., 832) = 832
open("/lib64/librt.so.1", O_RDONLY)     = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0@! \366=\0\0\0"..., 832) = 832
open("/lib64/libcap.so.2", O_RDONLY)    = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0000\23`\371=\0\0\0"..., 832) = 832
open("/lib64/libacl.so.1", O_RDONLY)    = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0\200\36`\2>\0\0\0"..., 832) = 832
open("/lib64/libc.so.6", O_RDONLY)      = 3
read(3, "\177ELF\2\1\1\3\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0p\356!\365=\0\0\0"..., 832) = 832
open("/lib64/libdl.so.2", O_RDONLY)     = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0\340\r\340\365=\0\0\0"..., 832) = 832
open("/lib64/libpthread.so.0", O_RDONLY) = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0\340]\240\365=\0\0\0"..., 832) = 832
open("/lib64/libattr.so.1", O_RDONLY)   = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0\200\23 \6>\0\0\0"..., 832) = 832
open("/usr/lib/locale/locale-archive", O_RDONLY) = 3
open("/home", O_RDONLY|O_NONBLOCK|O_DIRECTORY|O_CLOEXEC) = 3
interpel  tonyb
[tony@oc4443573018 ~]$ 
View Code

3.使用参数-o 保存strace结果

The following examples stores the strace output to output.txt file.

下面的列子展示strace命令输出的output.txt文件

[tonyboob@oc4443573018 ~]$ strace -o output.txt ls
A                    output.txt
a_b.py                    packages
a.py                    pexpect_test.py
B                    Pictures
bianli.py                Public
C                    putty.log
chefdk-0.10.0-1.el6.x86_64.rpm        python
CROSS_TEAM                Recycle Bin
derby.log                redis
Desktop                    redis_daemon.sh
Documents                rpmbuild
Downloads                SametimeRooms
。。。。。。。。
。。。。。。。。。。
[tony@oc4443573018 ~]$ cat output.txt 
execve("/bin/ls", ["ls"], [/* 53 vars */]) = 0
brk(0)                                  = 0x1dd9000
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f75f6d17000
access("/etc/ld.so.preload", R_OK)      = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY)      = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=99825, ...}) = 0
mmap(NULL, 99825, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7f75f6cfe000
close(3)                                = 0
open("/lib64/libselinux.so.1", O_RDONLY) = 3
View Code

4.使用-p 参数来strace一个运行中进程

You could execute strace on a program that is already running using the process id. First, identify the PID of a program using ps command.

可以使用已运行程序PID来strace一个程序,但首先你的使用ps命令来确定PID

For example, if you want to do strace on the firefox program that is currently running, identify the PID of the firefox program.

比如,你想strace运行中的Firefox,先确定Firefox的PID

[tony@oc4443573018 ~]$ ps -C firefox
  PID TTY          TIME CMD
 6970 ?        06:02:51 firefox
[tony@oc4443573018 ~]$ 
View Code

使用-p选项来展示指定PID输出

[tony@oc4443573018 ~]$ strace -p 6970 -o firefox_strace.txt
Process 6970 attached - interrupt to quit

^CProcess 6970 detached
[tony@oc4443573018 ~]$ tail -f firefox_strace.txt 
read(28, "\372", 1)   
View Code

firefox_trace中将记录firefox进程的trace记录,可以使用tail 命令的动态的观察firefox的输出,不过这是需要在另一个terminal来tail -f的

Strace会显示下面的错误,当你的user id不匹配给定的进程的UID

strace -p 1725 -o output.txt
attach: ptrace(PTRACE_ATTACH, ...): Operation not permitted
Could not attach to process.  If your uid matches the uid of the target
process, check the setting of /proc/sys/kernel/yama/ptrace_scope, or try
again as the root user.  For more details, see /etc/sysctl.d/10-ptrace.conf
View Code

5.使用-t参数为每行trace输出打印时间戳

tony@oc4443573018 ~]$ strace -t -e open ls /home
10:43:25 open("/etc/ld.so.cache", O_RDONLY) = 3
10:43:25 open("/lib64/libselinux.so.1", O_RDONLY) = 3
10:43:25 open("/lib64/librt.so.1", O_RDONLY) = 3
10:43:25 open("/lib64/libcap.so.2", O_RDONLY) = 3
10:43:25 open("/lib64/libacl.so.1", O_RDONLY) = 3
10:43:25 open("/lib64/libc.so.6", O_RDONLY) = 3
10:43:25 open("/lib64/libdl.so.2", O_RDONLY) = 3
10:43:25 open("/lib64/libpthread.so.0", O_RDONLY) = 3
10:43:25 open("/lib64/libattr.so.1", O_RDONLY) = 3
10:43:25 open("/usr/lib/locale/locale-archive", O_RDONLY) = 3
10:43:25 open("/home", O_RDONLY|O_NONBLOCK|O_DIRECTORY|O_CLOEXEC) = 3
interpel  tony
View Code

6.使用-r参数打印相关系统调用次数

[tony@oc4443573018 ~]$ strace -r ls
     0.000000 execve("/bin/ls", ["ls"], [/* 53 vars */]) = 0
     0.000653 brk(0)                    = 0x1a0b000
     0.000141 mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fdecabb8000
     0.000163 access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory)
     0.000423 open("/etc/ld.so.cache", O_RDONLY) = 3
     0.000895 fstat(3, {st_mode=S_IFREG|0644, st_size=99825, ...}) = 0
     0.000136 mmap(NULL, 99825, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7fdecab9f000
     0.000090 close(3)                  = 0
     0.000111 open("/lib64/libselinux.so.1", O_RDONLY) = 3
     0.000816 read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0\320X\340\366=\0\0\0"..., 832) = 832
     0.000089 fstat(3, {st_mode=S_IFREG|0755, st_size=124624, ...}) = 0
     0.000115 mmap(0x3df6e00000, 2221912, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x3df6e00000

。。。。。。。。。。。。。。。。。
。。。。。。。。。。。。。。。。。
View Code

7.使用-c参数来生成系统调用的统计报告

使用-c选项会提供有用的执行追踪统计报告,下面输出中calls列表明特定的系统被执行了多少次

[tony@oc4443573018 python]$ strace -c ls /home
interpel  tony
% time     seconds  usecs/call     calls    errors syscall
------ ----------- ----------- --------- --------- ----------------
 98.97    0.000671          61        11           open
  1.03    0.000007           0        27           mmap
  0.00    0.000000           0         8           read
  0.00    0.000000           0         1           write
  0.00    0.000000           0        13           close
  0.00    0.000000           0         2           stat
  0.00    0.000000           0        11           fstat
  0.00    0.000000           0        16           mprotect
  0.00    0.000000           0         2           munmap
  0.00    0.000000           0         3           brk
  0.00    0.000000           0         2           rt_sigaction
  0.00    0.000000           0         1           rt_sigprocmask
  0.00    0.000000           0         2           ioctl
  0.00    0.000000           0         1         1 access
  0.00    0.000000           0         1           execve
  0.00    0.000000           0         1           fcntl
  0.00    0.000000           0         2           getdents
  0.00    0.000000           0         1           getrlimit
  0.00    0.000000           0         2           statfs
View Code

 

posted @ 2016-02-23 10:53  myland  阅读(376)  评论(0编辑  收藏  举报