kernel学习之sys_fork,sys_vfork,sys_clone和kernel_thread
发布时间:2016-10-08 19:13:47 所属栏目:Unix 来源:网络整理
导读:用户空间进程创建接口:fork,vfork,clone函数,这里只做简单说明。 fork:使用该系统调用时,子进程复制父进程的全部资源。由于要复制父进程进程描述符给子进
内核线程是一种特殊的进程,它只能运行在内核态,不能访问用户空间的内容。内核线程除了各自的栈和硬件上下文外,共享所用资源。内核利用内核线程来完成一些后台工作如kswapd,ksoftirqd。内核线程有kernel_thread创建。 在linux2.6.xxx/arch/x86/include/asm/processor.h /* * create a kernel thread without removing itfrom tasklists */ extern intkernel_thread(int (*fn)(void *), void *arg, unsigned long flags); 在linux2.6.xxx/arch/arm/include/asm/processor.h /* * Create a new kernel thread */ extern intkernel_thread(int (*fn)(void *), void *arg, unsigned long flags); 参数说明: fn:新创建的内核线程要执行的函数。 arg:fn的参数。 flags:和do_fork中的clone_flags作用相似。 kernel_thread函数分析: 在linux2.6.xxx/arch/x86/kernel/process.c /* * Create a kernel thread */ intkernel_thread(int (*fn)(void *), void *arg, unsigned long flags) { struct pt_regs regs;//保存进程的硬件上下文 memset(®s, 0, sizeof(regs)); regs.si = (unsigned long) fn; regs.di = (unsigned long) arg; #ifdefCONFIG_X86_32 regs.ds = __USER_DS; regs.es = __USER_DS; regs.fs = __KERNEL_PERCPU; regs.gs = __KERNEL_STACK_CANARY; #else regs.ss = __KERNEL_DS; #endif regs.orig_ax = -1; regs.ip = (unsigned long)kernel_thread_helper; regs.cs = __KERNEL_CS | get_kernel_rpl(); regs.flags = X86_EFLAGS_IF | 0x2; /* Ok, create the new process.. */ return do_fork(flags | CLONE_VM |CLONE_UNTRACED, 0, ®s, 0, NULL, NULL); } 分析: 从这段代码可知,内核线程的创建最终还是调用了do_fork。 arm架构的kernel_thread实现: /* * Create a kernel thread. */ pid_tkernel_thread(int (*fn)(void *), void *arg, unsigned long flags) { struct pt_regs regs; memset(®s, 0, sizeof(regs)); regs.ARM_r4 = (unsigned long)arg; regs.ARM_r5 = (unsigned long)fn; regs.ARM_r6 = (unsignedlong)kernel_thread_exit; regs.ARM_r7 = SVC_MODE | PSR_ENDSTATE |PSR_ISETSTATE; regs.ARM_pc = (unsignedlong)kernel_thread_helper; regs.ARM_cpsr = regs.ARM_r7 | PSR_I_BIT; return do_fork(flags|CLONE_VM|CLONE_UNTRACED,0, ®s, 0, NULL, NULL); } /* * Shuffle the argument into the correctregister before calling the * thread function. r4 is the thread argument, r5 is the pointerto * the thread function, and r6 points to theexit function. */ extern voidkernel_thread_helper(void); asm( ".pushsection .textn" " .alignn" " .type kernel_thread_helper,#functionn" "kernel_thread_helper:n" #ifdefCONFIG_TRACE_IRQFLAGS " bl trace_hardirqs_onn" #endif " msr cpsr_c,r7n" " mov r0,r4n" " mov lr,r6n" " mov pc,r5n" " .size kernel_thread_helper,. - kernel_thread_helpern" " .popsection"); 出处:http://blog.csdn.net/muge0913/article/details/7479379 (编辑:佛山站长网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |