Skip to contentSkip to conversation

WARNING on latest master due to DYNAMIC_PREEMPT and cond_resched()

PATCH Applied Steven Rostedt 3 participants 5 messages Feb 25, 2021 – Mar 6, 2021 Static branch/call

lore
Share & tools
lore

Steven Rostedt

author reviewer
#0 lore raw

I got this warning dump on latest master (while fixing the kmem trace event)

 ------------[ cut here ]------------
 unexpected static_call insn opcode 0xe9 at drm_gem_check_release_pagevec+0x2a/0x30 [drm]
 WARNING: CPU: 6 PID: 646 at arch/x86/kernel/static_call.c:77 __static_call_validate+0x68/0x80
 Modules linked in: drm(+) e1000e(+) crct10dif_pclmul i2c_i801 crc32_pclmul snd_seq_device crc32c_intel wmi snd_pcm serio_raw mei_me tpm_infineon i2c_smbus video mei ghash_clmulni_intel lpc_ich snd_timer snd soundcore ip_tables
 CPU: 6 PID: 646 Comm: systemd-udevd Not tainted 5.11.0-test+ #24
 Hardware name: Hewlett-Packard HP Compaq Pro 6300 SFF/339A, BIOS K01 v03.03 07/14/2016
 RIP: 0010:__static_call_validate+0x68/0x80
 Code: 05 4f 7a fc 00 75 d7 0f b6 05 4a 7a fc 00 38 47 04 75 cb c3 48 89 fa 48 c7 c7 a0 66 35 89 c6 05 cd 92 9a 01 01 e8 d7 72 b2 00 <0f> 0b c3 0f b6 4a 04 38 4f 04 75 c9 c3 c3 66 2e 0f 1f 84 00 00 00
 e1000e 0000:00:19.0 0000:00:19.0 (uninitialized): registered PHC clock
 RSP: 0018:ffffa67d0050fc30 EFLAGS: 00010286
 RAX: 0000000000000000 RBX: 0000000000000000 RCX: ffff9584da800000
 RDX: 0000000000000000 RSI: ffffffff88156d6f RDI: ffffffff88156d6f
 RBP: ffffffffc0219f2a R08: 00000007e8bf25a1 R09: 0000000000000000
 R10: 0000000000000001 R11: 0000000000000001 R12: ffffffff8826c3c0
 R13: 0000000000000000 R14: ffffffffc0219f2a R15: ffffffffc0293e1b
 FS:  00007f4bd2a29940(0000) GS:ffff9584da800000(0000) knlGS:0000000000000000
 CS:  0010 DS: 0000 ES: 0000 CR0: 0000000080050033
 CR2: 00007fd14f762f44 CR3: 00000001069ce003 CR4: 00000000001706e0
 Call Trace:
  arch_static_call_transform+0x5f/0x90
  __static_call_init.part.0+0x15f/0x210
  ? __SCT__tp_func_sched_update_nr_running_tp+0x8/0x8
  static_call_module_notify+0x6b/0x190
 e1000e 0000:00:19.0 eth0: (PCI Express:2.5GT/s:Width x1) b4:b5:2f:ce:18:65
  notifier_call_chain_robust+0x5a/0xc0
 e1000e 0000:00:19.0 eth0: Intel(R) PRO/1000 Network Connection
  blocking_notifier_call_chain_robust+0x43/0x60
 e1000e 0000:00:19.0 eth0: MAC: 10, PHY: 11, PBA No: 0100FF-0FF
  load_module+0x2256/0x2ca0
  ? __kernel_read+0x152/0x2d0
  ? kernel_read_file+0x220/0x280
  ? __do_sys_finit_module+0xb1/0x110
  __do_sys_finit_module+0xb1/0x110
  do_syscall_64+0x33/0x40
  entry_SYSCALL_64_after_hwframe+0x44/0xae

It appears to be tripping up oven the static caller in cond_resched() in that function.

Attached is my config.

-- Steve

maintainer
#1 lore raw

PATCH 1/1 static_call: Fix the module key fixup

Subject: static_call: Fix the module key fixup

Provided the target address of a R_X86_64_PC32 relocation is aligned, the low two bits should be invariant between the relative and absolute value.

Turns out the address is not aligned and things go sideways, ensure we transfer the bits in the absolute form when fixing up the key address.

---
 kernel/static_call.c | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)
