kprof_func.d
选自Brendan Gregg
的DTrace书中的第三章:“System View
”(我对输出格式做了一点修改):
#!/usr/sbin/dtrace -s
#pragma D option quiet
profile-997hz
/arg0 && curthread->t_pri != -1/
{
@[func(caller), func(arg0)] = count();
}
tick-10sec
{
trunc(@,20);
printf("%-40s %-40s %-8s\n","CALLER","FUNCTION","COUNT");
printa("%-40a %-40a %-@8d\n",@);
exit(0);
}
(1)curthread->t_pri != -1
是Solaris
系统上判断是不是idle
线程(参考这里);
(2)func
函数的输入参数是程序计数器(Program Counter
),返回的是程序计数器所在的函数名字;
(3)%a
可以把输入是指针或者uintptr_t
类型的参数,转化为函数名字加上偏移量。
上述脚本在我的OmniOS
上输出如下(func()
函数的返回值已经是函数名字了,所以%a
就不起作用了,也就是无法得到偏移量了):
# ./kprof_func.d
CALLER FUNCTION COUNT
genunix`timeout genunix`timeout_generic 1
acpica`AcpiHwReadPort acpica`AcpiOsReadPort 2
apix`apix_dispatch_pending_autovect unix`ddi_get32 2
unix`todpc_get unix`todpc_rtcget 4
genunix`callout_list_expire unix`ddi_get32 4
ahci`ahci_fatal_error_recovery_handler unix`ddi_get32 10
ahci`ahci_tran_start unix`ddi_io_put32 15
ahci`ahci_put_port_into_notrunning_state unix`drv_usecwait 16
如果修改profile-997hz
探针的执行语句为:
profile-997hz
/arg0 && curthread->t_pri != -1/
{
@[caller, arg0] = count();
}
则输出变为(可以看到,多了偏移量):
# ./kprof_func.d
CALLER FUNCTION COUNT
apix`apix_dispatch_pending_hardint+0x34 apix`apix_dispatch_pending_autovect+0xbe 1
ehci`ehci_handle_root_hub_status_change+0xd7 unix`ddi_get32+0x14 1
unix`disp+0x192 unix`disp_getwork+0x209 1
genunix`cv_signal+0xa7 genunix`sleepq_wakeone_chan+0x36 1
unix`todpc_get+0x19 unix`todpc_rtcget+0xb1 3
genunix`callout_list_expire+0x91 unix`ddi_get32+0x14 3
unix`todpc_get+0x19 unix`todpc_rtcget+0xd6 4
genunix`callout_list_expire+0x91 unix`ddi_io_put32+0x17 5
genunix`gethrtime+0x10 unix`tsc_read+0x3 9
apix`apix_dispatch_pending_autovect+0xe6 unix`ddi_get32+0x14 10
ahci`ahci_put_port_into_notrunning_state+0xde unix`drv_usecwait+0x9a 10