]> git.ipfire.org Git - thirdparty/util-linux.git/commitdiff
lsfd: add BPF-MAP.TYPE, BPF-MAP.TYPE.RAW, and BPF-MAP.ID columns
authorMasatake YAMATO <yamato@redhat.com>
Tue, 11 Jul 2023 13:12:05 +0000 (22:12 +0900)
committerMasatake YAMATO <yamato@redhat.com>
Mon, 18 Sep 2023 11:22:57 +0000 (20:22 +0900)
Based on these new columns, the NAME column for "bpf-map" is enhanced.

An example output:

  # ./lsfd -p 1 -Q '(TYPE == "bpf-map")' | head
  COMMAND PID USER ASSOC  XMODE    TYPE       SOURCE MNTID INODE NAME
  systemd   1 root    13 rw---- bpf-map anon_inodefs    15   106 id=305 type=hash-of-maps

Signed-off-by: Masatake YAMATO <yamato@redhat.com>
misc-utils/lsfd-unkn.c
misc-utils/lsfd.1.adoc
misc-utils/lsfd.c
misc-utils/lsfd.h

index 9cfd2bfa5771e54ce09ebedb340f4c471e95951e..4d68f4010463698fc7ca0c341a6d6131ef8953a0 100644 (file)
@@ -1127,6 +1127,152 @@ static const struct anon_ops anon_bpf_prog_ops = {
        .handle_fdinfo = anon_bpf_prog_handle_fdinfo,
 };
 
