]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
libbpf: Introduce kflag for type_tags and decl_tags in BTF
authorIhor Solodrai <ihor.solodrai@linux.dev>
Thu, 30 Jan 2025 20:12:34 +0000 (12:12 -0800)
committerAndrii Nakryiko <andrii@kernel.org>
Thu, 6 Feb 2025 00:17:59 +0000 (16:17 -0800)
Add the following functions to libbpf API:
  * btf__add_type_attr()
  * btf__add_decl_attr()

These functions allow to add to BTF the type tags and decl tags with
info->kflag set to 1. The kflag indicates that the tag directly
encodes an __attribute__ and not a normal tag.

See Documentation/bpf/btf.rst changes in the subsequent patch for
details on the semantics.

Suggested-by: Andrii Nakryiko <andrii@kernel.org>
Signed-off-by: Ihor Solodrai <ihor.solodrai@linux.dev>
Signed-off-by: Andrii Nakryiko <andrii@kernel.org>
Reviewed-by: Alan Maguire <alan.maguire@oracle.com>
Acked-by: Andrii Nakryiko <andrii@kernel.org>
Link: https://lore.kernel.org/bpf/20250130201239.1429648-2-ihor.solodrai@linux.dev
tools/lib/bpf/btf.c
tools/lib/bpf/btf.h
tools/lib/bpf/libbpf.map

index 560b519f820e24ea4b60453b85fdd6398cae4d0c..eea99c766a2078df5f84ee61df299a5862f745b3 100644 (file)
@@ -2090,7 +2090,7 @@ static int validate_type_id(int id)
 }
 
 /* generic append function for PTR, TYPEDEF, CONST/VOLATILE/RESTRICT */
