我们知道进程ID是操作系统调度的最小单位,有时候根据业务的需要,我们会使用到多线程技术,当创建了多个线程时,也会有一个线程ID,那这个线程ID和进程ID有什么不一样吗?
其中,线程组的线程ID是属于NPTL(Native POSIX Thread Library)线程库的范畴,属该线程库调度的标识;而调度器的进程ID则属于操作系统的最小调度单位.两者具有在本质上截然不同的意义和使用范围,值得注意!我们来看一个实验代码:线程执行函数thread1和thread2都只做一件事情,输出自己的线程组中的线程ID和被调度器调度的进程ID,
#include <stdio.h> #include <stdlib.h> #include <string.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #include <unistd.h> #include <errno.h> #include <sys/ipc.h> #include <sys/shm.h> #include <sys/msg.h> #include <pthread.h> #include <sys/syscall.h> /* syscall(SYS_gettid); */ void *thread1(); void *thread2(); int main(int argc, char *argv[]) { int flag; pthread_t th1,th2; flag=pthread_create(&th1,NULL,thread1,NULL); if(flag != 0) { fprintf(stderr,"创建线程1失败[%s]\n",strerror(errno)); exit(0); } flag=pthread_create(&th2,NULL,thread2,NULL); if(flag != 0) { fprintf(stderr,"创建线程2失败[%s]\n",strerror(errno)); exit(0); } printf("main进程ID是[%d]\n",getpid()); pthread_join(th1,NULL); pthread_join(th2,NULL); return 0; } void *thread1() { int tid = syscall(SYS_gettid); /* 被进程调度器调度的进程ID */ printf("这是线程thread1,线程组的线程ID是[%u], 调度器的进程ID = %d\n",(unsigned int)pthread_self(), tid); /* 让线程不要退出,以便查看在proc下的线程信息 */ pause(); } void *thread2() { int tid = syscall(SYS_gettid); /* 被进程调度器调度的进程ID */ printf("这是线程thread2,线程组的线程ID是[%u], 调度器的进程ID = %d\n",(unsigned int)pthread_self(), tid); /* 让线程不要退出,以便查看在proc下的线程信息 */ pause(); }
运行结果
发现属于NPTL的线程ID的数值非常大(3078654832,3068164976),而属于系统调度器的进程ID则紧跟主进程的进程ID(4180,4181)
在线程没有退出的情况下(使用pause进行模拟),可以使用ls -l /proc/[pid]/task命令查看该进程下的所属线程信息.因为procfs文件系统在task下会给进程的每一个线程都建立一个子目录,目录名称为该线程的被调度的ID.(PS: 使用命令ps -L -p 4179也可以查看)
发现该进程的目录下的确有4180和4181的线程目录.
从本质上来说,属于NPTL范畴的线程ID的类型是pthread_t,而它指向了一个类型为struct pthread的结构体,所以还是一个指针,理解成为一个地址也可以.
而被系统调度的进程ID的类型却是pid_t,它是能被列入到调度队列的.所以,两者还是有很大区别的.
命令ps -L -p 4179的执行结果
./threadid的状态是Sl+,S表示该进程是静止的,l表示是多线程或者克隆线程.
备注:进程或线程的状态列表
D 不可中断 Uninterruptible sleep (usually IO)
R 正在运行,或在队列中的进程
S 处于休眠状态
T 停止或被追踪
Z 僵尸进程
W 进入内存交换(从内核2.6开始无效)
X 死掉的进程
< 高优先级
N 低优先级
L 有些页被锁进内存
s 包含子进程
+ 位于后台的进程组
l 多线程,克隆线程
原文:http://www.cnblogs.com/foggia2004/p/6255163.html