+/*
+ * bpf-map
+ */
+static const char *bpf_map_type_table[] = {
+       [0] = "unspec",           /* BPF_MAP_TYPE_UNSPEC */
+       [1] = "hash",             /* BPF_MAP_TYPE_HASH */
+       [2] = "array",            /* BPF_MAP_TYPE_ARRAY */
+       [3] = "prog-array",       /* BPF_MAP_TYPE_PROG_ARRAY */
+       [4] = "perf-event-array", /* BPF_MAP_TYPE_PERF_EVENT_ARRAY */
+       [5] = "percpu-hash",      /* BPF_MAP_TYPE_PERCPU_HASH */
+       [6] = "percpu-array",     /* BPF_MAP_TYPE_PERCPU_ARRAY */
+       [7] = "stack-trace",      /* BPF_MAP_TYPE_STACK_TRACE */
+       [8] = "cgroup-array",     /* BPF_MAP_TYPE_CGROUP_ARRAY */
+       [9] = "lru-hash",         /* BPF_MAP_TYPE_LRU_HASH */
+       [10] = "lru-percpu-hash", /* BPF_MAP_TYPE_LRU_PERCPU_HASH */
+       [11] = "lpm-trie",        /* BPF_MAP_TYPE_LPM_TRIE */
+       [12] = "array-of-maps",   /* BPF_MAP_TYPE_ARRAY_OF_MAPS */
+       [13] = "hash-of-maps",    /* BPF_MAP_TYPE_HASH_OF_MAPS */
+       [14] = "devmap",          /* BPF_MAP_TYPE_DEVMAP */
+       [15] = "sockmap",         /* BPF_MAP_TYPE_SOCKMAP */
+       [16] = "cpumap",          /* BPF_MAP_TYPE_CPUMAP */
+       [17] = "xskmap",          /* BPF_MAP_TYPE_XSKMAP */
+       [18] = "sockhash",        /* BPF_MAP_TYPE_SOCKHASH */
+       [19] = "cgroup-storage",  /* BPF_MAP_TYPE_CGROUP_STORAGE */
+       [20] = "reuseport-sockarray", /* BPF_MAP_TYPE_REUSEPORT_SOCKARRAY */
+       [21] = "percpu-cgroup-storage", /* BPF_MAP_TYPE_PERCPU_CGROUP_STORAGE */
+       [22] = "queue",                 /* BPF_MAP_TYPE_QUEUE */
+       [23] = "stack",                 /* BPF_MAP_TYPE_STACK */
+       [24] = "sk-storage",            /* BPF_MAP_TYPE_SK_STORAGE */
+       [25] = "devmap-hash",           /* BPF_MAP_TYPE_DEVMAP_HASH */
+       [26] = "struct-ops",            /* BPF_MAP_TYPE_STRUCT_OPS */
+       [27] = "ringbuf",               /* BPF_MAP_TYPE_RINGBUF */
+       [28] = "inode-storage", /* BPF_MAP_TYPE_INODE_STORAGE */
+       [29] = "task-storage",  /* BPF_MAP_TYPE_TASK_STORAGE */
+       [30] = "bloom-filter",  /* BPF_MAP_TYPE_BLOOM_FILTER */
+       [31] = "user-ringbuf",  /* BPF_MAP_TYPE_USER_RINGBUF */
+       [32] = "cgrp-storage",  /* BPF_MAP_TYPE_CGRP_STORAGE */
+};
+
+struct anon_bpf_map_data {
+       int type;
+       int id;
+};
+
+static bool anon_bpf_map_probe(const char *str)
+{
+       return strncmp(str, "bpf-map", 8) == 0;
+}
+
+static const char *anon_bpf_map_get_map_type_name(int type)
+{
+       if (0 <= type && type < (int)ARRAY_SIZE(bpf_map_type_table))
+               return bpf_map_type_table[type];
+       return NULL;
+}
+
+static bool anon_bpf_map_fill_column(struct proc *proc  __attribute__((__unused__)),
+                                    struct unkn *unkn,
+                                    struct libscols_line *ln __attribute__((__unused__)),
+                                    int column_id,
+                                    size_t column_index __attribute__((__unused__)),
+                                    char **str)
+{
+       struct anon_bpf_prog_data *data = (struct anon_bpf_prog_data *)unkn->anon_data;
+       const char *t;
+
+       switch(column_id) {
+       case COL_BPF_MAP_ID:
+               xasprintf(str, "%d", data->id);
+               return true;
+       case COL_BPF_MAP_TYPE_RAW:
+               xasprintf(str, "%d", data->type);
+               return true;
+       case COL_BPF_MAP_TYPE:
+               t = anon_bpf_map_get_map_type_name(data->type);
+               if (t)
+                       *str = xstrdup(t);
+               else
+                       xasprintf(str, "UNKNOWN(%d)", data->type);
+               return true;
+       default:
+               return false;
+       }
+}
+
+static char *anon_bpf_map_get_name(struct unkn *unkn)
+{
+       const char *t;
+       char *str = NULL;
+       struct anon_bpf_map_data *data = (struct anon_bpf_map_data *)unkn->anon_data;
+
+       t = anon_bpf_map_get_map_type_name(data->type);
+       if (t)
+               xasprintf(&str, "id=%d type=%s", data->id, t);
+       else
+               xasprintf(&str, "id=%d type=UNKNOWN(%d)", data->id, data->type);
+       return str;
+}
+
+static void anon_bpf_map_init(struct unkn *unkn)
+{
+       struct anon_bpf_map_data *data = xmalloc(sizeof(*data));
+       data->type = -1;
+       data->id = -1;
+       unkn->anon_data = data;
+}
+
+static void anon_bpf_map_free(struct unkn *unkn)
+{
+       struct anon_bpf_map_data *data = (struct anon_bpf_map_data *)unkn->anon_data;
+       free(data);
+}
+
+static int anon_bpf_map_handle_fdinfo(struct unkn *unkn, const char *key, const char *value)
+{
+       if (strcmp(key, "map_id") == 0) {
+               int32_t t = -1;
+               int rc = ul_strtos32(value, &t, 10);
+               if (rc < 0)
+                       return 0; /* ignore -- parse failed */
+               ((struct anon_bpf_map_data *)unkn->anon_data)->id = (int)t;
+               return 1;
+       }
+
+       if (strcmp(key, "map_type") == 0) {
+               int32_t t = -1;
+               int rc = ul_strtos32(value, &t, 10);
+               if (rc < 0)
+                       return 0; /* ignore -- parse failed */
+               ((struct anon_bpf_map_data *)unkn->anon_data)->type = (int)t;
+               return 1;
+       }
+
+       return 0;
+}
+
+static const struct anon_ops anon_bpf_map_ops = {
+       .class = "bpf-map",
+       .probe = anon_bpf_map_probe,
+       .get_name = anon_bpf_map_get_name,
+       .fill_column = anon_bpf_map_fill_column,
+       .init = anon_bpf_map_init,
+       .free = anon_bpf_map_free,
+       .handle_fdinfo = anon_bpf_map_handle_fdinfo,
+};
+
 /*
  * generic (fallback implementation)
  */