-static int btf_add_ref_kind(struct btf *btf, int kind, const char *name, int ref_type_id)
+static int btf_add_ref_kind(struct btf *btf, int kind, const char *name, int ref_type_id, int kflag)
 {
        struct btf_type *t;
        int sz, name_off = 0;
@@ -2113,7 +2113,7 @@ static int btf_add_ref_kind(struct btf *btf, int kind, const char *name, int ref
        }
 
        t->name_off = name_off;
-       t->info = btf_type_info(kind, 0, 0);
+       t->info = btf_type_info(kind, 0, kflag);
        t->type = ref_type_id;
 
        return btf_commit_type(btf, sz);
@@ -2128,7 +2128,7 @@ static int btf_add_ref_kind(struct btf *btf, int kind, const char *name, int ref
  */
 int btf__add_ptr(struct btf *btf, int ref_type_id)
 {
-       return btf_add_ref_kind(btf, BTF_KIND_PTR, NULL, ref_type_id);
+       return btf_add_ref_kind(btf, BTF_KIND_PTR, NULL, ref_type_id, 0);
 }
 
 /*
@@ -2506,7 +2506,7 @@ int btf__add_fwd(struct btf *btf, const char *name, enum btf_fwd_kind fwd_kind)
                struct btf_type *t;
                int id;
 
-               id = btf_add_ref_kind(btf, BTF_KIND_FWD, name, 0);
+               id = btf_add_ref_kind(btf, BTF_KIND_FWD, name, 0, 0);
                if (id <= 0)
                        return id;
                t = btf_type_by_id(btf, id);
@@ -2536,7 +2536,7 @@ int btf__add_typedef(struct btf *btf, const char *name, int ref_type_id)
        if (!name || !name[0])
                return libbpf_err(-EINVAL);
 
-       return btf_add_ref_kind(btf, BTF_KIND_TYPEDEF, name, ref_type_id);
+       return btf_add_ref_kind(btf, BTF_KIND_TYPEDEF, name, ref_type_id, 0);
 }
 
 /*
@@ -2548,7 +2548,7 @@ int btf__add_typedef(struct btf *btf, const char *name, int ref_type_id)
  */
 int btf__add_volatile(struct btf *btf, int ref_type_id)
 {
-       return btf_add_ref_kind(btf, BTF_KIND_VOLATILE, NULL, ref_type_id);
+       return btf_add_ref_kind(btf, BTF_KIND_VOLATILE, NULL, ref_type_id, 0);
 }
 
 /*
@@ -2560,7 +2560,7 @@ int btf__add_volatile(struct btf *btf, int ref_type_id)
  */
 int btf__add_const(struct btf *btf, int ref_type_id)
 {
-       return btf_add_ref_kind(btf, BTF_KIND_CONST, NULL, ref_type_id);
+       return btf_add_ref_kind(btf, BTF_KIND_CONST, NULL, ref_type_id, 0);
 }
 
 /*
@@ -2572,7 +2572,7 @@ int btf__add_const(struct btf *btf, int ref_type_id)
  */
 int btf__add_restrict(struct btf *btf, int ref_type_id)
 {
-       return btf_add_ref_kind(btf, BTF_KIND_RESTRICT, NULL, ref_type_id);
+       return btf_add_ref_kind(btf, BTF_KIND_RESTRICT, NULL, ref_type_id, 0);
 }
 
 /*
@@ -2588,7 +2588,24 @@ int btf__add_type_tag(struct btf *btf, const char *value, int ref_type_id)
        if (!value || !value[0])
                return libbpf_err(-EINVAL);
 
-       return btf_add_ref_kind(btf, BTF_KIND_TYPE_TAG, value, ref_type_id);
+       return btf_add_ref_kind(btf, BTF_KIND_TYPE_TAG, value, ref_type_id, 0);
+}
+
+/*
+ * Append new BTF_KIND_TYPE_TAG type with:
+ *   - *value*, non-empty/non-NULL tag value;
+ *   - *ref_type_id* - referenced type ID, it might not exist yet;
+ * Set info->kflag to 1, indicating this tag is an __attribute__
+ * Returns:
+ *   - >0, type ID of newly added BTF type;
+ *   - <0, on error.
+ */
+int btf__add_type_attr(struct btf *btf, const char *value, int ref_type_id)
+{
+       if (!value || !value[0])
+               return libbpf_err(-EINVAL);
+
+       return btf_add_ref_kind(btf, BTF_KIND_TYPE_TAG, value, ref_type_id, 1);
 }
 
 /*
@@ -2610,7 +2627,7 @@ int btf__add_func(struct btf *btf, const char *name,
            linkage != BTF_FUNC_EXTERN)
                return libbpf_err(-EINVAL);
 
-       id = btf_add_ref_kind(btf, BTF_KIND_FUNC, name, proto_type_id);
+       id = btf_add_ref_kind(btf, BTF_KIND_FUNC, name, proto_type_id, 0);
        if (id > 0) {
                struct btf_type *t = btf_type_by_id(btf, id);
 
@@ -2845,18 +2862,8 @@ int btf__add_datasec_var_info(struct btf *btf, int var_type_id, __u32 offset, __
        return 0;
 }
 
-/*
- * Append new BTF_KIND_DECL_TAG type with:
- *   - *value* - non-empty/non-NULL string;
- *   - *ref_type_id* - referenced type ID, it might not exist yet;
- *   - *component_idx* - -1 for tagging reference type, otherwise struct/union
- *     member or function argument index;
- * Returns:
- *   - >0, type ID of newly added BTF type;
- *   - <0, on error.
- */
-int btf__add_decl_tag(struct btf *btf, const char *value, int ref_type_id,
-                int component_idx)
+static int btf_add_decl_tag(struct btf *btf, const char *value, int ref_type_id,
+                           int component_idx, int kflag)
 {
        struct btf_type *t;
        int sz, value_off;
@@ -2880,13 +2887,46 @@ int btf__add_decl_tag(struct btf *btf, const char *value, int ref_type_id,
                return value_off;
 
        t->name_off = value_off;
-       t->info = btf_type_info(BTF_KIND_DECL_TAG, 0, false);
+       t->info = btf_type_info(BTF_KIND_DECL_TAG, 0, kflag);
        t->type = ref_type_id;
        btf_decl_tag(t)->component_idx = component_idx;
 
        return btf_commit_type(btf, sz);
 }
 
+/*
+ * Append new BTF_KIND_DECL_TAG type with:
+ *   - *value* - non-empty/non-NULL string;
+ *   - *ref_type_id* - referenced type ID, it might not exist yet;
+ *   - *component_idx* - -1 for tagging reference type, otherwise struct/union
+ *     member or function argument index;
+ * Returns:
+ *   - >0, type ID of newly added BTF type;
+ *   - <0, on error.
+ */
+int btf__add_decl_tag(struct btf *btf, const char *value, int ref_type_id,
+                     int component_idx)
+{
+       return btf_add_decl_tag(btf, value, ref_type_id, component_idx, 0);
+}
+
+/*
+ * Append new BTF_KIND_DECL_TAG type with:
+ *   - *value* - non-empty/non-NULL string;
+ *   - *ref_type_id* - referenced type ID, it might not exist yet;
+ *   - *component_idx* - -1 for tagging reference type, otherwise struct/union
+ *     member or function argument index;
+ * Set info->kflag to 1, indicating this tag is an __attribute__
+ * Returns:
+ *   - >0, type ID of newly added BTF type;
+ *   - <0, on error.
+ */
+int btf__add_decl_attr(struct btf *btf, const char *value, int ref_type_id,
+                      int component_idx)
+{
+       return btf_add_decl_tag(btf, value, ref_type_id, component_idx, 1);
+}
+
 struct btf_ext_sec_info_param {
        __u32 off;
        __u32 len;
index 47ee8f6ac489617a1425697a6177c432b91c7eb2..4392451d634bdf7a158a904a7b0c6e31f5cd643b 100644 (file)
@@ -227,6 +227,7 @@ LIBBPF_API int btf__add_volatile(struct btf *btf, int ref_type_id);
 LIBBPF_API int btf__add_const(struct btf *btf, int ref_type_id);
 LIBBPF_API int btf__add_restrict(struct btf *btf, int ref_type_id);
 LIBBPF_API int btf__add_type_tag(struct btf *btf, const char *value, int ref_type_id);
+LIBBPF_API int btf__add_type_attr(struct btf *btf, const char *value, int ref_type_id);
 
 /* func and func_proto construction APIs */
 LIBBPF_API int btf__add_func(struct btf *btf, const char *name,
@@ -243,6 +244,8 @@ LIBBPF_API int btf__add_datasec_var_info(struct btf *btf, int var_type_id,
 /* tag construction API */
 LIBBPF_API int btf__add_decl_tag(struct btf *btf, const char *value, int ref_type_id,
                            int component_idx);
+LIBBPF_API int btf__add_decl_attr(struct btf *btf, const char *value, int ref_type_id,
+                                 int component_idx);
 
 struct btf_dedup_opts {
        size_t sz;
index a8b2936a164668ca3c662d7251233e3763b97b6d..b5a838de6f47c1c51b56c52fa913443652a9dbdd 100644 (file)
@@ -436,4 +436,6 @@ LIBBPF_1.6.0 {
                bpf_linker__add_buf;
                bpf_linker__add_fd;
                bpf_linker__new_fd;
+               btf__add_decl_attr;
+               btf__add_type_attr;
 } LIBBPF_1.5.0;