strace常用参数详解
作者:尹正杰
版权声明:原创作品,谢绝转载!否则将追究法律责任。
strace命令大家应该比我熟悉吧,如果你不知道,呵呵,会可能跟我一样被人说:“我怀疑你是假运维”,不过没关系,linux内置命令且不说有1000多个,光外置命令也不少啊,比如有搭建过lvs,haproxy,keepalived这些外置的软件的时候都会有一些自带的命令被加入到系统环境变量中,所以大家有那么几百个命令记不住也没有关系的,好了,让我们步入正题,开始跟我一起学习一下这个命令吧。
strace常用来跟踪进程执行时的系统调用和所接收的信号。 在Linux世界,进程不能直接访问硬件设备,当进程需要访问硬件设备(比如读取磁盘文件,接收网络数据等等)时,必须由用户态模式切换至内核态模式,通 过系统调用访问硬件设备。strace可以跟踪到一个进程产生的系统调用,包括参数,返回值,执行消耗的时间。
1.输出参数含义
1 [root@yinzhengjie ~]# strace cat /dev/null 2 execve("/bin/cat", ["cat", "/dev/null"], [/* 25 vars */]) = 0 3 brk(0) = 0x25fd000 4 mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f6f78843000 5 access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory) 6 open("/etc/ld.so.cache", O_RDONLY) = 3 7 fstat(3, {st_mode=S_IFREG|0644, st_size=61467, ...}) = 0 8 mmap(NULL, 61467, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7f6f78833000 9 close(3) = 010 open("/lib64/libc.so.6", O_RDONLY) = 311 read(3, "\177ELF\2\1\1\3\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0p\356\241\261>\0\0\0"..., 832) = 83212 fstat(3, {st_mode=S_IFREG|0755, st_size=1926760, ...}) = 013 mmap(0x3eb1a00000, 3750152, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x3eb1a0000014 mprotect(0x3eb1b8a000, 2097152, PROT_NONE) = 015 mmap(0x3eb1d8a000, 20480, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x18a000) = 0x3eb1d8a00016 mmap(0x3eb1d8f000, 18696, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x3eb1d8f00017 close(3) = 018 mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f6f7883200019 mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f6f7883100020 mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f6f7883000021 arch_prctl(ARCH_SET_FS, 0x7f6f78831700) = 022 mprotect(0x3eb1d8a000, 16384, PROT_READ) = 023 mprotect(0x3eb141f000, 4096, PROT_READ) = 024 munmap(0x7f6f78833000, 61467) = 025 brk(0) = 0x25fd00026 brk(0x261e000) = 0x261e00027 open("/usr/lib/locale/locale-archive", O_RDONLY) = 328 fstat(3, {st_mode=S_IFREG|0644, st_size=99158576, ...}) = 029 mmap(NULL, 99158576, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7f6f7299f00030 close(3) = 031 fstat(1, {st_mode=S_IFCHR|0620, st_rdev=makedev(136, 2), ...}) = 032 open("/dev/null", O_RDONLY) = 333 fstat(3, {st_mode=S_IFCHR|0666, st_rdev=makedev(1, 3), ...}) = 034 read(3, "", 32768) = 035 close(3) = 036 close(1) = 037 close(2) = 038 exit_group(0) = ?39 [root@yinzhengjie ~]# 40 每一行都是一条系统调用,等号左边是系统调用的函数名及其参数,右边是该调用的返回值。41 strace 显示这些调用的参数并返回符号形式的值。strace 从内核接收信息,而且不需要以任何特殊的方式来构建内核。
2.通用的完整用法
1 [root@yinzhengjie ~]# lsof -i :80 2 COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME 3 clock-app 3294 root 22u IPv4 422720 0t0 TCP bogon:50925->61.213.149.41:http (CLOSE_WAIT) 4 httpd 3441 root 4u IPv6 38717 0t0 TCP *:http (LISTEN) 5 httpd 3625 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN) 6 httpd 3627 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN) 7 httpd 3630 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN) 8 httpd 3631 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN) 9 httpd 3663 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)10 httpd 3689 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)11 httpd 3699 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)12 httpd 3708 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)13 httpd 3709 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)14 httpd 3712 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)15 httpd 3719 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)16 httpd 3720 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)17 httpd 3722 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)18 httpd 3723 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)19 httpd 3725 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)20 httpd 3729 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)21 httpd 3733 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)22 httpd 3735 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)23 httpd 3736 apache 4u IPv6 38717 0t0 TCP *:http (LISTEN)24 25 [root@yinzhengjie ~]# strace -o output.txt -T -tt -e trace=all26 27 '''28 备注:29 上面的含义是 跟踪3441进程的所有系统调用(-e trace=all),并统计系统调用的花费时间,以及开始时间(并以可视化的时分秒格式显示),最后将记录结果存在output.txt文件里面。30 '''31 32 [root@yinzhengjie ~]# cat output.txt 33 06:06:12.033922 select(0, NULL, NULL, NULL, {0, 131348}) = 0 (Timeout) <0.131923>34 06:06:12.166174 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000013>35 06:06:12.166221 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.002046>36 06:06:13.168611 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000036>37 06:06:13.168752 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.001221>38 06:06:14.170389 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000038>39 06:06:14.170531 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.001175>40 06:06:15.172108 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000037>41 06:06:15.172248 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.002016>42 06:06:16.174678 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000036>43 06:06:16.174817 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.001788>44 06:06:17.176918 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000025>45 06:06:17.177015 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.001661>46 06:06:18.179080 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000036>47 06:06:18.179220 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.001740>48 06:06:19.181439 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000035>49 06:06:19.181579 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.001782>50 06:06:20.183723 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000026>51 06:06:20.183820 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.001200>52 06:06:21.185475 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000034>53 06:06:21.185611 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.001225>54 06:06:22.188209 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000049>55 06:06:22.188716 select(0, NULL, NULL, NULL, {1, 0}) = 0 (Timeout) <1.002025>56 06:06:23.191170 wait4(-1, 0x7fffc1cfad5c, WNOHANG|WSTOPPED, NULL) = 0 <0.000037>57 06:06:23.191315 select(0, NULL, NULL, NULL, {1, 0}58 [root@yinzhengjie ~]#
3.strace参数说明
1 -c 统计每一系统调用的所执行的时间,次数和出错的次数等. 2 -d 输出strace关于标准错误的调试信息. 3 -f 跟踪由fork调用所产生的子进程. 4 -ff 如果提供-o filename,则所有进程的跟踪结果输出到相应的filename.pid中,pid是各进程的进程号. 5 -F 尝试跟踪vfork调用.在-f时,vfork不被跟踪. 6 -h 输出简要的帮助信息. 7 -i 输出系统调用的入口指针. 8 -q 禁止输出关于脱离的消息. 9 -r 打印出相对时间关于,,每一个系统调用. 10 -t 在输出中的每一行前加上时间信息. 11 -tt 在输出中的每一行前加上时间信息,微秒级. 12 -ttt 微秒级输出,以秒了表示时间. 13 -T 显示每一调用所耗的时间. 14 -v 输出所有的系统调用.一些调用关于环境变量,状态,输入输出等调用由于使用频繁,默认不输出. 15 -V 输出strace的版本信息. 16 -x 以十六进制形式输出非标准字符串 17 -xx 所有字符串以十六进制形式输出. 18 -a column 19 设置返回值的输出位置.默认 为40. 20 -e expr 21 指定一个表达式,用来控制如何跟踪.格式如下: 22 [qualifier=][!]value1[,value2]... 23 qualifier只能是 trace,abbrev,verbose,raw,signal,read,write其中之一.value是用来限定的符号或数字.默认的 qualifier是 trace.感叹号是否定符号.例如: 24 -eopen等价于 -e trace=open,表示只跟踪open调用.而-etrace!=open表示跟踪除了open以外的其他调用.有两个特殊的符号 all 和 none. 25 注意有些shell使用!来执行历史记录里的命令,所以要使用\\. 26 -e trace=set 27 只跟踪指定的系统 调用.例如:-e trace=open,close,rean,write表示只跟踪这四个系统调用.默认的为set=all. 28 -e trace=file 29 只跟踪有关文件操作的系统调用. 30 -e trace=process 31 只跟踪有关进程控制的系统调用. 32 -e trace=network 33 跟踪与网络有关的所有系统调用. 34 -e strace=signal 35 跟踪所有与系统信号有关的 系统调用 36 -e trace=ipc 37 跟踪所有与进程通讯有关的系统调用 38 -e abbrev=set 39 设定 strace输出的系统调用的结果集.-v 等与 abbrev=none.默认为abbrev=all. 40 -e raw=set 41 将指 定的系统调用的参数以十六进制显示. 42 -e signal=set 43 指定跟踪的系统信号.默认为all.如 signal=!SIGIO(或者signal=!io),表示不跟踪SIGIO信号. 44 -e read=set 45 输出从指定文件中读出 的数据.例如: 46 -e read=3,5 47 -e write=set 48 输出写入到指定文件中的数据. 49 -o filename 50 将strace的输出写入文件filename 51 -p pid 52 跟踪指定的进程pid. 53 -s strsize 54 指定输出的字符串的最大长度.默认为32.文件名一直全部输出. 55 -u username 56 以username 的UID和GID执行被跟踪的命令
4.查看帮助
[root@yinzhengjie ~]# man strace
更多请参考一:http://www.cnblogs.com/ggjucheng/archive/2012/01/08/2316692.html
二:http://blog.csdn.net/kevinx_xu/article/details/26977477