arm64: armv8_deprecated: protect prev_mode or it would cause undef_lock deadlock

When do 'echo 1 > /proc/sys/abi/swp' on two cpus at the same time, we can see:

	call_undef_hook() at traps.c:442
	do_undefinstr() at traps.c:504
	el0_undef() at entry-common.c:605
	el0t_64_sync_handler() at entry-common.c:689
	el0t_64_sync() at entry.S:585

That is because write swp 1 at the same time, add the swp_hooks to the undef_hook
list twice, swp_hooks list node's next becomes itself. When list_for_each_entry of
the undef_hook, cpu loops forever here.

Change-Id: Ice60dbc633020220e7218a554e9d0e4c7dacceb4
Signed-off-by: Huibin Hong <huibin.hong@rock-chips.com>
This commit is contained in:
Huibin Hong
2025-04-30 14:41:57 +08:00
committed by Tao Huang
parent e54469c723
commit 3f38eabc5b

View File

@@ -209,9 +209,10 @@ static int emulation_proc_handler(struct ctl_table *table, int write,
{
int ret = 0;
struct insn_emulation *insn = container_of(table->data, struct insn_emulation, current_mode);
enum insn_emulation_mode prev_mode = insn->current_mode;
enum insn_emulation_mode prev_mode;
mutex_lock(&insn_emulation_mutex);
prev_mode = insn->current_mode;
ret = proc_dointvec_minmax(table, write, buffer, lenp, ppos);
if (ret || !write || prev_mode == insn->current_mode)