Unchanged and unpatchable function moves from .text to .text.unlikely
Closed this issue · 5 comments
Xinhua Li reports another potential bug similar to #1385 (building the following kpatch with RHEL9 kernel-5.14.0-362.24.1.el9_3.x86_64) except this time it's an UNchanged function that moves (so create-diff-object marks as CHANGED), but then it fails the mcount/fentry check as it's annotated as notrace:
--- src.orig/arch/x86/kernel/cpu/proc.c 2024-04-15 14:46:29.203617033 -0400
+++ src/arch/x86/kernel/cpu/proc.c 2024-04-15 14:46:43.803518044 -0400
@@ -65,7 +65,8 @@ static int show_cpuinfo(struct seq_file
int i;
cpu = c->cpu_index;
- seq_printf(m, "processor\t: %u\n"
+ printk(KERN_ALERT "show_cpuinfo current \n");
+ seq_printf(m, "TAM demo processor\t: %u\n"
"vendor_id\t: %s\n"
"cpu family\t: %d\n"
"model\t\t: %u\n"
results in kpatch-build error:
proc.ORIG.o: function cpumask_weight has no fentry/mcount call, unable to patch
ERROR: proc.ORIG.o: 1 function(s) can not be patched
create-diff-object: unreconcilable difference
Note that cpumask_weight() moves from .text.cpumask_weight to .text.unlikely.cpumask_weight, but otherwise carries no object code differences:
$ diff -upr \
<(objdump -Dr -j.text.cpumask_weight proc.ORIG.o) \
<(objdump -Dr -j.text.unlikely.cpumask_weight proc.PATCHED.o)
--- /dev/fd/63 2024-04-15 14:53:36.281721258 -0400
+++ /dev/fd/62 2024-04-15 14:53:36.282721251 -0400
@@ -1,8 +1,8 @@
-proc.ORIG.o: file format elf64-x86-64
+proc.PATCHED.o: file format elf64-x86-64
-Disassembly of section .text.cpumask_weight:
+Disassembly of section .text.unlikely.cpumask_weight:
0000000000000000 <__pfx_cpumask_weight>:
0: 90 nop
cpumask_weight() is included because create-diff-object considers the section change as allowed and marks the symbol as CHANGED:
static void kpatch_compare_correlated_symbol(struct symbol *sym)
{
[ ... snip ... ]
/*
* If two symbols are correlated but their sections are not, then the
* symbol has changed sections. This is only allowed if the symbol is
* moving out of an ignored section, or moving between normal/hot/unlikely
* subsections.
*/
if (sym1->sec && sym2->sec && sym1->sec->twin != sym2->sec) {
if ((sym2->sec->twin && sym2->sec->twin->ignore) ||
kpatch_subsection_changed(sym1->sec, sym2->sec))
sym->status = CHANGED;
else
DIFF_FATAL("symbol changed sections: %s", sym1->name);
}
[ ... snip ... ]
The CHANGED status means that we will be trying to kpatch the original function with the new one.
This issue has been open for 30 days with no activity and no assignee. It will be closed in 7 days unless a comment is added.
This issue was closed because it was inactive for 7 days after being marked stale.
This issue has been open for 30 days with no activity and no assignee. It will be closed in 7 days unless a comment is added.
This issue was closed because it was inactive for 7 days after being marked stale.