task切换-__entry_task percpu 静态变量作用

 

1、__entry_task为内核静态定义的percpu变量,在进程切换时,会将next进程的进程描述符保存到该变量中。

arch/arm64/kernel/process.c

 497
 498/*
 499 * We store our current task in sp_el0, which is clobbered by userspace. Keep a
 500 * shadow copy so that we can restore this upon entry from userspace.
 501 *
 502 * This is *only* for exception entry from EL0, and is not valid until we
 503 * __switch_to() a user task.
 504 */
 505DEFINE_PER_CPU(struct task_struct *, __entry_task);
 506
 507static void entry_task_switch(struct task_struct *next)
 508{
 509        __this_cpu_write(__entry_task, next);
 510}
 511

调用顺序

 544/*
 545 * Thread switching.
 546 */
 547__notrace_funcgraph struct task_struct *__switch_to(struct task_struct *prev,
 548                                struct task_struct *next)
 549{
 550        struct task_struct *last;

 556        entry_task_switch(next);

 

2、kernel_entry 从用户态切换到内核态是,从__entry_task 获取 当前的 task 指针,放到  sp_el0 中。

 175
 176        .macro  kernel_entry, el, regsize = 64

 199        ldr_this_cpu    tsk, __entry_task, x20
 200        msr     sp_el0, tsk

 

 所以,内核中,sp_el0 指向 current task 。 内核中 current 宏,通过读取当前的 sp_el0 来得到  current task

v5.10/arch/arm64/include/asm/current.h

  11/*
  12 * We don't use read_sysreg() as we want the compiler to cache the value where
  13 * possible.
  14 */
  15static __always_inline struct task_struct *get_current(void)
  16{
  17        unsigned long sp_el0;
  18
  19        asm ("mrs %0, sp_el0" : "=r" (sp_el0));
  20
  21        return (struct task_struct *)sp_el0;
  22}
  23
  24#define current get_current()

 

posted @ 2022-03-24 14:58  张志伟122  阅读(177)  评论(0编辑  收藏  举报