kernel/static_call.c +4 -3
index 6906c6ec4c97..ae825295cf68 100644
@@ -349,7 +349,8 @@ static int static_call_add_module(struct module *mod)
 	struct static_call_site *site;
 
 	for (site = start; site != stop; site++) {
-		unsigned long addr = (unsigned long)static_call_key(site);
+		unsigned long s_key = (long)site->key + (long)&site->key;
+		unsigned long addr = s_key & ~STATIC_CALL_SITE_FLAGS;
 		unsigned long key;
 
 		/*
@@ -373,8 +374,8 @@ static int static_call_add_module(struct module *mod)
 			return -EINVAL;
 		}
 
-		site->key = (key - (long)&site->key) |
-			    (site->key & STATIC_CALL_SITE_FLAGS);
+		key |= s_key & STATIC_CALL_SITE_FLAGS;
+		site->key = key - (long)&site->key;
 	}
 
 	return __static_call_init(mod, start, stop);
author reviewer Tested-by on v1 1/1
#2 lore raw

Re: [PATCH] static_call: Fix the module key fixup

Quoted 9 lines · On Thu, 25 Feb 2021 23:03:51 +0100 Peter Zijlstra <[email protected]> wrote:

Subject: static_call: Fix the module key fixup

Provided the target address of a R_X86_64_PC32 relocation is aligned, the low two bits should be invariant between the relative and absolute value.

Turns out the address is not aligned and things go sideways, ensure we transfer the bits in the absolute form when fixing up the key address.

Quoted 1 line

-- Steve

Quoted 30 lines
---
 kernel/static_call.c | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)
kernel/static_call.c +4 -3
index 6906c6ec4c97..ae825295cf68 100644
@@ -349,7 +349,8 @@ static int static_call_add_module(struct module *mod)
 	struct static_call_site *site;
 
 	for (site = start; site != stop; site++) {
-		unsigned long addr = (unsigned long)static_call_key(site);
+		unsigned long s_key = (long)site->key + (long)&site->key;
+		unsigned long addr = s_key & ~STATIC_CALL_SITE_FLAGS;
 		unsigned long key;
 
 		/*
@@ -373,8 +374,8 @@ static int static_call_add_module(struct module *mod)
 			return -EINVAL;
 		}
 
-		site->key = (key - (long)&site->key) |
-			    (site->key & STATIC_CALL_SITE_FLAGS);
+		key |= s_key & STATIC_CALL_SITE_FLAGS;
+		site->key = key - (long)&site->key;
 	}
 
 	return __static_call_init(mod, start, stop);
merge bot Applied
#3 lore raw

[tip: locking/urgent] static_call: Fix the module key fixup

In reply to Peter Zijlstra
The following commit has been merged into the locking/urgent branch of tip:

The following commit has been merged into the locking/urgent branch of tip:

Commit-ID:     8b97c027dfe4ba195be08fd0e18f716005763b8a
Gitweb:        https://git.kernel.org/tip/8b97c027dfe4ba195be08fd0e18f716005763b8a
Author:        Peter Zijlstra <[email protected]>
AuthorDate:    Thu, 25 Feb 2021 23:03:51 +01:00
Committer:     Peter Zijlstra <[email protected]>
CommitterDate: Mon, 01 Mar 2021 11:02:10 +01:00

static_call: Fix the module key fixup

Provided the target address of a R_X86_64_PC32 relocation is aligned, the low two bits should be invariant between the relative and absolute value.

Turns out the address is not aligned and things go sideways, ensure we transfer the bits in the absolute form when fixing up the key address.

Fixes 73f44fe19d35 ("static_call: Allow module use without exposing static_call_key")
---
 kernel/static_call.c | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)
kernel/static_call.c +4 -3
index 6906c6e..ae82529 100644
@@ -349,7 +349,8 @@ static int static_call_add_module(struct module *mod)
 	struct static_call_site *site;
 
 	for (site = start; site != stop; site++) {
-		unsigned long addr = (unsigned long)static_call_key(site);
+		unsigned long s_key = (long)site->key + (long)&site->key;
+		unsigned long addr = s_key & ~STATIC_CALL_SITE_FLAGS;
 		unsigned long key;
 
 		/*
@@ -373,8 +374,8 @@ static int static_call_add_module(struct module *mod)
 			return -EINVAL;
 		}
 
-		site->key = (key - (long)&site->key) |
-			    (site->key & STATIC_CALL_SITE_FLAGS);
+		key |= s_key & STATIC_CALL_SITE_FLAGS;
+		site->key = key - (long)&site->key;
 	}
 
 	return __static_call_init(mod, start, stop);
merge bot Applied
#4 lore raw

[tip: locking/core] static_call: Fix the module key fixup

In reply to Peter Zijlstra
The following commit has been merged into the locking/core branch of tip:

The following commit has been merged into the locking/core branch of tip:

Commit-ID:     50bf8080a94d171e843fc013abec19d8ab9f50ae
Gitweb:        https://git.kernel.org/tip/50bf8080a94d171e843fc013abec19d8ab9f50ae
Author:        Peter Zijlstra <[email protected]>
AuthorDate:    Thu, 25 Feb 2021 23:03:51 +01:00
Committer:     Ingo Molnar <[email protected]>
CommitterDate: Sat, 06 Mar 2021 12:49:08 +01:00

static_call: Fix the module key fixup

Provided the target address of a R_X86_64_PC32 relocation is aligned, the low two bits should be invariant between the relative and absolute value.

Turns out the address is not aligned and things go sideways, ensure we transfer the bits in the absolute form when fixing up the key address.

Fixes 73f44fe19d35 ("static_call: Allow module use without exposing static_call_key")
---
 kernel/static_call.c | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)
kernel/static_call.c +4 -3
index 6906c6e..ae82529 100644
@@ -349,7 +349,8 @@ static int static_call_add_module(struct module *mod)
 	struct static_call_site *site;
 
 	for (site = start; site != stop; site++) {
-		unsigned long addr = (unsigned long)static_call_key(site);
+		unsigned long s_key = (long)site->key + (long)&site->key;
+		unsigned long addr = s_key & ~STATIC_CALL_SITE_FLAGS;
 		unsigned long key;
 
 		/*
@@ -373,8 +374,8 @@ static int static_call_add_module(struct module *mod)
 			return -EINVAL;
 		}
 
-		site->key = (key - (long)&site->key) |
-			    (site->key & STATIC_CALL_SITE_FLAGS);
+		key |= s_key & STATIC_CALL_SITE_FLAGS;
+		site->key = key - (long)&site->key;
 	}
 
 	return __static_call_init(mod, start, stop);