summaryrefslogtreecommitdiffstats
path: root/tools/lib/bpf/libbpf.c
diff options
context:
space:
mode:
Diffstat (limited to 'tools/lib/bpf/libbpf.c')
-rw-r--r--tools/lib/bpf/libbpf.c26
1 files changed, 26 insertions, 0 deletions
diff --git a/tools/lib/bpf/libbpf.c b/tools/lib/bpf/libbpf.c
index 102156f322b6..e8088f8214d1 100644
--- a/tools/lib/bpf/libbpf.c
+++ b/tools/lib/bpf/libbpf.c
@@ -110,6 +110,11 @@ struct bpf_object {
Elf *elf;
GElf_Ehdr ehdr;
Elf_Data *symbols;
+ struct {
+ GElf_Shdr shdr;
+ Elf_Data *data;
+ } *reloc;
+ int nr_reloc;
} efile;
char path[];
};
@@ -231,6 +236,9 @@ static void bpf_object__elf_finish(struct bpf_object *obj)
obj->efile.elf = NULL;
}
obj->efile.symbols = NULL;
+
+ zfree(&obj->efile.reloc);
+ obj->efile.nr_reloc = 0;
zclose(obj->efile.fd);
obj->efile.obj_buf = NULL;
obj->efile.obj_buf_sz = 0;
@@ -447,6 +455,24 @@ static int bpf_object__elf_collect(struct bpf_object *obj)
pr_warning("failed to alloc program %s (%s): %s",
name, obj->path, errmsg);
}
+ } else if (sh.sh_type == SHT_REL) {
+ void *reloc = obj->efile.reloc;
+ int nr_reloc = obj->efile.nr_reloc + 1;
+
+ reloc = realloc(reloc,
+ sizeof(*obj->efile.reloc) * nr_reloc);
+ if (!reloc) {
+ pr_warning("realloc failed\n");
+ err = -ENOMEM;
+ } else {
+ int n = nr_reloc - 1;
+
+ obj->efile.reloc = reloc;
+ obj->efile.nr_reloc = nr_reloc;
+
+ obj->efile.reloc[n].shdr = sh;
+ obj->efile.reloc[n].data = data;
+ }
}
if (err)
goto out;