FreeBSD 用户空间 DTrace 和用户空间的转储函数参数
Posted
技术标签:
【中文标题】FreeBSD 用户空间 DTrace 和用户空间的转储函数参数【英文标题】:FreeBSD User Space DTrace and dumping function arguments for user space 【发布时间】:2013-08-16 23:58:10 【问题描述】:我们可以像函数一样为用户空间函数转储函数参数吗 在内核空间?如果我们可以 FBT 提供者转储用户空间函数的参数 执行 dtrace -l -f -v?
我在 DTrace 中使用“top”实用程序,(“top”实用程序同时具有 目标文件中内置的 CTF 和 Dwarf 调试部分)
我正在尝试检查“top”调用的 get_system_info 函数,我 确认它存在待探测
root% dtrace -l | grep get_system_info
55154 pid8488 top get_system_info entry
但我无法将参数转储到函数中......
root% dtrace -l -f get_system_info -v
ID PROVIDER MODULE FUNCTION NAME
55154 pid8488 top get_system_info entry
Probe Description Attributes
Identifier Names: Private
Data Semantics: Private
Dependency Class: Unknown
Argument Attributes
Identifier Names: Private
Data Semantics: Private
Dependency Class: Unknown
Argument Types
None
使用简单的脚本进行测试,
pid8488::get_system_info:entry
this->info = (struct system_info *)copyin(args[0], sizeof(struct system_info));
...如果我使用 args[0] 表示法,它会显示以下内容,
dtrace: failed to compile script top_d.d: line 17: index 0 is out of
range for pid8488::get_system_info:entry args[ ]
如果我用 arg0 替换,它会编译但值不是 一定是理智的。 示例 struct system_info 的 ncpus 成员显示垃圾值。
完整的脚本是
pid8488::get_system_info:entry
this->info = (struct system_info *)copyin(arg0, sizeof(struct system_info));
printf("last pid [%d] \n", this->info->last_pid);
pid8488::get_process_info:entry
this->info = (struct system_info *)copyin(arg0, sizeof(struct system_info));
printf("ncpus [%d] \n", this->info->ncpus);
运行这个
55154 get_system_info:entry last pid [8513]
55155 get_process_info:entry ncpus [134558720]
应该显示cpu数量?脚本有什么问题吗?
【问题讨论】:
【参考方案1】:我曾尝试在 9.1 和 9.2-RC2 上对此进行调查,但我无法让 DTrace 在任何一个上正常工作,因此我的 cmets 基于 Solaris 版本,应该大致相同。
fbt 提供程序检测内核功能。它的用户空间等价物是 pid 提供者。
pid 提供者当然可以公开函数参数,但除非 FreeBSD 的 DTrace 支持用户级 CTF,否则它们的类型将不可用。这可能就是为什么您发现输入的 args[n]
不可用,而您只能使用整数 argn
。
我猜测函数 get_system_info()
填充了 struct system_info
。如果是这种情况,那么您必须在从函数返回的 after 结构中复制。
此外,如果 dtrace(1) 找不到该结构的定义,那么您必须自己提供它,包括它或适当的头文件(并使用 -C
标志)。
这是一个(未经测试的)示例:
最后,在评估数据类型(例如指针大小)时,dtrace(1) 将
默认为运行内核的数据模型。如果您正在运行 64 位内核,但您正在检测 32 位进程,则使用“-32
”标志,以便 dtrace(1) 对其看到的各种类型使用适当的大小。
【讨论】:
以上是关于FreeBSD 用户空间 DTrace 和用户空间的转储函数参数的主要内容,如果未能解决你的问题,请参考以下文章