设置线程 /proc/PID/cmdline?

5
在Linux/NPTL下,线程被创建为某种进程。我可以看到我的一些进程有一个奇怪的cmdline:
cat /proc/5590/cmdline 
hald-addon-storage: polling /dev/scd0 (every 2 sec)

你有没有想过如何为进程的每个线程做到这一点?这对于调试非常有帮助。
3个回答

6

如果你想以一种可移植的方式实现这一点,也就是说,它将在多个Unix变体上工作,那么可用的选项非常有限。

你需要做的是,你的调用进程必须使用argv [0]参数调用exec函数,该参数指向你希望在进程输出中看到的名称,而文件名则指向实际的可执行文件。

你可以通过使用以下命令从shell尝试此行为:

exec -a "This is my cute name" bash

这将用一个名为"This is my cute name"的新进程替换当前的bash进程。

如果想在C语言中实现此功能,可以查看sendmail或其他已广泛移植的软件的源代码,并找到需要跨操作系统支持的所有变体。

一些操作系统具有setproctitle(3)API,另一些则允许您覆盖argv[0]的内容并显示结果。


1
PostgreSQL的实现似乎特别稳健:https://github.com/postgres/postgres/blob/71fc49dfe1d99bd83cd99c2e7a39f93e07d19310/src/backend/utils/misc/ps_status.c - nunks

5

argv 指向可写字符串。只需向其写入内容即可:

#include <string.h>
#include <unistd.h>

int
main(int argc, char** argv)
{
    strcpy(argv[0], "Hello, world!");
    sleep(10);
    return 0;
}

相当丑陋,但我想我会使用它。 - elmarco
这可能是一个缓冲区溢出。特别是如果你的新字符串比原始字符串长。你最好在堆上分配一个新字符串,并将其赋值给argv[0]。 - Evan Teran
1
不幸的是,将值分配给argv [0]并没有什么作用。那确实是我的首选。 - C. K. Young
1
是的,它绝对是缓冲区溢出。更严重的方法(例如util-linux中的setproctitle())实际上会在覆盖环境之前将其迁移到安全位置。 - C. K. Young

0

啊.. 这段代码不是很好,诀窍在于重复使用环境(这里是 argv_buffer)指针:

memset (argv_buffer[0] + len, 0, argv_size - len);
argv_buffer[1] = NULL;

有更好的想法吗?

这适用于不同的线程吗?


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接