From baf15e8f960f4c5edde74d87d9dcc5b2b97deaac Mon Sep 17 00:00:00 2001 From: Luis Gerhorst <privat@luisgerhorst.de> Date: Sat, 15 May 2021 17:01:20 +0200 Subject: [PATCH] filter_magic += write, iter, open, read --- libbpf | 2 +- src/task_filter_magic.bpf.c | 51 +++++++++++++------------------------ src/task_filter_magic.c | 36 ++++++++++++++++---------- src/task_filter_magic.h | 9 +++++-- src/task_lib.bpf.h | 28 ++++++++++++++++++-- 5 files changed, 74 insertions(+), 52 deletions(-) diff --git a/libbpf b/libbpf index 2e3baf6..3341a4e 160000 --- a/libbpf +++ b/libbpf @@ -1 +1 @@ -Subproject commit 2e3baf61a6178304ceb1e670910da67c8c239eda +Subproject commit 3341a4e49443c98dc5c058d2793ab8897cabe52d diff --git a/src/task_filter_magic.bpf.c b/src/task_filter_magic.bpf.c index f11fcd8..f1c3b12 100644 --- a/src/task_filter_magic.bpf.c +++ b/src/task_filter_magic.bpf.c @@ -15,13 +15,6 @@ char LICENSE[] SEC("license") = "Dual BSD/GPL"; -struct bpf_map_def SEC("maps") args = { - .type = BPF_MAP_TYPE_HASH, - .key_size = sizeof(uint32_t), - .value_size = sizeof(size_t), - .max_entries = 1, -}; - size_t offset; size_t magic_size; uintptr_t u_pathbufs; @@ -29,39 +22,33 @@ uintptr_t u_bpfmem; uintptr_t u_buf; uintptr_t u_magic; uintptr_t u_statbuf; +uintptr_t u_newline; SEC("task") int entry(void *ctx) { int err = 0; - /* struct stat *statbuf = bpf_task_map(sizeof(struct stat), u_statbuf); */ - /* if (statbuf == NULL) { */ - /* bpf_printk("Error: buf is NULL"); */ - /* return -1; */ - /* } */ - - struct bpfmem *bpfmem; + volatile struct bpfmem *bpfmem; bpfmem = bpf_task_map(sizeof(struct bpfmem), u_bpfmem); if (bpfmem == NULL) { - bpf_printk("Error: bpfmem is NULL"); - err = -1; + err = -6; goto end; } + if (bpfmem->bpfmem_magic != sizeof(struct bpfmem)) { + err = -7; + goto unmap; + } char *magic = &bpfmem->magic[0]; char *buf = &bpfmem->buf[0]; - struct stat *statbuf = &bpfmem->statbuf; - - goto unmap; - /* size_t burst_size = bpf_map_lookup_elem(args, 0); */ - for (size_t i = 0; i < MAX_BURST_SIZE; i++) { + for (size_t i = 0; i < MAX_BURST_SIZE && i < bpfmem->burst_size; i++) { uintptr_t u_pathbuf = u_pathbufs + i * MAX_PATHLEN; - int fd = open((char *) u_pathbuf, O_RDONLY); + int fd = open(u_pathbuf, O_RDONLY, 0777); if (fd == -1) { - err = -3; + err = -2; goto unmap; } @@ -84,27 +71,25 @@ int entry(void *ctx) ssize_t nread = read(fd, u_buf, magic_size-1); if (nread == -1) { - err = -1; + err = -3; goto unmap; } if (nread < magic_size-1) { - err = -2; - goto unmap; + goto close; } - /* if (strcmp(magic, buf) == 0) { */ - /* printf("%s\n", u_pathbuf); */ - /* } */ + if (magic[0] == buf[0]) { + write(STDOUT_FILENO, u_pathbuf, bpfmem->pathbuf_strlen[i]); + write(STDOUT_FILENO, u_newline, 1); + } close: - err = close(fd); - if (err) { - goto unmap; - } + close(fd); } unmap: bpf_task_unmap(bpfmem, sizeof(struct bpfmem)); end: + bpf_printk("Info: err = %d", err); return err; } diff --git a/src/task_filter_magic.c b/src/task_filter_magic.c index 9572636..9e183b9 100644 --- a/src/task_filter_magic.c +++ b/src/task_filter_magic.c @@ -402,10 +402,18 @@ static int filter_magic_user_burst(size_t offset, const char *magic, size_t max_ } } +static volatile struct bpfmem bpfmem = {}; + static int filter_magic_bpf(size_t offset, const char *magic_argv, size_t max_burst_size) { int err; int ret = EXIT_SUCCESS; + size_t magic_size = strlen(magic_argv) + 1; + if (magic_size > MAX_MAGIC_SIZE) { + log_err("magic too long"); + return EXIT_FAILURE; + } + struct NAME_BPF *skel; /* Set up libbpf errors and debug info callback */ @@ -423,13 +431,7 @@ static int filter_magic_bpf(size_t offset, const char *magic_argv, size_t max_bu char pathbufs[max_burst_size][MAX_PATHLEN]; - /* TODO: use struct mem */ - struct bpfmem bpfmem; - size_t magic_size = strlen(magic_argv) + 1; - if (magic_size > MAX_MAGIC_SIZE) { - log_err("magic too long"); - return EXIT_FAILURE; - } + bpfmem.bpfmem_magic = sizeof(struct bpfmem); bpfmem.buf[magic_size-1] = '\0'; strcpy(&bpfmem.magic[0], magic_argv); @@ -440,12 +442,13 @@ static int filter_magic_bpf(size_t offset, const char *magic_argv, size_t max_bu skel->bss->u_bpfmem = &bpfmem; skel->bss->u_buf = &bpfmem.buf[0]; skel->bss->u_magic = &bpfmem.magic[0]; - skel->bss->u_statbuf = &bpfmem.statbuf; + skel->bss->u_newline = "\n"; /* Load & verify BPF programs */ err = BPF_LOAD(skel); if (err) { fprintf(stderr, "Failed to load and verify BPF skeleton\n"); + ret = EXIT_FAILURE; goto destroy; } @@ -460,7 +463,8 @@ static int filter_magic_bpf(size_t offset, const char *magic_argv, size_t max_bu if (ptr == NULL) { if (ferror(stdin)) { log_err("fgets(stdin) failed"); - return EXIT_FAILURE; + ret = EXIT_FAILURE; + goto destroy; } else { log_debug("EOF reached"); eof = true; @@ -469,16 +473,20 @@ static int filter_magic_bpf(size_t offset, const char *magic_argv, size_t max_bu } /* Line must end with a newline. */ - if (pathbuf[strlen(pathbuf)-1] == '\n') { - pathbuf[strlen(pathbuf)-1] = '\0'; + size_t len = strlen(pathbuf); + if (pathbuf[len-1] == '\n') { + pathbuf[len-1] = '\0'; } else { log_err("line too long / no newline"); ret = EXIT_FAILURE; goto destroy; } + + bpfmem.pathbuf_strlen[burst_size] = len-1; + log_debug("i=%llu, len=%llu", burst_size, len); } + bpfmem.burst_size = burst_size; - /* TODO: pass burst_size to bpf */ err = syscall(SYS_bpftask, prog_fd, NULL); if (err) { log_err("sys_bpftaks = %d", err); @@ -495,10 +503,10 @@ destroy: int main(int argc, char **argv) { bool debug = false; - char *variant; + char *variant = "bpf"; size_t max_burst_size = 1024; /* 32k l1d, 256k l2, 4096k l3 */ size_t offset = 0; - char *magic; + char *magic = ""; int c; opterr = 0; diff --git a/src/task_filter_magic.h b/src/task_filter_magic.h index fd44904..18cd28a 100644 --- a/src/task_filter_magic.h +++ b/src/task_filter_magic.h @@ -5,10 +5,15 @@ #define MAX_PATHLEN 512 #define MAX_BURST_SIZE 1024 -struct bpfmem { +#define __packed __attribute__((__packed__)) + +struct __packed __attribute__((__aligned__(4096))) bpfmem { + size_t bpfmem_magic; char buf[MAX_MAGIC_SIZE]; char magic[MAX_MAGIC_SIZE]; - struct stat statbuf; + size_t burst_size; + size_t pathbuf_strlen[MAX_BURST_SIZE]; + /* struct stat statbuf; */ }; #endif // __TASK_BULK_H_ diff --git a/src/task_lib.bpf.h b/src/task_lib.bpf.h index 28d53ae..bd17b01 100644 --- a/src/task_lib.bpf.h +++ b/src/task_lib.bpf.h @@ -26,6 +26,10 @@ typedef __u64 ino64_t; typedef __u64 off64_t; typedef off64_t off_t; +#define STDIN_FILENO 0 +#define STDOUT_FILENO 1 +#define STDERR_FILENO 2 + /* Copied from man getdents64(2). */ struct linux_dirent64 { ino64_t d_ino; /* 64-bit inode number */ @@ -45,6 +49,7 @@ struct timespec { }; /* fstat(2) */ +/* TODO: fix */ typedef int dev_t; typedef int ino_t; typedef int mode_t; @@ -84,6 +89,21 @@ static char *strncpy(char *dest, const char *src, size_t n) { return dest; } +static int strncmp(const char *s1, const char *s2, size_t n) { + size_t i; + for (i = 0; i < n; i++) { + if (!s1[i] || s1[i] != s2[i]) { + break; + } + } + + if (n == i) { + return 0; + } else { + return (unsigned char) s1[i] - (unsigned char) s2[i]; + } +} + static void *mmap(void *addr, size_t length, int prot, int flags, int fd, off_t offset) { uint64_t arg_tail[3] = {flags, fd, offset}; return (void *) bpf_task_sys_mmap_6((uint64_t) addr, length, prot, arg_tail, sizeof(arg_tail)); @@ -93,14 +113,18 @@ static int nanosleep(const struct timespec *req, struct timespec *rem) { return (int) bpf_task_sys_nanosleep_2((uint64_t) req, (uint64_t) rem); } -static int open(const char *pathname, int flags) { - return (int) bpf_task_sys_open_2((uint64_t) pathname, flags); +static int open(uintptr_t pathname, int flags, mode_t mode) { + return (int) bpf_task_sys_open_3((uint64_t) pathname, flags, mode); } static ssize_t read(int fd, void *buf, size_t count) { return (ssize_t) bpf_task_sys_read_3(fd, (uint64_t) buf, count); } +static ssize_t write(int fd, void *buf, size_t count) { + return (ssize_t) bpf_task_sys_write_3(fd, (uint64_t) buf, count); +} + static int close(int fd) { return (int) bpf_task_sys_close_1(fd); } -- GitLab