@@ -1147,6 +1293,7 @@ static const struct anon_ops *anon_ops[] = {
        &anon_signalfd_ops,
        &anon_inotify_ops,
        &anon_bpf_prog_ops,
+       &anon_bpf_map_ops,
 };
 
 static const struct anon_ops *anon_probe(const char *str)
index d023801080548e15c82e71a853a921fadbef677a..d3c993777bc779e1951f2d81f90a6a6e9eefc760 100644 (file)
@@ -132,6 +132,15 @@ Association between file and process.
 BLKDRV <``string``>::
 Block device driver name resolved by `/proc/devices`.
 
+BPF-MAP.ID <``number``>::
+Bpf map ID.
+
+BPF-MAP.TYPE <``string``>::
+Decoded name of bpf map type.
+
+BPF-MAP.TYPE.RAW <``number``>::
+Bpf map type (raw).
+
 BPF-PROG.ID <``number``>::
 Bpf program ID.
 
@@ -250,6 +259,9 @@ Cooked version of KNAME. It is mostly same as KNAME.
 +
 Some files have special formats and information sources:
 +
+bpf-map:::
+id=_BPF-MAP.ID_ type=_BPF-MAP.TYPE_
++
 bpf-prog:::
 id=_BPF-PROG.ID_ type=_BPF-PROG.TYPE_
 +
index 0aaf18f12f353af421c6fae963c7344d1a4abd91..39b50d8f102da65438b444564348eb209282fcab 100644 (file)
@@ -128,6 +128,15 @@ static const struct colinfo infos[] = {
        [COL_BLKDRV]           = { "BLKDRV",
                                   0,   SCOLS_FL_RIGHT, SCOLS_JSON_STRING,
                                   N_("block device driver name resolved by /proc/devices") },
+       [COL_BPF_MAP_ID]       = { "BPF-MAP.ID",
+                                  0,   SCOLS_FL_RIGHT, SCOLS_JSON_NUMBER,
+                                  N_("bpf map id associated with the fd") },
+       [COL_BPF_MAP_TYPE]     = { "BPF-MAP.TYPE",
+                                  0,   SCOLS_FL_RIGHT, SCOLS_JSON_STRING,
+                                  N_("bpf map type (decoded)") },
+       [COL_BPF_MAP_TYPE_RAW]= { "BPF-MAP.TYPE.RAW",
+                                  0,   SCOLS_FL_RIGHT, SCOLS_JSON_NUMBER,
+                                  N_("bpf map type (raw)") },
        [COL_BPF_PROG_ID]      = { "BPF-PROG.ID",
                                   0,   SCOLS_FL_RIGHT, SCOLS_JSON_NUMBER,
                                   N_("bpf program id associated with the fd") },
index a7396bddfda75efac1169b7f5b63ec937deb1c46..7a5034e255459434444aeb89b0babd041e1c7747 100644 (file)
@@ -43,6 +43,9 @@ enum {
        COL_AINODECLASS,
        COL_ASSOC,
        COL_BLKDRV,
+       COL_BPF_MAP_ID,
+       COL_BPF_MAP_TYPE,
+       COL_BPF_MAP_TYPE_RAW,
        COL_BPF_PROG_ID,
        COL_BPF_PROG_TYPE,
        COL_BPF_PROG_TYPE_RAW,