summaryrefslogtreecommitdiffstats
path: root/libnetdata/ebpf
diff options
context:
space:
mode:
Diffstat (limited to 'libnetdata/ebpf')
-rw-r--r--libnetdata/ebpf/ebpf.c99
-rw-r--r--libnetdata/ebpf/ebpf.h25
2 files changed, 112 insertions, 12 deletions
diff --git a/libnetdata/ebpf/ebpf.c b/libnetdata/ebpf/ebpf.c
index a9ff21f69..8619ae26f 100644
--- a/libnetdata/ebpf/ebpf.c
+++ b/libnetdata/ebpf/ebpf.c
@@ -8,6 +8,9 @@
#include "../libnetdata.h"
+char *ebpf_user_config_dir = CONFIG_DIR;
+char *ebpf_stock_config_dir = LIBCONFIG_DIR;
+
/*
static int clean_kprobe_event(FILE *out, char *filename, char *father_pid, netdata_ebpf_events_t *ptr)
{
@@ -97,7 +100,7 @@ int get_kernel_version(char *out, int size)
return -1;
move = patch;
- while (*version && *version != '\n')
+ while (*version && *version != '\n' && *version != '-')
*move++ = *version++;
*move = '\0';
@@ -182,20 +185,26 @@ static int kernel_is_rejected()
}
char filename[FILENAME_MAX + 1];
- snprintfz(filename, FILENAME_MAX, "%s/%s", config_dir, EBPF_KERNEL_REJECT_LIST_FILE);
+ snprintfz(filename, FILENAME_MAX, "%s/ebpf.d/%s", config_dir, EBPF_KERNEL_REJECT_LIST_FILE);
FILE *kernel_reject_list = fopen(filename, "r");
if (!kernel_reject_list) {
- config_dir = getenv("NETDATA_STOCK_CONFIG_DIR");
- if (config_dir == NULL) {
- config_dir = LIBCONFIG_DIR;
- }
-
+ // Keep this to have compatibility with old versions
snprintfz(filename, FILENAME_MAX, "%s/%s", config_dir, EBPF_KERNEL_REJECT_LIST_FILE);
kernel_reject_list = fopen(filename, "r");
- if (!kernel_reject_list)
- return 0;
+ if (!kernel_reject_list) {
+ config_dir = getenv("NETDATA_STOCK_CONFIG_DIR");
+ if (config_dir == NULL) {
+ config_dir = LIBCONFIG_DIR;
+ }
+
+ snprintfz(filename, FILENAME_MAX, "%s/ebpf.d/%s", config_dir, EBPF_KERNEL_REJECT_LIST_FILE);
+ kernel_reject_list = fopen(filename, "r");
+
+ if (!kernel_reject_list)
+ return 0;
+ }
}
// Find if the kernel is in the reject list
@@ -246,7 +255,9 @@ char *ebpf_kernel_suffix(int version, int isrh)
else
return "3.10";
} else {
- if (version >= NETDATA_EBPF_KERNEL_5_10)
+ if (version >= NETDATA_EBPF_KERNEL_5_11)
+ return "5.11";
+ else if (version >= NETDATA_EBPF_KERNEL_5_10)
return "5.10";
else if (version >= NETDATA_EBPF_KERNEL_4_17)
return "5.4";
@@ -294,8 +305,10 @@ struct bpf_link **ebpf_load_program(char *plugins_dir, ebpf_module_t *em, char *
if (test < 0 || test > 127)
return NULL;
- snprintf(lpath, 4096, "%s/%s", plugins_dir, lname);
- if (bpf_prog_load(lpath, BPF_PROG_TYPE_KPROBE, obj, &prog_fd)) {
+ snprintf(lpath, 4096, "%s/ebpf.d/%s", plugins_dir, lname);
+ // We are using BPF_PROG_TYPE_UNSPEC instead a specific type for bpf_prog_load to define the type
+ // according the eBPF program loaded
+ if (bpf_prog_load(lpath, BPF_PROG_TYPE_UNSPEC, obj, &prog_fd)) {
em->enabled = CONFIG_BOOLEAN_NO;
info("Cannot load program: %s", lpath);
return NULL;
@@ -322,3 +335,65 @@ struct bpf_link **ebpf_load_program(char *plugins_dir, ebpf_module_t *em, char *
return links;
}
+
+//----------------------------------------------------------------------------------------------------------------------
+
+void ebpf_mount_config_name(char *filename, size_t length, char *path, char *config)
+{
+ snprintf(filename, length, "%s/ebpf.d/%s", path, config);
+}
+
+int ebpf_load_config(struct config *config, char *filename)
+{
+ return appconfig_load(config, filename, 0, NULL);
+}
+
+
+static netdata_run_mode_t ebpf_select_mode(char *mode)
+{
+ if (!strcasecmp(mode, "return"))
+ return MODE_RETURN;
+ else if (!strcasecmp(mode, "dev"))
+ return MODE_DEVMODE;
+
+ return MODE_ENTRY;
+}
+
+void ebpf_update_module_using_config(ebpf_module_t *modules, struct config *cfg)
+{
+ char *mode = appconfig_get(cfg, EBPF_GLOBAL_SECTION, EBPF_CFG_LOAD_MODE, EBPF_CFG_LOAD_MODE_DEFAULT);
+ modules->mode = ebpf_select_mode(mode);
+
+ modules->update_time = (int)appconfig_get_number(cfg, EBPF_GLOBAL_SECTION, EBPF_CFG_UPDATE_EVERY, 1);
+
+ modules->apps_charts = appconfig_get_boolean(cfg, EBPF_GLOBAL_SECTION, EBPF_CFG_APPLICATION,
+ CONFIG_BOOLEAN_YES);
+}
+
+
+/**
+ * Update module
+ *
+ * When this function is called, it will load the configuration file and after this
+ * it updates the global information of ebpf_module.
+ * If the module has specific configuration, this function will load it, but it will not
+ * update the variables.
+ *
+ * @param em the module structure
+ * @param cfg the configuration structure
+ * @param cfg_file the filename to load
+ */
+void ebpf_update_module(ebpf_module_t *em, struct config *cfg, char *cfg_file)
+{
+ char filename[FILENAME_MAX+1];
+ ebpf_mount_config_name(filename, FILENAME_MAX, ebpf_user_config_dir, cfg_file);
+ if (!ebpf_load_config(cfg, filename)) {
+ ebpf_mount_config_name(filename, FILENAME_MAX, ebpf_stock_config_dir, cfg_file);
+ if (!ebpf_load_config(cfg, filename)) {
+ error("Cannot load the ebpf configuration file %s", cfg_file);
+ return;
+ }
+ }
+
+ ebpf_update_module_using_config(em, cfg);
+}
diff --git a/libnetdata/ebpf/ebpf.h b/libnetdata/ebpf/ebpf.h
index d4faccffd..ac3a1a2fc 100644
--- a/libnetdata/ebpf/ebpf.h
+++ b/libnetdata/ebpf/ebpf.h
@@ -8,6 +8,15 @@
#define NETDATA_DEBUGFS "/sys/kernel/debug/tracing/"
+// Config files
+#define EBPF_GLOBAL_SECTION "global"
+#define EBPF_CFG_LOAD_MODE "ebpf load mode"
+#define EBPF_CFG_LOAD_MODE_DEFAULT "entry"
+#define EBPF_CFG_LOAD_MODE_RETURN "return"
+
+#define EBPF_CFG_UPDATE_EVERY "update every"
+#define EBPF_CFG_APPLICATION "apps"
+
/**
* The next magic number is got doing the following math:
* 294960 = 4*65536 + 11*256 + 0
@@ -32,6 +41,13 @@
#define NETDATA_RH_8 2048
/**
+ * Kernel 5.11
+ *
+ * 330240 = 5*65536 + 11*256
+ */
+#define NETDATA_EBPF_KERNEL_5_11 330496
+
+/**
* Kernel 5.10
*
* 330240 = 5*65536 + 10*256
@@ -62,6 +78,9 @@
#define VERSION_STRING_LEN 256
#define EBPF_KERNEL_REJECT_LIST_FILE "ebpf_kernel_reject_list.txt"
+extern char *ebpf_user_config_dir;
+extern char *ebpf_stock_config_dir;
+
typedef struct ebpf_data {
int *map_fd;
@@ -87,6 +106,7 @@ typedef struct ebpf_module {
netdata_run_mode_t mode;
uint32_t thread_id;
int optional;
+ void (*apps_routine)(struct ebpf_module *em, void *ptr);
} ebpf_module_t;
#define NETDATA_MAX_PROBES 64
@@ -102,4 +122,9 @@ extern struct bpf_link **ebpf_load_program(char *plugins_dir,
struct bpf_object **obj,
int *map_fd);
+extern void ebpf_mount_config_name(char *filename, size_t length, char *path, char *config);
+extern int ebpf_load_config(struct config *config, char *filename);
+extern void ebpf_update_module_using_config(ebpf_module_t *modules, struct config *cfg);
+extern void ebpf_update_module(ebpf_module_t *em, struct config *cfg, char *cfg_file);
+
#endif /* NETDATA_EBPF_H */