perf dso: Add BPF DSO read and size hooks
Add BPF related code into DSO reading paths to return size (bpf_size) and read the BPF code (bpf_read). Signed-off-by: Jiri Olsa <jolsa@kernel.org> Acked-by: Song Liu <songliubraving@fb.com> Cc: Adrian Hunter <adrian.hunter@intel.com> Cc: Alexander Shishkin <alexander.shishkin@linux.intel.com> Cc: Andi Kleen <ak@linux.intel.com> Cc: Namhyung Kim <namhyung@kernel.org> Cc: Peter Zijlstra <peterz@infradead.org> Cc: Stanislav Fomichev <sdf@google.com> Link: http://lkml.kernel.org/r/20190508132010.14512-5-jolsa@kernel.org [ Use uintptr_t when casting from u64 to u8 pointers ] Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
This commit is contained in:
parent
cacddfe7b0
commit
6c398d723a
|
@ -9,6 +9,8 @@
|
|||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <libgen.h>
|
||||
#include <bpf/libbpf.h>
|
||||
#include "bpf-event.h"
|
||||
#include "compress.h"
|
||||
#include "namespaces.h"
|
||||
#include "path.h"
|
||||
|
@ -706,6 +708,44 @@ bool dso__data_status_seen(struct dso *dso, enum dso_data_status_seen by)
|
|||
return false;
|
||||
}
|
||||
|
||||
static ssize_t bpf_read(struct dso *dso, u64 offset, char *data)
|
||||
{
|
||||
struct bpf_prog_info_node *node;
|
||||
ssize_t size = DSO__DATA_CACHE_SIZE;
|
||||
u64 len;
|
||||
u8 *buf;
|
||||
|
||||
node = perf_env__find_bpf_prog_info(dso->bpf_prog.env, dso->bpf_prog.id);
|
||||
if (!node || !node->info_linear) {
|
||||
dso->data.status = DSO_DATA_STATUS_ERROR;
|
||||
return -1;
|
||||
}
|
||||
|
||||
len = node->info_linear->info.jited_prog_len;
|
||||
buf = (u8 *)(uintptr_t)node->info_linear->info.jited_prog_insns;
|
||||
|
||||
if (offset >= len)
|
||||
return -1;
|
||||
|
||||
size = (ssize_t)min(len - offset, (u64)size);
|
||||
memcpy(data, buf + offset, size);
|
||||
return size;
|
||||
}
|
||||
|
||||
static int bpf_size(struct dso *dso)
|
||||
{
|
||||
struct bpf_prog_info_node *node;
|
||||
|
||||
node = perf_env__find_bpf_prog_info(dso->bpf_prog.env, dso->bpf_prog.id);
|
||||
if (!node || !node->info_linear) {
|
||||
dso->data.status = DSO_DATA_STATUS_ERROR;
|
||||
return -1;
|
||||
}
|
||||
|
||||
dso->data.file_size = node->info_linear->info.jited_prog_len;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
dso_cache__free(struct dso *dso)
|
||||
{
|
||||
|
@ -832,7 +872,11 @@ dso_cache__read(struct dso *dso, struct machine *machine,
|
|||
if (!cache)
|
||||
return -ENOMEM;
|
||||
|
||||
ret = file_read(dso, machine, cache_offset, cache->data);
|
||||
if (dso->binary_type == DSO_BINARY_TYPE__BPF_PROG_INFO)
|
||||
ret = bpf_read(dso, cache_offset, cache->data);
|
||||
else
|
||||
ret = file_read(dso, machine, cache_offset, cache->data);
|
||||
|
||||
if (ret > 0) {
|
||||
cache->offset = cache_offset;
|
||||
cache->size = ret;
|
||||
|
@ -941,6 +985,9 @@ int dso__data_file_size(struct dso *dso, struct machine *machine)
|
|||
if (dso->data.status == DSO_DATA_STATUS_ERROR)
|
||||
return -1;
|
||||
|
||||
if (dso->binary_type == DSO_BINARY_TYPE__BPF_PROG_INFO)
|
||||
return bpf_size(dso);
|
||||
|
||||
return file_size(dso, machine);
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue