objtool/klp: Special section validation fixes
Subsystems (2)
Josh Poimboeuf
maintainercover objtool/klp: Special section validation fixes
Fix some issues in validate_special_section_klp_reloc().
Josh Poimboeuf (3):
objtool/klp: Fix detection of corrupt static branch/call entries objtool/klp: Disable unsupported pr_debug() usage objtool/klp: Avoid NULL pointer dereference when printing code symbol
name
tools/objtool/klp-diff.c | 39 ++++++++++++++++++++++++++------------- 1 file changed, 26 insertions(+), 13 deletions(-)
Signature · 1 line
2.53.0
Josh Poimboeuf
maintainerPATCH 1/3 objtool/klp: Fix detection of corrupt static branch/call entries
Patching a function which references a static key living in a kernel module is unsupported due to ordering issues inherent to late module patching:
1) Load a livepatch module which has a __jump_table entry which needs a klp reloc to reference static key K which lives in module M.
2) The __jump_table klp reloc does *not* get resolved because module M is not yet loaded.
3) jump_label_add_module() corrupts memory (or causes a panic) when dereferencing the uninitialized pointer to key K.
validate_special_section_klp_reloc() intends to prevent that from ever happening by catching it at build time. However, it incorrectly assumes the special section entry's reloc symbol references have already been converted from section symbols to object symbols, causing the validation to miss corruption in extracted static branch/call table entries.
Make sure the references have been properly converted before doing the validation.
--- tools/objtool/klp-diff.c | 3 +++ 1 file changed, 3 insertions(+)
tools/objtool/klp-diff.c +3 -0
@@ -1364,6 +1364,9 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *symconst char *sym_modname;struct export *export; +if (convert_reloc_sym (e->patched, reloc)) +continue ; +/* Static branch/call keys are always STT_OBJECT */ if (reloc->sym->type !=STT_OBJECT ) {
Signature · 1 line
2.53.0
[tip: objtool/urgent] objtool/klp: Fix detection of corrupt static branch/call entries
The following commit has been merged into the objtool/urgent branch of tip:
The following commit has been merged into the objtool/urgent branch of tip:
Commit-ID: f9fb44b0ecefc1f218db56661ed66d4e8d67317d Gitweb: https://git.kernel.org/tip/f9fb44b0ecefc1f218db56661ed66d4e8d67317d Author: Josh Poimboeuf <[email protected]> AuthorDate: Tue, 10 Feb 2026 13:50:09 -08:00 Committer: Josh Poimboeuf <[email protected]> CommitterDate: Fri, 06 Mar 2026 07:47:10 -08:00
objtool/klp: Fix detection of corrupt static branch/call entries
Patching a function which references a static key living in a kernel module is unsupported due to ordering issues inherent to late module patching:
1) Load a livepatch module which has a __jump_table entry which needs a klp reloc to reference static key K which lives in module M.
2) The __jump_table klp reloc does *not* get resolved because module M is not yet loaded.
3) jump_label_add_module() corrupts memory (or causes a panic) when dereferencing the uninitialized pointer to key K.
validate_special_section_klp_reloc() intends to prevent that from ever happening by catching it at build time. However, it incorrectly assumes the special section entry's reloc symbol references have already been converted from section symbols to object symbols, causing the validation to miss corruption in extracted static branch/call table entries.
Make sure the references have been properly converted before doing the validation.
--- tools/objtool/klp-diff.c | 3 +++ 1 file changed, 3 insertions(+)
tools/objtool/klp-diff.c +3 -0
@@ -1364,6 +1364,9 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *symconst char *sym_modname;struct export *export; +if (convert_reloc_sym (e->patched, reloc)) +continue ; +/* Static branch/call keys are always STT_OBJECT */ if (reloc->sym->type !=STT_OBJECT ) {
Josh Poimboeuf
maintainerPATCH 2/3 objtool/klp: Disable unsupported pr_debug() usage
In reply to Josh PoimboeufInstead of erroring out on unsupported pr_debug() (e.g., when patching a module), issue a warning and make it inert, similar to how unsupported tracepoints are currently handled.
--- tools/objtool/klp-diff.c | 23 +++++++++++++++-------- 1 file changed, 15 insertions(+), 8 deletions(-)
tools/objtool/klp-diff.c +15 -8
@@ -1334,18 +1334,18 @@ static bool should_keep_special_sym(struct elf *elf, struct symbol *sym)* be applied after static branch/call init, resulting in code corruption. * * Validate a special section entry to avoid that. Note that an inert -* tracepoint is harmless enough, in that case just skip the entry and print a -* warning. Otherwise, return an error. +* tracepoint or pr_debug() is harmless enough, in that case just skip the +* entry and print a warning. Otherwise, return an error. * -* This is only a temporary limitation which will be fixed when livepatch adds -* support for submodules: fully self-contained modules which are embedded in -* the top-level livepatch module's data and which can be loaded on demand when -* their corresponding to-be-patched module gets loaded. Then klp relocs can -* be retired. +* TODO: This is only a temporary limitation which will be fixed when livepatch +* adds support for submodules: fully self-contained modules which are embedded +* in the top-level livepatch module's data and which can be loaded on demand +* when their corresponding to-be-patched module gets loaded. Then klp relocs +* can be retired. * * Return: * -1: error: validation failed -* 1: warning: tracepoint skipped +* 1: warning: disabled tracepoint or pr_debug() * 0: success */ static int validate_special_section_klp_reloc (struct elfs *e,struct symbol *sym)
@@ -1403,6 +1403,13 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *symcontinue ; } +if (strstr (reloc->sym->name,"__UNIQUE_ID_ddebug_" )) { +WARN ("%s: disabling unsupported pr_debug()" , + code_sym->name); + ret =1 ; +continue ; + } +ERROR ("%s+0x%lx: unsupported static branch key %s. Use static_key_enabled() instead" , code_sym->name, code_offset, reloc->sym->name);return -1 ;
Signature · 1 line
2.53.0
[tip: objtool/urgent] objtool/klp: Disable unsupported pr_debug() usage
The following commit has been merged into the objtool/urgent branch of tip:
The following commit has been merged into the objtool/urgent branch of tip:
Commit-ID: e476bb277cf91b7ac3ea803ec78a4f0791bddec3 Gitweb: https://git.kernel.org/tip/e476bb277cf91b7ac3ea803ec78a4f0791bddec3 Author: Josh Poimboeuf <[email protected]> AuthorDate: Tue, 10 Feb 2026 13:50:10 -08:00 Committer: Josh Poimboeuf <[email protected]> CommitterDate: Fri, 06 Mar 2026 07:47:11 -08:00
objtool/klp: Disable unsupported pr_debug() usage
Instead of erroring out on unsupported pr_debug() (e.g., when patching a module), issue a warning and make it inert, similar to how unsupported tracepoints are currently handled.
--- tools/objtool/klp-diff.c | 23 +++++++++++++++-------- 1 file changed, 15 insertions(+), 8 deletions(-)
tools/objtool/klp-diff.c +15 -8
@@ -1334,18 +1334,18 @@ static bool should_keep_special_sym(struct elf *elf, struct symbol *sym)* be applied after static branch/call init, resulting in code corruption. * * Validate a special section entry to avoid that. Note that an inert -* tracepoint is harmless enough, in that case just skip the entry and print a -* warning. Otherwise, return an error. +* tracepoint or pr_debug() is harmless enough, in that case just skip the +* entry and print a warning. Otherwise, return an error. * -* This is only a temporary limitation which will be fixed when livepatch adds -* support for submodules: fully self-contained modules which are embedded in -* the top-level livepatch module's data and which can be loaded on demand when -* their corresponding to-be-patched module gets loaded. Then klp relocs can -* be retired. +* TODO: This is only a temporary limitation which will be fixed when livepatch +* adds support for submodules: fully self-contained modules which are embedded +* in the top-level livepatch module's data and which can be loaded on demand +* when their corresponding to-be-patched module gets loaded. Then klp relocs +* can be retired. * * Return: * -1: error: validation failed -* 1: warning: tracepoint skipped +* 1: warning: disabled tracepoint or pr_debug() * 0: success */ static int validate_special_section_klp_reloc (struct elfs *e,struct symbol *sym)
@@ -1403,6 +1403,13 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *symcontinue ; } +if (strstr (reloc->sym->name,"__UNIQUE_ID_ddebug_" )) { +WARN ("%s: disabling unsupported pr_debug()" , + code_sym->name); + ret =1 ; +continue ; + } +ERROR ("%s+0x%lx: unsupported static branch key %s. Use static_key_enabled() instead" , code_sym->name, code_offset, reloc->sym->name);return -1 ;
Josh Poimboeuf
maintainerPATCH 3/3 objtool/klp: Avoid NULL pointer dereference when printing code symbol name
In reply to Josh PoimboeufFix a hypothetical NULL pointer defereference of the 'code_sym' variable. In theory this should never happen.
--- tools/objtool/klp-diff.c | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-)
tools/objtool/klp-diff.c +9 -6
@@ -1352,7 +1352,7 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *sym {bool static_branch = !strcmp (sym->sec->name,"__jump_table" );bool static_call = !strcmp (sym->sec->name,".static_call_sites" ); -struct symbol *code_sym =NULL ; +const char *code_sym =NULL ;unsigned long code_offset =0 ;struct reloc *reloc;int ret =0 ;
@@ -1372,7 +1372,7 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *sym/* Save code location which can be printed below */ if (reloc->sym->type ==STT_FUNC && !code_sym) { - code_sym = reloc->sym; + code_sym = reloc->sym->name; code_offset =reloc_addend (reloc); }
@@ -1395,23 +1395,26 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *symif (!strcmp (sym_modname,"vmlinux" ))continue ; +if (!code_sym) + code_sym ="<unknown>" ; +if (static_branch) {if (strstarts (reloc->sym->name,"__tracepoint_" )) {WARN ("%s: disabling unsupported tracepoint %s" , - code_sym->name, reloc->sym->name +13 ); + code_sym, reloc->sym->name +13 ); ret =1 ;continue ; }if (strstr (reloc->sym->name,"__UNIQUE_ID_ddebug_" )) {WARN ("%s: disabling unsupported pr_debug()" , - code_sym->name); + code_sym); ret =1 ;continue ; }ERROR ("%s+0x%lx: unsupported static branch key %s. Use static_key_enabled() instead" , - code_sym->name, code_offset, reloc->sym->name); + code_sym, code_offset, reloc->sym->name);return -1 ; }
@@ -1422,7 +1425,7 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *sym }ERROR ("%s()+0x%lx: unsupported static call key %s. Use KLP_STATIC_CALL() instead" , - code_sym->name, code_offset, reloc->sym->name); + code_sym, code_offset, reloc->sym->name);return -1 ; }
Signature · 1 line
2.53.0
[tip: objtool/urgent] objtool/klp: Avoid NULL pointer dereference when printing code symbol name
The following commit has been merged into the objtool/urgent branch of tip:
The following commit has been merged into the objtool/urgent branch of tip:
Commit-ID: 11c2adcd1fa2a9380a507db1e57c8542bfc81827 Gitweb: https://git.kernel.org/tip/11c2adcd1fa2a9380a507db1e57c8542bfc81827 Author: Josh Poimboeuf <[email protected]> AuthorDate: Tue, 10 Feb 2026 13:50:11 -08:00 Committer: Josh Poimboeuf <[email protected]> CommitterDate: Fri, 06 Mar 2026 07:47:11 -08:00
objtool/klp: Avoid NULL pointer dereference when printing code symbol name
Fix a hypothetical NULL pointer defereference of the 'code_sym' variable. In theory this should never happen.
--- tools/objtool/klp-diff.c | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-)
tools/objtool/klp-diff.c +9 -6
@@ -1352,7 +1352,7 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *sym {bool static_branch = !strcmp (sym->sec->name,"__jump_table" );bool static_call = !strcmp (sym->sec->name,".static_call_sites" ); -struct symbol *code_sym =NULL ; +const char *code_sym =NULL ;unsigned long code_offset =0 ;struct reloc *reloc;int ret =0 ;
@@ -1372,7 +1372,7 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *sym/* Save code location which can be printed below */ if (reloc->sym->type ==STT_FUNC && !code_sym) { - code_sym = reloc->sym; + code_sym = reloc->sym->name; code_offset =reloc_addend (reloc); }
@@ -1395,23 +1395,26 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *symif (!strcmp (sym_modname,"vmlinux" ))continue ; +if (!code_sym) + code_sym ="<unknown>" ; +if (static_branch) {if (strstarts (reloc->sym->name,"__tracepoint_" )) {WARN ("%s: disabling unsupported tracepoint %s" , - code_sym->name, reloc->sym->name +13 ); + code_sym, reloc->sym->name +13 ); ret =1 ;continue ; }if (strstr (reloc->sym->name,"__UNIQUE_ID_ddebug_" )) {WARN ("%s: disabling unsupported pr_debug()" , - code_sym->name); + code_sym); ret =1 ;continue ; }ERROR ("%s+0x%lx: unsupported static branch key %s. Use static_key_enabled() instead" , - code_sym->name, code_offset, reloc->sym->name); + code_sym, code_offset, reloc->sym->name);return -1 ; }
@@ -1422,7 +1425,7 @@ static int validate_special_section_klp_reloc(struct elfs *e, struct symbol *sym }ERROR ("%s()+0x%lx: unsupported static call key %s. Use KLP_STATIC_CALL() instead" , - code_sym->name, code_offset, reloc->sym->name); + code_sym, code_offset, reloc->sym->name);return -1 ; }
Song Liu
maintainerQuoted 8 lines · Josh Poimboeuf
Fix some issues in
validate_special_section_klp_reloc().Josh Poimboeuf (3):
objtool/klp: Fix detection of corrupt static branch/call entries objtool/klp: Disable unsupportedpr_debug()usage objtool/klp: Avoid NULL pointer dereference when printing code symbol
name
For the set
Quoted 7 lines
tools/objtool/klp-diff.c | 39 ++++++++++++++++++++++++++------------- 1 file changed, 26 insertions(+), 13 deletions(-)--
2.53.0