Blame SOURCES/bcc-0.24.0-libbpf-Allow-kernel_struct_has_field-to-reach-field-.patch

20d482
From e9ae2826b8712d491362771233ed6bf21ae1a07a Mon Sep 17 00:00:00 2001
20d482
From: Jerome Marchand <jmarchan@redhat.com>
20d482
Date: Thu, 19 May 2022 16:37:40 +0200
20d482
Subject: [PATCH 3/3] libbpf: Allow kernel_struct_has_field to reach field in
20d482
 unnamed struct or union
20d482
20d482
Some field can belong to unnamed struct or union. In C, they are
20d482
accessed as if their belong directly to the parent struct or union but
20d482
this is not the case for BTF.
20d482
20d482
When looking for a field, kernel_struct_has_field should also look
20d482
reccursively into unnamed structs or unions.
20d482
---
20d482
 src/cc/libbpf.c | 28 ++++++++++++++++++----------
20d482
 1 file changed, 18 insertions(+), 10 deletions(-)
20d482
20d482
diff --git a/src/cc/libbpf.c b/src/cc/libbpf.c
20d482
index 7410ae1a..e98b8852 100644
20d482
--- a/src/cc/libbpf.c
20d482
+++ b/src/cc/libbpf.c
20d482
@@ -1302,12 +1302,27 @@ bool bpf_has_kernel_btf(void)
20d482
   return true;
20d482
 }
20d482
 
20d482
+static int find_member_by_name(struct btf *btf, const struct btf_type *btf_type, const char *field_name) {
20d482
+  const struct btf_member *btf_member = btf_members(btf_type);
20d482
+  int i;
20d482
+
20d482
+  for (i = 0; i < btf_vlen(btf_type); i++, btf_member++) {
20d482
+    const char *name = btf__name_by_offset(btf, btf_member->name_off);
20d482
+    if (!strcmp(name, field_name)) {
20d482
+      return 1;
20d482
+    } else if (name[0] == '\0') {
20d482
+      if (find_member_by_name(btf, btf__type_by_id(btf, btf_member->type), field_name))
20d482
+        return 1;
20d482
+    }
20d482
+  }
20d482
+  return 0;
20d482
+}
20d482
+
20d482
 int kernel_struct_has_field(const char *struct_name, const char *field_name)
20d482
 {
20d482
   const struct btf_type *btf_type;
20d482
-  const struct btf_member *btf_member;
20d482
   struct btf *btf;
20d482
-  int i, ret, btf_id;
20d482
+  int ret, btf_id;
20d482
 
20d482
   btf = libbpf_find_kernel_btf();
20d482
   ret = libbpf_get_error(btf);
20d482
@@ -1321,14 +1336,7 @@ int kernel_struct_has_field(const char *struct_name, const char *field_name)
20d482
   }
20d482
 
20d482
   btf_type = btf__type_by_id(btf, btf_id);
20d482
-  btf_member = btf_members(btf_type);
20d482
-  for (i = 0; i < btf_vlen(btf_type); i++, btf_member++) {
20d482
-    if (!strcmp(btf__name_by_offset(btf, btf_member->name_off), field_name)) {
20d482
-      ret = 1;
20d482
-      goto cleanup;
20d482
-    }
20d482
-  }
20d482
-  ret = 0;
20d482
+  ret = find_member_by_name(btf, btf_type, field_name);
20d482
 
20d482
 cleanup:
20d482
   btf__free(btf);
20d482
-- 
20d482
2.35.3
20d482