...
// int __pthread_clone(void* (*fn)(void*), void* child_stack, int flags, void* arg);
...
END(__pthread_clone)
2.3 在Kernel空间
首先处理SWI指令
$kernel_root/arch/arm/kernel/entry-common.S
/*=============================================================================
* SWI handler
*-----------------------------------------------------------------------------
*/
.align 5
ENTRY(vector_swi)
sub sp, sp, #S_FRAME_SIZE
stmia sp, {r0 - r12} @ Calling r0 - r12
ARM( add r8, sp, #S_PC )
ARM( stmdb r8, {sp, lr}^ ) @ Calling sp, lr
THUMB( mov r8, sp )
THUMB( store_user_sp_lr r8, r10, S_SP ) @ calling sp, lr
mrs r8, spsr @ called from non-FIQ mode, so ok.
str lr, [sp, #S_PC] @ Save calling PC
str r8, [sp, #S_PSR] @ Save CPSR
str r0, [sp, #S_OLD_R0] @ Save OLD_R0
zero_fp
...
...
adr tbl, sys_call_table @ load syscall table pointer //再根据系统调用号,查询sys_call_table这个表,找到相应的系统调用
ENTRY(sys_call_table)
#include "calls.S"
sys_call_table即calls.S
=>calls.S
...
/* 120 */ CALL(sys_clone)//120号对应的就是sys_clone
...
=>entry-common.S
ldrcc pc, [tbl, scno, lsl #2] @ call sys_* routine//这里执行系统调用。
那么在哪实现sys_clone的呢?不同的系统的调用,在不同的目录里,比较open就是在fs/下面,clone就就在kernel下面。使用宏SYSCALL_DEFINE来配合使用。
=>kernel/fork.c
#ifdef __ARCH_WANT_SYS_CLONE
#ifdef CONFIG_CLONE_BACKWARDS
SYSCALL_DEFINE5(clone, unsigned long, clone_flags, unsigned long, newsp,
int __user *, parent_tidptr,
int, tls_val,
int __user *, child_tidptr)
#elif defined(CONFIG_CLONE_BACKWARDS2)
SYSCALL_DEFINE5(clone, unsigned long, newsp, unsigned long, clone_flags,
int __user *, parent_tidptr,
int __user *, child_tidptr,
int, tls_val)
#elif defined(CONFIG_CLONE_BACKWARDS3)
SYSCALL_DEFINE6(clone, unsigned long, clone_flags, unsigned long, newsp,
int, stack_size,
int __user *, parent_tidptr,
int __user *, child_tidptr,
int, tls_val)
#else
SYSCALL_DEFINE5(clone, unsigned long, clone_flags, unsigned long, newsp,
int __user *, parent_tidptr,
int __user *, child_tidptr,
int, tls_val)
#endif
{
return do_fork(clone_flags, newsp, 0, parent_tidptr, child_tidptr);
}
#endif
=>
最终是调用forkc.c/do_fork()的.
整个流程是这样的,通了流程,有需要有精力就可以深入细节啦。