cregit-Linux how code gets into the kernel

Release 4.18 tools/testing/selftests/bpf/trace_helpers.c

// SPDX-License-Identifier: GPL-2.0
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include <errno.h>
#include <poll.h>
#include <unistd.h>
#include <linux/perf_event.h>
#include <sys/mman.h>
#include "trace_helpers.h"


#define MAX_SYMS 300000

static struct ksym syms[MAX_SYMS];

static int sym_cnt;


static int ksym_cmp(const void *p1, const void *p2) { return ((struct ksym *)p1)->addr - ((struct ksym *)p2)->addr; }

Contributors

PersonTokensPropCommitsCommitProp
Yonghong Song39100.00%1100.00%
Total39100.00%1100.00%


int load_kallsyms(void) { FILE *f = fopen("/proc/kallsyms", "r"); char func[256], buf[256]; char symbol; void *addr; int i = 0; if (!f) return -ENOENT; while (!feof(f)) { if (!fgets(buf, sizeof(buf), f)) break; if (sscanf(buf, "%p %c %s", &addr, &symbol, func) != 3) break; if (!addr) continue; syms[i].addr = (long) addr; syms[i].name = strdup(func); i++; } sym_cnt = i; qsort(syms, sym_cnt, sizeof(struct ksym), ksym_cmp); return 0; }

Contributors

PersonTokensPropCommitsCommitProp
Yonghong Song151100.00%1100.00%
Total151100.00%1100.00%


struct ksym *ksym_search(long key) { int start = 0, end = sym_cnt; int result; while (start < end) { size_t mid = start + (end - start) / 2; result = key - syms[mid].addr; if (result < 0) end = mid; else if (result > 0) start = mid + 1; else return &syms[mid]; } if (start >= 1 && syms[start - 1].addr < key && key < syms[start].addr) /* valid ksym */ return &syms[start - 1]; /* out of range. return _stext */ return &syms[0]; }

Contributors

PersonTokensPropCommitsCommitProp
Yonghong Song129100.00%1100.00%
Total129100.00%1100.00%


long ksym_get_addr(const char *name) { int i; for (i = 0; i < sym_cnt; i++) { if (strcmp(syms[i].name, name) == 0) return syms[i].addr; } return 0; }

Contributors

PersonTokensPropCommitsCommitProp
Yonghong Song55100.00%1100.00%
Total55100.00%1100.00%

static int page_size; static int page_cnt = 8; static struct perf_event_mmap_page *header;
int perf_event_mmap(int fd) { void *base; int mmap_size; page_size = getpagesize(); mmap_size = page_size * (page_cnt + 1); base = mmap(NULL, mmap_size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); if (base == MAP_FAILED) { printf("mmap err\n"); return -1; } header = base; return 0; }

Contributors

PersonTokensPropCommitsCommitProp
Yonghong Song73100.00%1100.00%
Total73100.00%1100.00%


static int perf_event_poll(int fd) { struct pollfd pfd = { .fd = fd, .events = POLLIN }; return poll(&pfd, 1, 1000); }

Contributors

PersonTokensPropCommitsCommitProp
Yonghong Song36100.00%1100.00%
Total36100.00%1100.00%

struct perf_event_sample { struct perf_event_header header; __u32 size; char data[]; };
static enum bpf_perf_event_ret bpf_perf_event_print(void *event, void *priv) { struct perf_event_sample *e = event; perf_event_print_fn fn = priv; int ret; if (e->header.type == PERF_RECORD_SAMPLE) { ret = fn(e->data, e->size); if (ret != LIBBPF_PERF_EVENT_CONT) return ret; } else if (e->header.type == PERF_RECORD_LOST) { struct { struct perf_event_header header; __u64 id; __u64 lost; } *lost = (void *) e; printf("lost %lld events\n", lost->lost); } else { printf("unknown event type=%d size=%d\n", e->header.type, e->header.size); } return LIBBPF_PERF_EVENT_CONT; }

Contributors

PersonTokensPropCommitsCommitProp
Yonghong Song11386.26%150.00%
Jakub Kiciński1813.74%150.00%
Total131100.00%2100.00%


int perf_event_poller(int fd, perf_event_print_fn output_fn) { enum bpf_perf_event_ret ret; void *buf = NULL; size_t len = 0; for (;;) { perf_event_poll(fd); ret = bpf_perf_event_read_simple(header, page_cnt * page_size, page_size, &buf, &len, bpf_perf_event_print, output_fn); if (ret != LIBBPF_PERF_EVENT_CONT) break; } free(buf); return ret; }

Contributors

PersonTokensPropCommitsCommitProp
Yonghong Song3850.00%150.00%
Jakub Kiciński3850.00%150.00%
Total76100.00%2100.00%


Overall Contributors

PersonTokensPropCommitsCommitProp
Yonghong Song71392.72%266.67%
Jakub Kiciński567.28%133.33%
Total769100.00%3100.00%
Information contained on this website is for historical information purposes only and does not indicate or represent copyright ownership.
Created with cregit.