一直对nginx显示master和worker进程名字的方式很好奇,自己当时也是看了代码的,可是并没有理解关键点,直到看了http://gcoder.blogbus.com/logs/131966702.html这篇文章,再仔细研读nginx代码后,才发现更改进程名称的关键点是:
(1)修改argv[1]=NULL;
(2)修改argv[0]=title;
需要注意的是,argv[0]指向的内存不一定容得下title。在linux下,argv和environ指向的内存时连续的,我们可以malloc能容得下environ的内存,把environ的内容复制到malloc出的内存里,让title占用environ现在的内存。
ngx_int_t
ngx_init_setproctitle(ngx_log_t *log)
{
u_char *p;
size_t size;
ngx_uint_t i;
size = 0;
//environ的总空间
for (i = 0; environ[i]; i++) {
size += ngx_strlen(environ[i]) + 1;
}
p = ngx_alloc(size, log);
if (p == NULL) {
return NGX_ERROR;
}
ngx_os_argv_last = ngx_os_argv[0]; //存放最后一个argv
for (i = 0; ngx_os_argv[i]; i++) {
if (ngx_os_argv_last == ngx_os_argv[i]) {
ngx_os_argv_last = ngx_os_argv[i] + ngx_strlen(ngx_os_argv[i]) + 1; //到environ部分了
}
}
for (i = 0; environ[i]; i++) {
if (ngx_os_argv_last == environ[i]) {
size = ngx_strlen(environ[i]) + 1;
ngx_os_argv_last = environ[i] + size;
ngx_cpystrn(p, (u_char *) environ[i], size);
environ[i] = (char *) p;
p += size;
}
} //将environ的数据copy到malloc的空间里
ngx_os_argv_last--;
return NGX_OK;
}
void
ngx_setproctitle(char *title)
{
u_char *p;
ngx_os_argv[1] = NULL; //ngx_os_argv = (char **) argv;
//设置proc的title
p = ngx_cpystrn((u_char *) ngx_os_argv[0], (u_char *) "nginx: ",
ngx_os_argv_last - ngx_os_argv[0]);
p = ngx_cpystrn(p, (u_char *) title, ngx_os_argv_last - (char *) p);
。。。
//设置结尾标识’\0’
if (ngx_os_argv_last - (char *) p) {
ngx_memset(p, NGX_SETPROCTITLE_PAD, ngx_os_argv_last - (char *) p);
}
ngx_log_debug1(NGX_LOG_DEBUG_CORE, ngx_cycle->log, 0,
"setproctitle: \"%s\"", ngx_os_argv[0]);
}
#include
#include
char **os_argv = NULL; //全局变量
char *cpystrn(char *dst, char *src, size_t n)
{
if (n == 0) {
return dst;
}
while (--n) {
*dst = *src;
if (*dst == '\0') {
return dst;
}
dst++;
src++;
}
*dst = '\0';
return dst;
}
//设置进程的title
int setproctitle(char *title)
{
char *p;
os_argv[1] = NULL; //可有可无,经测试不影响结果
p = cpystrn((char *)os_argv[0], "chenjie: ", 100);
p = cpystrn(p, title, 100);
memset(p, '\0', 100);
return 0;
}
int main(int argc, char **argv)
{
os_argv = (char **) argv;
setproctitle("test process");
sleep(10);
}
# gcc -o chenjie proc.c
#./chenjie