For in_ksymbol_range(), it determine the kernel range by st->symtable[0].value
as the start and st->symtable[st->symcnt-1].value as the end, this
however, implies the last element is in the kernel range. In most
cases it was correct, but it is no longer valid with the kernel commit [1].
The xen_elfnote_phys32_entry_value introduced by [1], is beyound the kernel
range(doesn't belong to any kernel section), thus doesn't get relocated
by relocate(). So in order to have a correct in_ksymbol_range(), we need
to eliminate those symbols.
Without the patch:
crash> sym schedule
ffffffff973ffb30 (T) schedule /root/linux-6.14-rc3/kernel/sched/core.c: 6848
crash> sym 0xffffffff973ffb30
sym: invalid address: 0xffffffff973ffb30
With the patch:
crash> sym schedule
ffffffff973ffb30 (T) schedule /root/linux-6.14-rc3/kernel/sched/core.c: 6848
crash> sym 0xffffffff973ffb30
ffffffff973ffb30 (T) schedule /root/linux-6.14-rc3/kernel/sched/core.c: 6848
[1]:
https://github.com/torvalds/linux/commit/223abe96ac0d227b22d48ab447dd9384...
Signed-off-by: Tao Liu <ltao(a)redhat.com>
---
v2 -> v1: In fact the gnu_qsort() does sort the symbols with no
problem, unlike the root cause described in v1. It's because
xen_elfnote_phys32_entry_value doesn't belong to any kernel
section, so the
symval >= st->first_section_start && symval <=
st->last_section_end
check will not success in relocate(), so the symbol is not relocated.
But I'm not sure if xen_elfnote_phys32_entry_value should be
relocated or not, it looks to be an absoluate symbol to me,
but the code comment is not very clear...
v1 patch:
https://www.mail-archive.com/devel@lists.crash-utility.osci.io/msg01373.html
v1 discussion:
https://www.mail-archive.com/devel@lists.crash-utility.osci.io/msg01378.html
---
---
symbols.c | 8 +++++++-
1 file changed, 7 insertions(+), 1 deletion(-)
diff --git a/symbols.c b/symbols.c
index 6385d02..edbafa4 100644
--- a/symbols.c
+++ b/symbols.c
@@ -5443,8 +5443,14 @@ old_module:
int
in_ksymbol_range(ulong value)
{
+ int i;
+ for (i = st->symcnt-1; i >= 0; i--) {
+ if (!strstr(st->symtable[i].name, "xen_elfnote"))
+ break;
+ }
+
if ((value >= st->symtable[0].value) &&
- (value <= st->symtable[st->symcnt-1].value)) {
+ (value <= st->symtable[i].value)) {
if ((st->flags & PERCPU_SYMS) && (value < st->first_ksymbol))
return FALSE;
else
--
2.47.0