diff options
author | Ian Moffett <ian@osmora.org> | 2025-07-17 18:42:29 -0400 |
---|---|---|
committer | Ian Moffett <ian@osmora.org> | 2025-07-17 18:42:29 -0400 |
commit | de7ab64e895c37cadc4d4032c24013d28edb248b (patch) | |
tree | 3e5c2c236fad9fbfdf097961c0be6c7551f69893 /sys | |
parent | 37bc0faac60d9e6ee11d09e57e360091c425922c (diff) |
kernel/amd64: mp: Pin one idle thread to each coremain
Each core on the CPU gets one idle thread so that it is always up to
something. To ensure these threads are not bouncing wildly between cores
and are always ready for their respective processor to take when they
have no threads to grab. We must call proc_pin() on each for every
processor.
Signed-off-by: Ian Moffett <ian@osmora.org>
Diffstat (limited to 'sys')
-rw-r--r-- | sys/arch/amd64/amd64/mp.c | 17 |
1 files changed, 11 insertions, 6 deletions
diff --git a/sys/arch/amd64/amd64/mp.c b/sys/arch/amd64/amd64/mp.c index 21881b2..20f550f 100644 --- a/sys/arch/amd64/amd64/mp.c +++ b/sys/arch/amd64/amd64/mp.c @@ -56,6 +56,7 @@ static void ap_trampoline(struct limine_smp_info *si) { struct cpu_info *ci; + struct proc *idle; ci = dynalloc(sizeof(*ci)); __assert(ci != NULL); @@ -64,6 +65,11 @@ ap_trampoline(struct limine_smp_info *si) cpu_startup(ci); spinlock_acquire(&ci_list_lock); ci_list[ncpu_up] = ci; + + ci->id = ncpu_up; + spawn(&g_proc0, sched_enter, NULL, 0, &idle); + proc_pin(idle, ci->id); + spinlock_release(&ci_list_lock); atomic_inc_int(&ncpu_up); @@ -110,6 +116,7 @@ mp_bootstrap_aps(struct cpu_info *ci) { struct limine_smp_response *resp = g_smp_req.response; struct limine_smp_info **cpus; + struct proc *idle; size_t cpu_init_counter; uint32_t ncpu; @@ -121,6 +128,10 @@ mp_bootstrap_aps(struct cpu_info *ci) cpu_init_counter = ncpu - 1; ci_list[0] = ci; + /* Pin an idle thread to the BSP */ + spawn(&g_proc0, sched_enter, NULL, 0, &idle); + proc_pin(idle, 0); + if (resp->cpu_count == 1) { pr_trace("CPU has 1 core, no APs to bootstrap...\n"); return; @@ -136,12 +147,6 @@ mp_bootstrap_aps(struct cpu_info *ci) cpus[i]->goto_address = ap_trampoline; } - /* Start up idle threads */ - pr_trace("kicking %d idle threads...\n", ncpu); - for (uint32_t i = 0; i < ncpu; ++i) { - spawn(&g_proc0, sched_enter, NULL, 0, NULL); - } - /* Wait for all cores to be ready */ while ((ncpu_up - 1) < cpu_init_counter); } |