Skip to content

Commit 76867d4

Browse files
committed
ensure stack pointer isn't touched until we set it
1 parent 3863ca7 commit 76867d4

File tree

2 files changed

+28
-13
lines changed

2 files changed

+28
-13
lines changed

arch/wasm/kernel/process.c

Lines changed: 19 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -15,38 +15,43 @@ struct task_struct *__switch_to(struct task_struct *from,
1515
struct thread_info *to_info = task_thread_info(to);
1616
int cpu, other_cpu;
1717

18-
cpu = atomic_xchg_release(&from_info->running_cpu, -1);
18+
cpu = atomic_xchg(&from_info->running_cpu, -1);
1919
BUG_ON(cpu < 0); // current process must be scheduled to a cpu
2020

2121
// give the current cpu to the new worker
22-
other_cpu = atomic_xchg_acquire(&to_info->running_cpu, cpu);
22+
other_cpu = atomic_xchg(&to_info->running_cpu, cpu);
2323
BUG_ON(other_cpu >= 0); // new process should not have had a cpu
2424

25+
pr_info("broken task: %p",
26+
&((struct task_struct *)0x00174000)->se.group_node);
27+
2528
// wake the other worker:
26-
// pr_info("wake cpu=%i task=%p\n", cpu, to);
29+
pr_info("wake cpu=%i task=%p\n", cpu, to);
2730
// memory.atomic.notify returns how many waiters were notified
2831
// 0 is fine, because it means the worker isn't running yet
2932
// 1 is great, because it means someone is waiting for this number
3033
// 2+ means there's an issue, because I asked for only 1
3134
BUG_ON(__builtin_wasm_memory_atomic_notify(
32-
&to_info->running_cpu.counter, 1) > 1);
35+
&to_info->running_cpu.counter,
36+
/* how many to wake up (at most): */ 1) > 1);
3337

34-
// pr_info("waiting cpu=%i task=%p in switch\n", cpu, from);
38+
pr_info("waiting cpu=%i task=%p in switch\n",
39+
atomic_read(&from_info->running_cpu), from);
3540

3641
// sleep this worker:
3742
/* memory.atomic.wait32 returns:
3843
* 0 -> the thread blocked and was woken
3944
= we slept and were woken
4045
* 1 -> the value at the pointer didn't match the passed value
41-
= somebody gave us their cpu straight await
46+
= somebody gave us their cpu straight away
4247
* 2 -> the thread blocked but timed out
4348
= not possible because we pass an infinite timeout
4449
*/
4550
__builtin_wasm_memory_atomic_wait32(&from_info->running_cpu.counter,
4651
/* block if the value is: */ -1,
4752
/* timeout: */ -1);
4853

49-
// pr_info("woke up cpu=%i task=%p in switch\n", cpu, from);
54+
pr_info("woke up cpu=%i task=%p in switch\n", cpu, from);
5055

5156
BUG_ON(cpu < 0); // we should be given a new cpu
5257

@@ -73,14 +78,12 @@ int copy_thread(struct task_struct *p, const struct kernel_clone_args *args)
7378
return 0;
7479
}
7580

76-
__attribute__((export_name("task"))) void _start_task(struct task_struct *task)
81+
static void noinline_for_stack start_task_inner(struct task_struct *task)
7782
{
7883
struct thread_info *info = task_thread_info(task);
7984
struct pt_regs *regs = task_pt_regs(task);
8085
int cpu;
8186

82-
set_stack_pointer(task_pt_regs(task) - 1);
83-
8487
early_printk(" waiting cpu=%i task=%p in entry\n",
8588
atomic_read(&info->running_cpu), task);
8689

@@ -106,3 +109,9 @@ __attribute__((export_name("task"))) void _start_task(struct task_struct *task)
106109
// call into userspace?
107110
panic("can't call userspace\n");
108111
}
112+
113+
__attribute__((export_name("task"))) void _start_task(struct task_struct *task)
114+
{
115+
set_stack_pointer(task_pt_regs(task) - 1);
116+
start_task_inner(task);
117+
}

arch/wasm/kernel/smp.c

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,10 +11,9 @@ int __cpu_up(unsigned int cpu, struct task_struct *idle)
1111
wasm_bringup_secondary(cpu, idle);
1212
}
1313

14-
__attribute__((export_name("secondary"))) void
15-
_start_secondary(int cpu, struct task_struct *idle)
14+
static void noinline_for_stack start_secondary_inner(int cpu,
15+
struct task_struct *idle)
1616
{
17-
set_stack_pointer(task_pt_regs(idle) - 1);
1817
smp_tls_init(cpu, true);
1918

2019
BUG_ON(cpu_online(cpu));
@@ -31,6 +30,13 @@ _start_secondary(int cpu, struct task_struct *idle)
3130
cpu_startup_entry(CPUHP_AP_ONLINE_IDLE);
3231
}
3332

33+
__attribute__((export_name("secondary"))) void
34+
_start_secondary(int cpu, struct task_struct *idle)
35+
{
36+
set_stack_pointer(task_pt_regs(idle) - 1);
37+
start_secondary_inner(cpu, idle);
38+
}
39+
3440
static struct {
3541
unsigned long bits ____cacheline_aligned;
3642
} ipi_data[NR_CPUS] __cacheline_aligned = { 0 };

0 commit comments

Comments
 (0)