IBM文档说:The thread_create kernel service can be called from the process environment only. This service cannot be called directly from a kernel extension
同时IBM的文档又说:Kernel extensions use the thread_create and kthread_start services to create and initialize kernel-only threads. For more information about threads, see Understanding Kernel Threads
第一次看很困惑,尼马到底能不能用?后来我仔细琢磨了一下(当然也可能第一眼看时脑子一时短路了),其实两种说法不矛盾,就是能用,但不能直接用。不能直接用的意思是,不能在extension所在的process里直接用(返回ENOSUP类似的错误),这是因为extension所在的process实际上是extension loader process,这是个user space domain进程,而thread_create必须在kernel process里才能被调用,因此需要在extension所在的进程中通过creatp重新创建一个kernel process,然后其实它的入口函数就是我们需要的kernel thread,通过thread_self()就能获得这个initial thread的ID了。当然如果在这个新的kernel process里再调用thread_create就可以了。
但是IBM文档还是落后源码的,即便是号称针对7.1 aix的在线文档:
%2Fcom.ibm.aix.kerneltechref%2Fdoc%2Fktechrf1%2Finitp.htm
其对initp的原型说明也是很老的,或者就根本没有更新过:
int initp
(pid, func, init_parms,
parms_length, name)
pid_t ;
void ( ) (int
flag, void* init_parms, int parms_length );
void * ;
int ;
char * ;
事实上在6.1 aix头文件/usr/include/sys/proc.h中,关于initp的原型已经是:
extern int initp(pid_t, int (*)(), char *, int32long64_t, char[]);
到底哪个是对的呢? 从实际结果来看,头文件的定义是不对的(头文件有问题此处并非唯一的案例)。在头文件定义的原型中, func函数已经没有参数列表了,这涉及进程间数据共享的问题,在内核空间里只能用全局变量了,否则的话是得不到预期的结果,比如直接使用IBM文档提供的源码,结果肯定是错误的了。事实上它应该是int (*func)(int, void*, int), 调用initp的参数栈的建立是对的,如果你实现了int (*func)(void *, int),那么必然是有问题了。这种事情很操蛋,有时候得花很多的时间精力在这种无谓的小问题上。IBM这方面很不勘。
阅读(3542) | 评论(0) | 转发(0) |