mirror of
https://github.com/dynup/kpatch
synced 2025-03-30 23:26:23 +00:00
kpatch-build: Add sym->has_func_profiling support for aarch64
The "has_function_profiling" support field in the symbol struct is used to show that a function symbol is able to be patched. This is necessary to check that functions which need to be patched are able to be. On arm64 this means the presence of 2 NOP instructions at function entry which are patched by ftrace to call the ftrace handling code. These 2 NOPs are inserted by the compiler and the location of them is recorded in a section called "__patchable_function_entries". Check whether a symbol has a corresponding entry in the "__patchable_function_entries" section and if so mark it as "has_func_profiling". Signed-off-by: Suraj Jitindar Singh <surajjs@amazon.com> --- V1->V2: - Make error message standard across architectures when no patchable entry - Don't store __patchable_function_entries section in kpatch_find_func_profiling_calls(), instead find it each time
This commit is contained in:
parent
e0b20c9673
commit
fcae79f54b
@ -1696,7 +1696,7 @@ static void kpatch_check_func_profiling_calls(struct kpatch_elf *kelf)
|
||||
(sym->parent && sym->parent->status == CHANGED))
|
||||
continue;
|
||||
if (!sym->twin->has_func_profiling) {
|
||||
log_normal("function %s has no fentry/mcount call, unable to patch\n",
|
||||
log_normal("function %s doesn't have patchable function entry, unable to patch\n",
|
||||
sym->name);
|
||||
errs++;
|
||||
}
|
||||
@ -3976,6 +3976,24 @@ static void kpatch_find_func_profiling_calls(struct kpatch_elf *kelf)
|
||||
continue;
|
||||
|
||||
switch(kelf->arch) {
|
||||
case AARCH64: {
|
||||
struct section *sec = find_section_by_name(&kelf->sections,
|
||||
"__patchable_function_entries");
|
||||
/*
|
||||
* If we can't find the __patchable_function_entries section or
|
||||
* there are no relocations in it then not patchable.
|
||||
*/
|
||||
if (!sec || !sec->rela)
|
||||
return;
|
||||
list_for_each_entry(rela, &sec->rela->relas, list) {
|
||||
if (rela->sym->sec && sym->sec == rela->sym->sec) {
|
||||
sym->has_func_profiling = 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
case PPC64:
|
||||
list_for_each_entry(rela, &sym->sec->rela->relas, list) {
|
||||
if (!strcmp(rela->sym->name, "_mcount")) {
|
||||
|
@ -604,6 +604,9 @@ struct kpatch_elf *kpatch_elf_open(const char *name)
|
||||
if (!gelf_getehdr(kelf->elf, &ehdr))
|
||||
ERROR("gelf_getehdr");
|
||||
switch (ehdr.e_machine) {
|
||||
case EM_AARCH64:
|
||||
kelf->arch = AARCH64;
|
||||
break;
|
||||
case EM_PPC64:
|
||||
kelf->arch = PPC64;
|
||||
break;
|
||||
|
@ -115,6 +115,7 @@ enum architecture {
|
||||
PPC64 = 0x1 << 0,
|
||||
X86_64 = 0x1 << 1,
|
||||
S390 = 0x1 << 2,
|
||||
AARCH64 = 0x1 << 3,
|
||||
};
|
||||
|
||||
struct kpatch_elf {
|
||||
|
Loading…
Reference in New Issue
Block a user