^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) /* SPDX-License-Identifier: GPL-2.0 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /* Copyright (c) 2018 Facebook */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) #include <uapi/linux/btf.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) #include <uapi/linux/bpf.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) #include <uapi/linux/bpf_perf_event.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) #include <uapi/linux/types.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) #include <linux/seq_file.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #include <linux/compiler.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <linux/ctype.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <linux/errno.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/anon_inodes.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <linux/file.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) #include <linux/uaccess.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include <linux/idr.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) #include <linux/sort.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #include <linux/bpf_verifier.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) #include <linux/btf.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) #include <linux/btf_ids.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) #include <linux/skmsg.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) #include <linux/perf_event.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) #include <linux/bsearch.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) #include <linux/btf_ids.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) #include <net/sock.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) /* BTF (BPF Type Format) is the meta data format which describes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) * the data types of BPF program/map. Hence, it basically focus
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) * on the C programming language which the modern BPF is primary
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) * using.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) * ELF Section:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) * ~~~~~~~~~~~
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) * The BTF data is stored under the ".BTF" ELF section
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) * struct btf_type:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) * ~~~~~~~~~~~~~~~
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) * Each 'struct btf_type' object describes a C data type.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) * Depending on the type it is describing, a 'struct btf_type'
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) * object may be followed by more data. F.e.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) * To describe an array, 'struct btf_type' is followed by
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) * 'struct btf_array'.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) * 'struct btf_type' and any extra data following it are
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) * 4 bytes aligned.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) * Type section:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) * ~~~~~~~~~~~~~
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) * The BTF type section contains a list of 'struct btf_type' objects.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) * Each one describes a C type. Recall from the above section
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) * that a 'struct btf_type' object could be immediately followed by extra
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) * data in order to desribe some particular C types.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) * type_id:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) * ~~~~~~~
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) * Each btf_type object is identified by a type_id. The type_id
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) * is implicitly implied by the location of the btf_type object in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) * the BTF type section. The first one has type_id 1. The second
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) * one has type_id 2...etc. Hence, an earlier btf_type has
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) * a smaller type_id.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) * A btf_type object may refer to another btf_type object by using
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) * type_id (i.e. the "type" in the "struct btf_type").
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) * NOTE that we cannot assume any reference-order.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) * A btf_type object can refer to an earlier btf_type object
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) * but it can also refer to a later btf_type object.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) * For example, to describe "const void *". A btf_type
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) * object describing "const" may refer to another btf_type
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) * object describing "void *". This type-reference is done
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) * by specifying type_id:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) * [1] CONST (anon) type_id=2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) * [2] PTR (anon) type_id=0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) * The above is the btf_verifier debug log:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) * - Each line started with "[?]" is a btf_type object
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) * - [?] is the type_id of the btf_type object.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) * - CONST/PTR is the BTF_KIND_XXX
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) * - "(anon)" is the name of the type. It just
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) * happens that CONST and PTR has no name.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) * - type_id=XXX is the 'u32 type' in btf_type
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) * NOTE: "void" has type_id 0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) * String section:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) * ~~~~~~~~~~~~~~
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) * The BTF string section contains the names used by the type section.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) * Each string is referred by an "offset" from the beginning of the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) * string section.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) * Each string is '\0' terminated.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) * The first character in the string section must be '\0'
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) * which is used to mean 'anonymous'. Some btf_type may not
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) * have a name.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) /* BTF verification:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) * To verify BTF data, two passes are needed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) * Pass #1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) * ~~~~~~~
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) * The first pass is to collect all btf_type objects to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) * an array: "btf->types".
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) * Depending on the C type that a btf_type is describing,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) * a btf_type may be followed by extra data. We don't know
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) * how many btf_type is there, and more importantly we don't
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) * know where each btf_type is located in the type section.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) * Without knowing the location of each type_id, most verifications
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) * cannot be done. e.g. an earlier btf_type may refer to a later
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) * btf_type (recall the "const void *" above), so we cannot
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) * check this type-reference in the first pass.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) * In the first pass, it still does some verifications (e.g.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) * checking the name is a valid offset to the string section).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) * Pass #2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) * ~~~~~~~
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) * The main focus is to resolve a btf_type that is referring
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) * to another type.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) * We have to ensure the referring type:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) * 1) does exist in the BTF (i.e. in btf->types[])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) * 2) does not cause a loop:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) * struct A {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) * struct B b;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) * };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) * struct B {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) * struct A a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) * };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) * btf_type_needs_resolve() decides if a btf_type needs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) * to be resolved.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) * The needs_resolve type implements the "resolve()" ops which
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) * essentially does a DFS and detects backedge.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) * During resolve (or DFS), different C types have different
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) * "RESOLVED" conditions.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) * When resolving a BTF_KIND_STRUCT, we need to resolve all its
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) * members because a member is always referring to another
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) * type. A struct's member can be treated as "RESOLVED" if
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) * it is referring to a BTF_KIND_PTR. Otherwise, the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) * following valid C struct would be rejected:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) * struct A {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) * int m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) * struct A *a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) * };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) * When resolving a BTF_KIND_PTR, it needs to keep resolving if
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) * it is referring to another BTF_KIND_PTR. Otherwise, we cannot
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) * detect a pointer loop, e.g.:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) * BTF_KIND_CONST -> BTF_KIND_PTR -> BTF_KIND_CONST -> BTF_KIND_PTR +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) * ^ |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) * +-----------------------------------------+
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) #define BITS_PER_U128 (sizeof(u64) * BITS_PER_BYTE * 2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) #define BITS_PER_BYTE_MASK (BITS_PER_BYTE - 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) #define BITS_PER_BYTE_MASKED(bits) ((bits) & BITS_PER_BYTE_MASK)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) #define BITS_ROUNDDOWN_BYTES(bits) ((bits) >> 3)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) #define BITS_ROUNDUP_BYTES(bits) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) (BITS_ROUNDDOWN_BYTES(bits) + !!BITS_PER_BYTE_MASKED(bits))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) #define BTF_INFO_MASK 0x8f00ffff
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) #define BTF_INT_MASK 0x0fffffff
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) #define BTF_TYPE_ID_VALID(type_id) ((type_id) <= BTF_MAX_TYPE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) #define BTF_STR_OFFSET_VALID(name_off) ((name_off) <= BTF_MAX_NAME_OFFSET)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) /* 16MB for 64k structs and each has 16 members and
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) * a few MB spaces for the string section.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) * The hard limit is S32_MAX.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) #define BTF_MAX_SIZE (16 * 1024 * 1024)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) #define for_each_member_from(i, from, struct_type, member) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) for (i = from, member = btf_type_member(struct_type) + from; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) i < btf_type_vlen(struct_type); \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) i++, member++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) #define for_each_vsi_from(i, from, struct_type, member) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) for (i = from, member = btf_type_var_secinfo(struct_type) + from; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) i < btf_type_vlen(struct_type); \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) i++, member++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) DEFINE_IDR(btf_idr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) DEFINE_SPINLOCK(btf_idr_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) struct btf {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) void *data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) struct btf_type **types;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) u32 *resolved_ids;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) u32 *resolved_sizes;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) const char *strings;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) void *nohdr_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) struct btf_header hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) u32 nr_types;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) u32 types_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) u32 data_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) refcount_t refcnt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) u32 id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) struct rcu_head rcu;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) enum verifier_phase {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) CHECK_META,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) CHECK_TYPE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) struct resolve_vertex {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) const struct btf_type *t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) u32 type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) u16 next_member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) enum visit_state {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) NOT_VISITED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) VISITED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) RESOLVED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) enum resolve_mode {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) RESOLVE_TBD, /* To Be Determined */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) RESOLVE_PTR, /* Resolving for Pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) RESOLVE_STRUCT_OR_ARRAY, /* Resolving for struct/union
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) * or array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) #define MAX_RESOLVE_DEPTH 32
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) struct btf_sec_info {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) u32 off;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) u32 len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) struct btf_verifier_env {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) struct btf *btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) u8 *visit_states;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) struct resolve_vertex stack[MAX_RESOLVE_DEPTH];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) struct bpf_verifier_log log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) u32 log_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) u32 top_stack;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) enum verifier_phase phase;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) enum resolve_mode resolve_mode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) static const char * const btf_kind_str[NR_BTF_KINDS] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) [BTF_KIND_UNKN] = "UNKNOWN",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) [BTF_KIND_INT] = "INT",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) [BTF_KIND_PTR] = "PTR",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) [BTF_KIND_ARRAY] = "ARRAY",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) [BTF_KIND_STRUCT] = "STRUCT",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) [BTF_KIND_UNION] = "UNION",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) [BTF_KIND_ENUM] = "ENUM",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) [BTF_KIND_FWD] = "FWD",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) [BTF_KIND_TYPEDEF] = "TYPEDEF",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) [BTF_KIND_VOLATILE] = "VOLATILE",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) [BTF_KIND_CONST] = "CONST",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) [BTF_KIND_RESTRICT] = "RESTRICT",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) [BTF_KIND_FUNC] = "FUNC",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) [BTF_KIND_FUNC_PROTO] = "FUNC_PROTO",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) [BTF_KIND_VAR] = "VAR",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) [BTF_KIND_DATASEC] = "DATASEC",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) static const char *btf_type_str(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) return btf_kind_str[BTF_INFO_KIND(t->info)];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) /* Chunk size we use in safe copy of data to be shown. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) #define BTF_SHOW_OBJ_SAFE_SIZE 32
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) * This is the maximum size of a base type value (equivalent to a
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) * 128-bit int); if we are at the end of our safe buffer and have
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) * less than 16 bytes space we can't be assured of being able
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) * to copy the next type safely, so in such cases we will initiate
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) * a new copy.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) #define BTF_SHOW_OBJ_BASE_TYPE_SIZE 16
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) /* Type name size */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) #define BTF_SHOW_NAME_SIZE 80
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) * Common data to all BTF show operations. Private show functions can add
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) * their own data to a structure containing a struct btf_show and consult it
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) * in the show callback. See btf_type_show() below.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) * One challenge with showing nested data is we want to skip 0-valued
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) * data, but in order to figure out whether a nested object is all zeros
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) * we need to walk through it. As a result, we need to make two passes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) * when handling structs, unions and arrays; the first path simply looks
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) * for nonzero data, while the second actually does the display. The first
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) * pass is signalled by show->state.depth_check being set, and if we
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) * encounter a non-zero value we set show->state.depth_to_show to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) * the depth at which we encountered it. When we have completed the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) * first pass, we will know if anything needs to be displayed if
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) * depth_to_show > depth. See btf_[struct,array]_show() for the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) * implementation of this.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) * Another problem is we want to ensure the data for display is safe to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) * access. To support this, the anonymous "struct {} obj" tracks the data
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) * object and our safe copy of it. We copy portions of the data needed
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) * to the object "copy" buffer, but because its size is limited to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) * BTF_SHOW_OBJ_COPY_LEN bytes, multiple copies may be required as we
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) * traverse larger objects for display.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) * The various data type show functions all start with a call to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) * btf_show_start_type() which returns a pointer to the safe copy
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) * of the data needed (or if BTF_SHOW_UNSAFE is specified, to the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) * raw data itself). btf_show_obj_safe() is responsible for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) * using copy_from_kernel_nofault() to update the safe data if necessary
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) * as we traverse the object's data. skbuff-like semantics are
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) * used:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) * - obj.head points to the start of the toplevel object for display
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) * - obj.size is the size of the toplevel object
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) * - obj.data points to the current point in the original data at
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) * which our safe data starts. obj.data will advance as we copy
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) * portions of the data.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) * In most cases a single copy will suffice, but larger data structures
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) * such as "struct task_struct" will require many copies. The logic in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) * btf_show_obj_safe() handles the logic that determines if a new
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) * copy_from_kernel_nofault() is needed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) struct btf_show {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) u64 flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) void *target; /* target of show operation (seq file, buffer) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) void (*showfn)(struct btf_show *show, const char *fmt, va_list args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) const struct btf *btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) /* below are used during iteration */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) struct {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) u8 depth;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) u8 depth_to_show;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) u8 depth_check;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) u8 array_member:1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) array_terminated:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) u16 array_encoding;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) u32 type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) int status; /* non-zero for error */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) const struct btf_type *type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) const struct btf_member *member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) char name[BTF_SHOW_NAME_SIZE]; /* space for member name/type */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) } state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) struct {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) u32 size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) void *head;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) void *data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) u8 safe[BTF_SHOW_OBJ_SAFE_SIZE];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) } obj;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) struct btf_kind_operations {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) s32 (*check_meta)(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) u32 meta_left);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) int (*resolve)(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) const struct resolve_vertex *v);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) int (*check_member)(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) const struct btf_type *member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) int (*check_kflag_member)(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) const struct btf_type *member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) void (*log_details)(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) const struct btf_type *t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) void (*show)(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) u32 type_id, void *data, u8 bits_offsets,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) struct btf_show *show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) static const struct btf_kind_operations * const kind_ops[NR_BTF_KINDS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) static struct btf_type btf_void;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) static int btf_resolve(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) const struct btf_type *t, u32 type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) static bool btf_type_is_modifier(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) /* Some of them is not strictly a C modifier
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) * but they are grouped into the same bucket
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) * for BTF concern:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) * A type (t) that refers to another
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) * type through t->type AND its size cannot
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) * be determined without following the t->type.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) * ptr does not fall into this bucket
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) * because its size is always sizeof(void *).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) switch (BTF_INFO_KIND(t->info)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) case BTF_KIND_TYPEDEF:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) case BTF_KIND_VOLATILE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) case BTF_KIND_CONST:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) case BTF_KIND_RESTRICT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) bool btf_type_is_void(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) return t == &btf_void;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) static bool btf_type_is_fwd(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) return BTF_INFO_KIND(t->info) == BTF_KIND_FWD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) static bool btf_type_nosize(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) return btf_type_is_void(t) || btf_type_is_fwd(t) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) btf_type_is_func(t) || btf_type_is_func_proto(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) static bool btf_type_nosize_or_null(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) return !t || btf_type_nosize(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) static bool __btf_type_is_struct(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) return BTF_INFO_KIND(t->info) == BTF_KIND_STRUCT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) static bool btf_type_is_array(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) return BTF_INFO_KIND(t->info) == BTF_KIND_ARRAY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) static bool btf_type_is_datasec(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) return BTF_INFO_KIND(t->info) == BTF_KIND_DATASEC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) s32 btf_find_by_name_kind(const struct btf *btf, const char *name, u8 kind)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) const struct btf_type *t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) const char *tname;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) u32 i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) for (i = 1; i <= btf->nr_types; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) t = btf->types[i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) if (BTF_INFO_KIND(t->info) != kind)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) tname = btf_name_by_offset(btf, t->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) if (!strcmp(tname, name))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) return i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) return -ENOENT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) const struct btf_type *btf_type_skip_modifiers(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) u32 id, u32 *res_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) const struct btf_type *t = btf_type_by_id(btf, id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) while (btf_type_is_modifier(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) if (res_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) *res_id = id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) return t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) const struct btf_type *btf_type_resolve_ptr(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) u32 id, u32 *res_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) const struct btf_type *t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) t = btf_type_skip_modifiers(btf, id, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) if (!btf_type_is_ptr(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) return btf_type_skip_modifiers(btf, t->type, res_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) const struct btf_type *btf_type_resolve_func_ptr(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) u32 id, u32 *res_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) const struct btf_type *ptype;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) ptype = btf_type_resolve_ptr(btf, id, res_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) if (ptype && btf_type_is_func_proto(ptype))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) return ptype;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) /* Types that act only as a source, not sink or intermediate
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) * type when resolving.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) static bool btf_type_is_resolve_source_only(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) return btf_type_is_var(t) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) btf_type_is_datasec(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) /* What types need to be resolved?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) * btf_type_is_modifier() is an obvious one.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) * btf_type_is_struct() because its member refers to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) * another type (through member->type).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) * btf_type_is_var() because the variable refers to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) * another type. btf_type_is_datasec() holds multiple
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) * btf_type_is_var() types that need resolving.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) * btf_type_is_array() because its element (array->type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) * refers to another type. Array can be thought of a
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) * special case of struct while array just has the same
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) * member-type repeated by array->nelems of times.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) static bool btf_type_needs_resolve(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) return btf_type_is_modifier(t) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) btf_type_is_ptr(t) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) btf_type_is_struct(t) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) btf_type_is_array(t) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) btf_type_is_var(t) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) btf_type_is_datasec(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) /* t->size can be used */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) static bool btf_type_has_size(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) switch (BTF_INFO_KIND(t->info)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) case BTF_KIND_INT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) case BTF_KIND_STRUCT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) case BTF_KIND_UNION:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) case BTF_KIND_ENUM:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) case BTF_KIND_DATASEC:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) static const char *btf_int_encoding_str(u8 encoding)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) if (encoding == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) return "(none)";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) else if (encoding == BTF_INT_SIGNED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) return "SIGNED";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) else if (encoding == BTF_INT_CHAR)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) return "CHAR";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) else if (encoding == BTF_INT_BOOL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) return "BOOL";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) return "UNKN";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) static u32 btf_type_int(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) return *(u32 *)(t + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) static const struct btf_array *btf_type_array(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) return (const struct btf_array *)(t + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) static const struct btf_enum *btf_type_enum(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) return (const struct btf_enum *)(t + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) static const struct btf_var *btf_type_var(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) return (const struct btf_var *)(t + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) static const struct btf_kind_operations *btf_type_ops(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) return kind_ops[BTF_INFO_KIND(t->info)];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) static bool btf_name_offset_valid(const struct btf *btf, u32 offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) return BTF_STR_OFFSET_VALID(offset) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) offset < btf->hdr.str_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) static bool __btf_name_char_ok(char c, bool first, bool dot_ok)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) if ((first ? !isalpha(c) :
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) !isalnum(c)) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) c != '_' &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) ((c == '.' && !dot_ok) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) c != '.'))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) static bool __btf_name_valid(const struct btf *btf, u32 offset, bool dot_ok)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) /* offset must be valid */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) const char *src = &btf->strings[offset];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) const char *src_limit;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) if (!__btf_name_char_ok(*src, true, dot_ok))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) /* set a limit on identifier length */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) src_limit = src + KSYM_NAME_LEN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) src++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) while (*src && src < src_limit) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) if (!__btf_name_char_ok(*src, false, dot_ok))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) src++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) return !*src;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) /* Only C-style identifier is permitted. This can be relaxed if
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) * necessary.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) static bool btf_name_valid_identifier(const struct btf *btf, u32 offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) return __btf_name_valid(btf, offset, false);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) static bool btf_name_valid_section(const struct btf *btf, u32 offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) return __btf_name_valid(btf, offset, true);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) static const char *__btf_name_by_offset(const struct btf *btf, u32 offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) if (!offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) return "(anon)";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) else if (offset < btf->hdr.str_len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) return &btf->strings[offset];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) return "(invalid-name-offset)";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) const char *btf_name_by_offset(const struct btf *btf, u32 offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664) if (offset < btf->hdr.str_len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665) return &btf->strings[offset];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) const struct btf_type *btf_type_by_id(const struct btf *btf, u32 type_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) if (type_id > btf->nr_types)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) return btf->types[type_id];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) * Regular int is not a bit field and it must be either
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) * u8/u16/u32/u64 or __int128.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) static bool btf_type_int_is_regular(const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) u8 nr_bits, nr_bytes;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) u32 int_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) int_data = btf_type_int(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) nr_bits = BTF_INT_BITS(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) nr_bytes = BITS_ROUNDUP_BYTES(nr_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) if (BITS_PER_BYTE_MASKED(nr_bits) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) BTF_INT_OFFSET(int_data) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) (nr_bytes != sizeof(u8) && nr_bytes != sizeof(u16) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) nr_bytes != sizeof(u32) && nr_bytes != sizeof(u64) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) nr_bytes != (2 * sizeof(u64)))) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) * Check that given struct member is a regular int with expected
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703) * offset and size.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) bool btf_member_is_reg_int(const struct btf *btf, const struct btf_type *s,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) const struct btf_member *m,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) u32 expected_offset, u32 expected_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) const struct btf_type *t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) u32 id, int_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) u8 nr_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) id = m->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) t = btf_type_id_size(btf, &id, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) if (!t || !btf_type_is_int(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) int_data = btf_type_int(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) nr_bits = BTF_INT_BITS(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) if (btf_type_kflag(s)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) u32 bitfield_size = BTF_MEMBER_BITFIELD_SIZE(m->offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722) u32 bit_offset = BTF_MEMBER_BIT_OFFSET(m->offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) /* if kflag set, int should be a regular int and
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) * bit offset should be at byte boundary.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) return !bitfield_size &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) BITS_ROUNDUP_BYTES(bit_offset) == expected_offset &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) BITS_ROUNDUP_BYTES(nr_bits) == expected_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) if (BTF_INT_OFFSET(int_data) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) BITS_PER_BYTE_MASKED(m->offset) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) BITS_ROUNDUP_BYTES(m->offset) != expected_offset ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) BITS_PER_BYTE_MASKED(nr_bits) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736) BITS_ROUNDUP_BYTES(nr_bits) != expected_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742) /* Similar to btf_type_skip_modifiers() but does not skip typedefs. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) static const struct btf_type *btf_type_skip_qualifiers(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) u32 id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746) const struct btf_type *t = btf_type_by_id(btf, id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) while (btf_type_is_modifier(t) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) BTF_INFO_KIND(t->info) != BTF_KIND_TYPEDEF) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) return t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) #define BTF_SHOW_MAX_ITER 10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) #define BTF_KIND_BIT(kind) (1ULL << kind)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762) * Populate show->state.name with type name information.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763) * Format of type name is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765) * [.member_name = ] (type_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767) static const char *btf_show_name(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) /* BTF_MAX_ITER array suffixes "[]" */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) const char *array_suffixes = "[][][][][][][][][][]";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771) const char *array_suffix = &array_suffixes[strlen(array_suffixes)];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772) /* BTF_MAX_ITER pointer suffixes "*" */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) const char *ptr_suffixes = "**********";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) const char *ptr_suffix = &ptr_suffixes[strlen(ptr_suffixes)];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775) const char *name = NULL, *prefix = "", *parens = "";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) const struct btf_member *m = show->state.member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777) const struct btf_type *t = show->state.type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) const struct btf_array *array;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) u32 id = show->state.type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) const char *member = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781) bool show_member = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) u64 kinds = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) show->state.name[0] = '\0';
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) * Don't show type name if we're showing an array member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789) * in that case we show the array type so don't need to repeat
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) * ourselves for each member.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) if (show->state.array_member)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) return "";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) /* Retrieve member name, if any. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) if (m) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797) member = btf_name_by_offset(show->btf, m->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) show_member = strlen(member) > 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) id = m->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) * Start with type_id, as we have resolved the struct btf_type *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804) * via btf_modifier_show() past the parent typedef to the child
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) * struct, int etc it is defined as. In such cases, the type_id
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) * still represents the starting type while the struct btf_type *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) * in our show->state points at the resolved type of the typedef.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809) t = btf_type_by_id(show->btf, id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) if (!t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) return "";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) * The goal here is to build up the right number of pointer and
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) * array suffixes while ensuring the type name for a typedef
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) * is represented. Along the way we accumulate a list of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) * BTF kinds we have encountered, since these will inform later
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818) * display; for example, pointer types will not require an
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819) * opening "{" for struct, we will just display the pointer value.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821) * We also want to accumulate the right number of pointer or array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) * indices in the format string while iterating until we get to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823) * the typedef/pointee/array member target type.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) * We start by pointing at the end of pointer and array suffix
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826) * strings; as we accumulate pointers and arrays we move the pointer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) * or array string backwards so it will show the expected number of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828) * '*' or '[]' for the type. BTF_SHOW_MAX_ITER of nesting of pointers
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) * and/or arrays and typedefs are supported as a precaution.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831) * We also want to get typedef name while proceeding to resolve
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832) * type it points to so that we can add parentheses if it is a
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833) * "typedef struct" etc.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835) for (i = 0; i < BTF_SHOW_MAX_ITER; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) switch (BTF_INFO_KIND(t->info)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838) case BTF_KIND_TYPEDEF:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) if (!name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) name = btf_name_by_offset(show->btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) t->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842) kinds |= BTF_KIND_BIT(BTF_KIND_TYPEDEF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843) id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) case BTF_KIND_ARRAY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846) kinds |= BTF_KIND_BIT(BTF_KIND_ARRAY);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) parens = "[";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848) if (!t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) return "";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850) array = btf_type_array(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) if (array_suffix > array_suffixes)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852) array_suffix -= 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) id = array->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 854) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 855) case BTF_KIND_PTR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 856) kinds |= BTF_KIND_BIT(BTF_KIND_PTR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 857) if (ptr_suffix > ptr_suffixes)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 858) ptr_suffix -= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 859) id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 860) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 861) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 862) id = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 863) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 864) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 865) if (!id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 866) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 867) t = btf_type_skip_qualifiers(show->btf, id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 868) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 869) /* We may not be able to represent this type; bail to be safe */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 870) if (i == BTF_SHOW_MAX_ITER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 871) return "";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 872)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 873) if (!name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 874) name = btf_name_by_offset(show->btf, t->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 875)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 876) switch (BTF_INFO_KIND(t->info)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 877) case BTF_KIND_STRUCT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 878) case BTF_KIND_UNION:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 879) prefix = BTF_INFO_KIND(t->info) == BTF_KIND_STRUCT ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 880) "struct" : "union";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 881) /* if it's an array of struct/union, parens is already set */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 882) if (!(kinds & (BTF_KIND_BIT(BTF_KIND_ARRAY))))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 883) parens = "{";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 884) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 885) case BTF_KIND_ENUM:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 886) prefix = "enum";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 887) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 888) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 889) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 890) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 891)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 892) /* pointer does not require parens */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 893) if (kinds & BTF_KIND_BIT(BTF_KIND_PTR))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 894) parens = "";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 895) /* typedef does not require struct/union/enum prefix */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 896) if (kinds & BTF_KIND_BIT(BTF_KIND_TYPEDEF))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 897) prefix = "";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 898)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 899) if (!name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 900) name = "";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 901)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 902) /* Even if we don't want type name info, we want parentheses etc */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 903) if (show->flags & BTF_SHOW_NONAME)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 904) snprintf(show->state.name, sizeof(show->state.name), "%s",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 905) parens);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 906) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 907) snprintf(show->state.name, sizeof(show->state.name),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 908) "%s%s%s(%s%s%s%s%s%s)%s",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 909) /* first 3 strings comprise ".member = " */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 910) show_member ? "." : "",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 911) show_member ? member : "",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 912) show_member ? " = " : "",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 913) /* ...next is our prefix (struct, enum, etc) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 914) prefix,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 915) strlen(prefix) > 0 && strlen(name) > 0 ? " " : "",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 916) /* ...this is the type name itself */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 917) name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 918) /* ...suffixed by the appropriate '*', '[]' suffixes */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 919) strlen(ptr_suffix) > 0 ? " " : "", ptr_suffix,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 920) array_suffix, parens);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 921)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 922) return show->state.name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 923) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 924)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 925) static const char *__btf_show_indent(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 926) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 927) const char *indents = " ";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 928) const char *indent = &indents[strlen(indents)];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 929)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 930) if ((indent - show->state.depth) >= indents)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 931) return indent - show->state.depth;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 932) return indents;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 933) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 934)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 935) static const char *btf_show_indent(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 936) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 937) return show->flags & BTF_SHOW_COMPACT ? "" : __btf_show_indent(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 938) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 939)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 940) static const char *btf_show_newline(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 941) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 942) return show->flags & BTF_SHOW_COMPACT ? "" : "\n";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 943) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 944)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 945) static const char *btf_show_delim(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 946) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 947) if (show->state.depth == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 948) return "";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 949)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 950) if ((show->flags & BTF_SHOW_COMPACT) && show->state.type &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 951) BTF_INFO_KIND(show->state.type->info) == BTF_KIND_UNION)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 952) return "|";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 953)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 954) return ",";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 955) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 956)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 957) __printf(2, 3) static void btf_show(struct btf_show *show, const char *fmt, ...)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 958) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 959) va_list args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 960)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 961) if (!show->state.depth_check) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 962) va_start(args, fmt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 963) show->showfn(show, fmt, args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 964) va_end(args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 965) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 966) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 967)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 968) /* Macros are used here as btf_show_type_value[s]() prepends and appends
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 969) * format specifiers to the format specifier passed in; these do the work of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 970) * adding indentation, delimiters etc while the caller simply has to specify
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 971) * the type value(s) in the format specifier + value(s).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 972) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 973) #define btf_show_type_value(show, fmt, value) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 974) do { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 975) if ((value) != 0 || (show->flags & BTF_SHOW_ZERO) || \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 976) show->state.depth == 0) { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 977) btf_show(show, "%s%s" fmt "%s%s", \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 978) btf_show_indent(show), \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 979) btf_show_name(show), \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 980) value, btf_show_delim(show), \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 981) btf_show_newline(show)); \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 982) if (show->state.depth > show->state.depth_to_show) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 983) show->state.depth_to_show = show->state.depth; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 984) } \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 985) } while (0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 986)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 987) #define btf_show_type_values(show, fmt, ...) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 988) do { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 989) btf_show(show, "%s%s" fmt "%s%s", btf_show_indent(show), \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 990) btf_show_name(show), \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 991) __VA_ARGS__, btf_show_delim(show), \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 992) btf_show_newline(show)); \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 993) if (show->state.depth > show->state.depth_to_show) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 994) show->state.depth_to_show = show->state.depth; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 995) } while (0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 996)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 997) /* How much is left to copy to safe buffer after @data? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 998) static int btf_show_obj_size_left(struct btf_show *show, void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 999) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1000) return show->obj.head + show->obj.size - data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1001) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1002)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1003) /* Is object pointed to by @data of @size already copied to our safe buffer? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1004) static bool btf_show_obj_is_safe(struct btf_show *show, void *data, int size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1005) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1006) return data >= show->obj.data &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1007) (data + size) < (show->obj.data + BTF_SHOW_OBJ_SAFE_SIZE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1008) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1009)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1010) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1011) * If object pointed to by @data of @size falls within our safe buffer, return
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1012) * the equivalent pointer to the same safe data. Assumes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1013) * copy_from_kernel_nofault() has already happened and our safe buffer is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1014) * populated.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1015) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1016) static void *__btf_show_obj_safe(struct btf_show *show, void *data, int size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1017) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1018) if (btf_show_obj_is_safe(show, data, size))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1019) return show->obj.safe + (data - show->obj.data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1020) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1021) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1022)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1023) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1024) * Return a safe-to-access version of data pointed to by @data.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1025) * We do this by copying the relevant amount of information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1026) * to the struct btf_show obj.safe buffer using copy_from_kernel_nofault().
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1027) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1028) * If BTF_SHOW_UNSAFE is specified, just return data as-is; no
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1029) * safe copy is needed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1030) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1031) * Otherwise we need to determine if we have the required amount
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1032) * of data (determined by the @data pointer and the size of the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1033) * largest base type we can encounter (represented by
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1034) * BTF_SHOW_OBJ_BASE_TYPE_SIZE). Having that much data ensures
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1035) * that we will be able to print some of the current object,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1036) * and if more is needed a copy will be triggered.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1037) * Some objects such as structs will not fit into the buffer;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1038) * in such cases additional copies when we iterate over their
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1039) * members may be needed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1040) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1041) * btf_show_obj_safe() is used to return a safe buffer for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1042) * btf_show_start_type(); this ensures that as we recurse into
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1043) * nested types we always have safe data for the given type.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1044) * This approach is somewhat wasteful; it's possible for example
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1045) * that when iterating over a large union we'll end up copying the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1046) * same data repeatedly, but the goal is safety not performance.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1047) * We use stack data as opposed to per-CPU buffers because the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1048) * iteration over a type can take some time, and preemption handling
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1049) * would greatly complicate use of the safe buffer.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1050) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1051) static void *btf_show_obj_safe(struct btf_show *show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1052) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1053) void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1054) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1055) const struct btf_type *rt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1056) int size_left, size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1057) void *safe = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1058)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1059) if (show->flags & BTF_SHOW_UNSAFE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1060) return data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1061)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1062) rt = btf_resolve_size(show->btf, t, &size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1063) if (IS_ERR(rt)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1064) show->state.status = PTR_ERR(rt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1065) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1066) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1067)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1068) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1069) * Is this toplevel object? If so, set total object size and
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1070) * initialize pointers. Otherwise check if we still fall within
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1071) * our safe object data.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1072) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1073) if (show->state.depth == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1074) show->obj.size = size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1075) show->obj.head = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1076) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1077) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1078) * If the size of the current object is > our remaining
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1079) * safe buffer we _may_ need to do a new copy. However
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1080) * consider the case of a nested struct; it's size pushes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1081) * us over the safe buffer limit, but showing any individual
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1082) * struct members does not. In such cases, we don't need
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1083) * to initiate a fresh copy yet; however we definitely need
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1084) * at least BTF_SHOW_OBJ_BASE_TYPE_SIZE bytes left
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1085) * in our buffer, regardless of the current object size.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1086) * The logic here is that as we resolve types we will
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1087) * hit a base type at some point, and we need to be sure
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1088) * the next chunk of data is safely available to display
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1089) * that type info safely. We cannot rely on the size of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1090) * the current object here because it may be much larger
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1091) * than our current buffer (e.g. task_struct is 8k).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1092) * All we want to do here is ensure that we can print the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1093) * next basic type, which we can if either
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1094) * - the current type size is within the safe buffer; or
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1095) * - at least BTF_SHOW_OBJ_BASE_TYPE_SIZE bytes are left in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1096) * the safe buffer.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1097) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1098) safe = __btf_show_obj_safe(show, data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1099) min(size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1100) BTF_SHOW_OBJ_BASE_TYPE_SIZE));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1101) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1102)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1103) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1104) * We need a new copy to our safe object, either because we haven't
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1105) * yet copied and are intializing safe data, or because the data
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1106) * we want falls outside the boundaries of the safe object.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1107) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1108) if (!safe) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1109) size_left = btf_show_obj_size_left(show, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1110) if (size_left > BTF_SHOW_OBJ_SAFE_SIZE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1111) size_left = BTF_SHOW_OBJ_SAFE_SIZE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1112) show->state.status = copy_from_kernel_nofault(show->obj.safe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1113) data, size_left);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1114) if (!show->state.status) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1115) show->obj.data = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1116) safe = show->obj.safe;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1117) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1118) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1119)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1120) return safe;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1121) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1122)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1123) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1124) * Set the type we are starting to show and return a safe data pointer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1125) * to be used for showing the associated data.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1126) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1127) static void *btf_show_start_type(struct btf_show *show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1128) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1129) u32 type_id, void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1130) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1131) show->state.type = t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1132) show->state.type_id = type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1133) show->state.name[0] = '\0';
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1134)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1135) return btf_show_obj_safe(show, t, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1136) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1137)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1138) static void btf_show_end_type(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1139) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1140) show->state.type = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1141) show->state.type_id = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1142) show->state.name[0] = '\0';
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1143) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1144)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1145) static void *btf_show_start_aggr_type(struct btf_show *show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1146) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1147) u32 type_id, void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1148) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1149) void *safe_data = btf_show_start_type(show, t, type_id, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1150)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1151) if (!safe_data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1152) return safe_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1153)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1154) btf_show(show, "%s%s%s", btf_show_indent(show),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1155) btf_show_name(show),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1156) btf_show_newline(show));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1157) show->state.depth++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1158) return safe_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1159) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1160)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1161) static void btf_show_end_aggr_type(struct btf_show *show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1162) const char *suffix)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1163) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1164) show->state.depth--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1165) btf_show(show, "%s%s%s%s", btf_show_indent(show), suffix,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1166) btf_show_delim(show), btf_show_newline(show));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1167) btf_show_end_type(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1168) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1169)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1170) static void btf_show_start_member(struct btf_show *show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1171) const struct btf_member *m)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1172) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1173) show->state.member = m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1174) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1175)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1176) static void btf_show_start_array_member(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1177) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1178) show->state.array_member = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1179) btf_show_start_member(show, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1180) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1181)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1182) static void btf_show_end_member(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1183) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1184) show->state.member = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1185) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1186)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1187) static void btf_show_end_array_member(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1188) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1189) show->state.array_member = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1190) btf_show_end_member(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1191) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1192)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1193) static void *btf_show_start_array_type(struct btf_show *show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1194) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1195) u32 type_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1196) u16 array_encoding,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1197) void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1198) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1199) show->state.array_encoding = array_encoding;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1200) show->state.array_terminated = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1201) return btf_show_start_aggr_type(show, t, type_id, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1202) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1204) static void btf_show_end_array_type(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1205) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1206) show->state.array_encoding = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1207) show->state.array_terminated = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1208) btf_show_end_aggr_type(show, "]");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1209) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1210)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1211) static void *btf_show_start_struct_type(struct btf_show *show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1212) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1213) u32 type_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1214) void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1215) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1216) return btf_show_start_aggr_type(show, t, type_id, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1217) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1218)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1219) static void btf_show_end_struct_type(struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1220) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1221) btf_show_end_aggr_type(show, "}");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1222) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1223)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1224) __printf(2, 3) static void __btf_verifier_log(struct bpf_verifier_log *log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1225) const char *fmt, ...)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1226) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1227) va_list args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1229) va_start(args, fmt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1230) bpf_verifier_vlog(log, fmt, args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1231) va_end(args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1232) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1233)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1234) __printf(2, 3) static void btf_verifier_log(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1235) const char *fmt, ...)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1236) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1237) struct bpf_verifier_log *log = &env->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1238) va_list args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1239)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1240) if (!bpf_verifier_log_needed(log))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1241) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1242)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1243) va_start(args, fmt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1244) bpf_verifier_vlog(log, fmt, args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1245) va_end(args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1246) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1247)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1248) __printf(4, 5) static void __btf_verifier_log_type(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1249) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1250) bool log_details,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1251) const char *fmt, ...)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1252) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1253) struct bpf_verifier_log *log = &env->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1254) u8 kind = BTF_INFO_KIND(t->info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1255) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1256) va_list args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1257)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1258) if (!bpf_verifier_log_needed(log))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1259) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1260)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1261) /* btf verifier prints all types it is processing via
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1262) * btf_verifier_log_type(..., fmt = NULL).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1263) * Skip those prints for in-kernel BTF verification.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1264) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1265) if (log->level == BPF_LOG_KERNEL && !fmt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1266) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1267)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1268) __btf_verifier_log(log, "[%u] %s %s%s",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1269) env->log_type_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1270) btf_kind_str[kind],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1271) __btf_name_by_offset(btf, t->name_off),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1272) log_details ? " " : "");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1273)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1274) if (log_details)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1275) btf_type_ops(t)->log_details(env, t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1276)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1277) if (fmt && *fmt) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1278) __btf_verifier_log(log, " ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1279) va_start(args, fmt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1280) bpf_verifier_vlog(log, fmt, args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1281) va_end(args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1282) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1283)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1284) __btf_verifier_log(log, "\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1285) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1286)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1287) #define btf_verifier_log_type(env, t, ...) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1288) __btf_verifier_log_type((env), (t), true, __VA_ARGS__)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1289) #define btf_verifier_log_basic(env, t, ...) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1290) __btf_verifier_log_type((env), (t), false, __VA_ARGS__)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1291)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1292) __printf(4, 5)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1293) static void btf_verifier_log_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1294) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1295) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1296) const char *fmt, ...)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1297) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1298) struct bpf_verifier_log *log = &env->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1299) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1300) va_list args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1301)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1302) if (!bpf_verifier_log_needed(log))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1303) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1304)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1305) if (log->level == BPF_LOG_KERNEL && !fmt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1306) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1307) /* The CHECK_META phase already did a btf dump.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1308) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1309) * If member is logged again, it must hit an error in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1310) * parsing this member. It is useful to print out which
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1311) * struct this member belongs to.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1312) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1313) if (env->phase != CHECK_META)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1314) btf_verifier_log_type(env, struct_type, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1315)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1316) if (btf_type_kflag(struct_type))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1317) __btf_verifier_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1318) "\t%s type_id=%u bitfield_size=%u bits_offset=%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1319) __btf_name_by_offset(btf, member->name_off),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1320) member->type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1321) BTF_MEMBER_BITFIELD_SIZE(member->offset),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1322) BTF_MEMBER_BIT_OFFSET(member->offset));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1323) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1324) __btf_verifier_log(log, "\t%s type_id=%u bits_offset=%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1325) __btf_name_by_offset(btf, member->name_off),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1326) member->type, member->offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1327)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1328) if (fmt && *fmt) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1329) __btf_verifier_log(log, " ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1330) va_start(args, fmt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1331) bpf_verifier_vlog(log, fmt, args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1332) va_end(args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1333) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1334)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1335) __btf_verifier_log(log, "\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1336) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1337)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1338) __printf(4, 5)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1339) static void btf_verifier_log_vsi(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1340) const struct btf_type *datasec_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1341) const struct btf_var_secinfo *vsi,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1342) const char *fmt, ...)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1343) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1344) struct bpf_verifier_log *log = &env->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1345) va_list args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1346)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1347) if (!bpf_verifier_log_needed(log))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1348) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1349) if (log->level == BPF_LOG_KERNEL && !fmt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1350) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1351) if (env->phase != CHECK_META)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1352) btf_verifier_log_type(env, datasec_type, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1353)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1354) __btf_verifier_log(log, "\t type_id=%u offset=%u size=%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1355) vsi->type, vsi->offset, vsi->size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1356) if (fmt && *fmt) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1357) __btf_verifier_log(log, " ");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1358) va_start(args, fmt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1359) bpf_verifier_vlog(log, fmt, args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1360) va_end(args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1361) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1362)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1363) __btf_verifier_log(log, "\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1364) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1365)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1366) static void btf_verifier_log_hdr(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1367) u32 btf_data_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1368) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1369) struct bpf_verifier_log *log = &env->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1370) const struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1371) const struct btf_header *hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1372)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1373) if (!bpf_verifier_log_needed(log))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1374) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1375)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1376) if (log->level == BPF_LOG_KERNEL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1377) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1378) hdr = &btf->hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1379) __btf_verifier_log(log, "magic: 0x%x\n", hdr->magic);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1380) __btf_verifier_log(log, "version: %u\n", hdr->version);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1381) __btf_verifier_log(log, "flags: 0x%x\n", hdr->flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1382) __btf_verifier_log(log, "hdr_len: %u\n", hdr->hdr_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1383) __btf_verifier_log(log, "type_off: %u\n", hdr->type_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1384) __btf_verifier_log(log, "type_len: %u\n", hdr->type_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1385) __btf_verifier_log(log, "str_off: %u\n", hdr->str_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1386) __btf_verifier_log(log, "str_len: %u\n", hdr->str_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1387) __btf_verifier_log(log, "btf_total_size: %u\n", btf_data_size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1388) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1389)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1390) static int btf_add_type(struct btf_verifier_env *env, struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1391) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1392) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1393)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1394) /* < 2 because +1 for btf_void which is always in btf->types[0].
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1395) * btf_void is not accounted in btf->nr_types because btf_void
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1396) * does not come from the BTF file.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1397) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1398) if (btf->types_size - btf->nr_types < 2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1399) /* Expand 'types' array */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1400)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1401) struct btf_type **new_types;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1402) u32 expand_by, new_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1403)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1404) if (btf->types_size == BTF_MAX_TYPE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1405) btf_verifier_log(env, "Exceeded max num of types");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1406) return -E2BIG;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1407) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1408)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1409) expand_by = max_t(u32, btf->types_size >> 2, 16);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1410) new_size = min_t(u32, BTF_MAX_TYPE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1411) btf->types_size + expand_by);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1412)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1413) new_types = kvcalloc(new_size, sizeof(*new_types),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1414) GFP_KERNEL | __GFP_NOWARN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1415) if (!new_types)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1416) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1417)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1418) if (btf->nr_types == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1419) new_types[0] = &btf_void;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1420) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1421) memcpy(new_types, btf->types,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1422) sizeof(*btf->types) * (btf->nr_types + 1));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1423)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1424) kvfree(btf->types);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1425) btf->types = new_types;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1426) btf->types_size = new_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1427) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1428)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1429) btf->types[++(btf->nr_types)] = t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1430)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1431) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1432) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1433)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1434) static int btf_alloc_id(struct btf *btf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1435) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1436) int id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1437)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1438) idr_preload(GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1439) spin_lock_bh(&btf_idr_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1440) id = idr_alloc_cyclic(&btf_idr, btf, 1, INT_MAX, GFP_ATOMIC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1441) if (id > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1442) btf->id = id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1443) spin_unlock_bh(&btf_idr_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1444) idr_preload_end();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1445)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1446) if (WARN_ON_ONCE(!id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1447) return -ENOSPC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1448)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1449) return id > 0 ? 0 : id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1450) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1451)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1452) static void btf_free_id(struct btf *btf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1453) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1454) unsigned long flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1455)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1456) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1457) * In map-in-map, calling map_delete_elem() on outer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1458) * map will call bpf_map_put on the inner map.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1459) * It will then eventually call btf_free_id()
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1460) * on the inner map. Some of the map_delete_elem()
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1461) * implementation may have irq disabled, so
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1462) * we need to use the _irqsave() version instead
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1463) * of the _bh() version.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1464) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1465) spin_lock_irqsave(&btf_idr_lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1466) idr_remove(&btf_idr, btf->id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1467) spin_unlock_irqrestore(&btf_idr_lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1468) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1469)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1470) static void btf_free(struct btf *btf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1471) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1472) kvfree(btf->types);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1473) kvfree(btf->resolved_sizes);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1474) kvfree(btf->resolved_ids);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1475) kvfree(btf->data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1476) kfree(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1477) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1478)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1479) static void btf_free_rcu(struct rcu_head *rcu)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1480) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1481) struct btf *btf = container_of(rcu, struct btf, rcu);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1482)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1483) btf_free(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1484) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1485)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1486) void btf_put(struct btf *btf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1487) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1488) if (btf && refcount_dec_and_test(&btf->refcnt)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1489) btf_free_id(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1490) call_rcu(&btf->rcu, btf_free_rcu);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1491) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1492) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1493)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1494) static int env_resolve_init(struct btf_verifier_env *env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1495) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1496) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1497) u32 nr_types = btf->nr_types;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1498) u32 *resolved_sizes = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1499) u32 *resolved_ids = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1500) u8 *visit_states = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1501)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1502) /* +1 for btf_void */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1503) resolved_sizes = kvcalloc(nr_types + 1, sizeof(*resolved_sizes),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1504) GFP_KERNEL | __GFP_NOWARN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1505) if (!resolved_sizes)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1506) goto nomem;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1507)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1508) resolved_ids = kvcalloc(nr_types + 1, sizeof(*resolved_ids),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1509) GFP_KERNEL | __GFP_NOWARN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1510) if (!resolved_ids)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1511) goto nomem;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1512)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1513) visit_states = kvcalloc(nr_types + 1, sizeof(*visit_states),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1514) GFP_KERNEL | __GFP_NOWARN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1515) if (!visit_states)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1516) goto nomem;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1517)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1518) btf->resolved_sizes = resolved_sizes;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1519) btf->resolved_ids = resolved_ids;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1520) env->visit_states = visit_states;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1521)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1522) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1523)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1524) nomem:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1525) kvfree(resolved_sizes);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1526) kvfree(resolved_ids);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1527) kvfree(visit_states);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1528) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1529) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1530)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1531) static void btf_verifier_env_free(struct btf_verifier_env *env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1532) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1533) kvfree(env->visit_states);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1534) kfree(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1535) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1536)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1537) static bool env_type_is_resolve_sink(const struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1538) const struct btf_type *next_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1539) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1540) switch (env->resolve_mode) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1541) case RESOLVE_TBD:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1542) /* int, enum or void is a sink */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1543) return !btf_type_needs_resolve(next_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1544) case RESOLVE_PTR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1545) /* int, enum, void, struct, array, func or func_proto is a sink
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1546) * for ptr
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1547) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1548) return !btf_type_is_modifier(next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1549) !btf_type_is_ptr(next_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1550) case RESOLVE_STRUCT_OR_ARRAY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1551) /* int, enum, void, ptr, func or func_proto is a sink
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1552) * for struct and array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1553) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1554) return !btf_type_is_modifier(next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1555) !btf_type_is_array(next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1556) !btf_type_is_struct(next_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1557) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1558) BUG();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1559) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1560) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1561)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1562) static bool env_type_is_resolved(const struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1563) u32 type_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1564) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1565) return env->visit_states[type_id] == RESOLVED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1566) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1567)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1568) static int env_stack_push(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1569) const struct btf_type *t, u32 type_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1570) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1571) struct resolve_vertex *v;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1572)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1573) if (env->top_stack == MAX_RESOLVE_DEPTH)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1574) return -E2BIG;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1575)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1576) if (env->visit_states[type_id] != NOT_VISITED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1577) return -EEXIST;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1578)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1579) env->visit_states[type_id] = VISITED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1580)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1581) v = &env->stack[env->top_stack++];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1582) v->t = t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1583) v->type_id = type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1584) v->next_member = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1585)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1586) if (env->resolve_mode == RESOLVE_TBD) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1587) if (btf_type_is_ptr(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1588) env->resolve_mode = RESOLVE_PTR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1589) else if (btf_type_is_struct(t) || btf_type_is_array(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1590) env->resolve_mode = RESOLVE_STRUCT_OR_ARRAY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1591) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1592)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1593) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1594) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1595)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1596) static void env_stack_set_next_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1597) u16 next_member)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1598) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1599) env->stack[env->top_stack - 1].next_member = next_member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1600) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1601)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1602) static void env_stack_pop_resolved(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1603) u32 resolved_type_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1604) u32 resolved_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1605) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1606) u32 type_id = env->stack[--(env->top_stack)].type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1607) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1608)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1609) btf->resolved_sizes[type_id] = resolved_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1610) btf->resolved_ids[type_id] = resolved_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1611) env->visit_states[type_id] = RESOLVED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1612) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1613)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1614) static const struct resolve_vertex *env_stack_peak(struct btf_verifier_env *env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1615) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1616) return env->top_stack ? &env->stack[env->top_stack - 1] : NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1617) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1618)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1619) /* Resolve the size of a passed-in "type"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1620) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1621) * type: is an array (e.g. u32 array[x][y])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1622) * return type: type "u32[x][y]", i.e. BTF_KIND_ARRAY,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1623) * *type_size: (x * y * sizeof(u32)). Hence, *type_size always
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1624) * corresponds to the return type.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1625) * *elem_type: u32
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1626) * *elem_id: id of u32
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1627) * *total_nelems: (x * y). Hence, individual elem size is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1628) * (*type_size / *total_nelems)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1629) * *type_id: id of type if it's changed within the function, 0 if not
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1630) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1631) * type: is not an array (e.g. const struct X)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1632) * return type: type "struct X"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1633) * *type_size: sizeof(struct X)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1634) * *elem_type: same as return type ("struct X")
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1635) * *elem_id: 0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1636) * *total_nelems: 1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1637) * *type_id: id of type if it's changed within the function, 0 if not
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1638) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1639) static const struct btf_type *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1640) __btf_resolve_size(const struct btf *btf, const struct btf_type *type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1641) u32 *type_size, const struct btf_type **elem_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1642) u32 *elem_id, u32 *total_nelems, u32 *type_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1643) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1644) const struct btf_type *array_type = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1645) const struct btf_array *array = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1646) u32 i, size, nelems = 1, id = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1647)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1648) for (i = 0; i < MAX_RESOLVE_DEPTH; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1649) switch (BTF_INFO_KIND(type->info)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1650) /* type->size can be used */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1651) case BTF_KIND_INT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1652) case BTF_KIND_STRUCT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1653) case BTF_KIND_UNION:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1654) case BTF_KIND_ENUM:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1655) size = type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1656) goto resolved;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1657)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1658) case BTF_KIND_PTR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1659) size = sizeof(void *);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1660) goto resolved;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1661)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1662) /* Modifiers */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1663) case BTF_KIND_TYPEDEF:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1664) case BTF_KIND_VOLATILE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1665) case BTF_KIND_CONST:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1666) case BTF_KIND_RESTRICT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1667) id = type->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1668) type = btf_type_by_id(btf, type->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1669) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1670)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1671) case BTF_KIND_ARRAY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1672) if (!array_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1673) array_type = type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1674) array = btf_type_array(type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1675) if (nelems && array->nelems > U32_MAX / nelems)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1676) return ERR_PTR(-EINVAL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1677) nelems *= array->nelems;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1678) type = btf_type_by_id(btf, array->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1679) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1680)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1681) /* type without size */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1682) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1683) return ERR_PTR(-EINVAL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1684) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1685) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1686)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1687) return ERR_PTR(-EINVAL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1688)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1689) resolved:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1690) if (nelems && size > U32_MAX / nelems)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1691) return ERR_PTR(-EINVAL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1692)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1693) *type_size = nelems * size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1694) if (total_nelems)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1695) *total_nelems = nelems;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1696) if (elem_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1697) *elem_type = type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1698) if (elem_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1699) *elem_id = array ? array->type : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1700) if (type_id && id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1701) *type_id = id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1702)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1703) return array_type ? : type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1704) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1705)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1706) const struct btf_type *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1707) btf_resolve_size(const struct btf *btf, const struct btf_type *type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1708) u32 *type_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1709) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1710) return __btf_resolve_size(btf, type, type_size, NULL, NULL, NULL, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1711) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1712)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1713) /* The input param "type_id" must point to a needs_resolve type */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1714) static const struct btf_type *btf_type_id_resolve(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1715) u32 *type_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1716) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1717) *type_id = btf->resolved_ids[*type_id];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1718) return btf_type_by_id(btf, *type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1719) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1720)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1721) const struct btf_type *btf_type_id_size(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1722) u32 *type_id, u32 *ret_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1723) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1724) const struct btf_type *size_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1725) u32 size_type_id = *type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1726) u32 size = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1727)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1728) size_type = btf_type_by_id(btf, size_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1729) if (btf_type_nosize_or_null(size_type))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1730) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1731)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1732) if (btf_type_has_size(size_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1733) size = size_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1734) } else if (btf_type_is_array(size_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1735) size = btf->resolved_sizes[size_type_id];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1736) } else if (btf_type_is_ptr(size_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1737) size = sizeof(void *);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1738) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1739) if (WARN_ON_ONCE(!btf_type_is_modifier(size_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1740) !btf_type_is_var(size_type)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1741) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1742)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1743) size_type_id = btf->resolved_ids[size_type_id];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1744) size_type = btf_type_by_id(btf, size_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1745) if (btf_type_nosize_or_null(size_type))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1746) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1747) else if (btf_type_has_size(size_type))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1748) size = size_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1749) else if (btf_type_is_array(size_type))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1750) size = btf->resolved_sizes[size_type_id];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1751) else if (btf_type_is_ptr(size_type))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1752) size = sizeof(void *);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1753) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1754) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1755) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1756)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1757) *type_id = size_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1758) if (ret_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1759) *ret_size = size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1760)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1761) return size_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1762) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1763)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1764) static int btf_df_check_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1765) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1766) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1767) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1768) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1769) btf_verifier_log_basic(env, struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1770) "Unsupported check_member");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1771) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1772) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1773)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1774) static int btf_df_check_kflag_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1775) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1776) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1777) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1778) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1779) btf_verifier_log_basic(env, struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1780) "Unsupported check_kflag_member");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1781) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1782) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1783)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1784) /* Used for ptr, array and struct/union type members.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1785) * int, enum and modifier types have their specific callback functions.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1786) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1787) static int btf_generic_check_kflag_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1788) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1789) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1790) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1791) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1792) if (BTF_MEMBER_BITFIELD_SIZE(member->offset)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1793) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1794) "Invalid member bitfield_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1795) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1796) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1797)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1798) /* bitfield size is 0, so member->offset represents bit offset only.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1799) * It is safe to call non kflag check_member variants.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1800) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1801) return btf_type_ops(member_type)->check_member(env, struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1802) member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1803) member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1804) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1805)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1806) static int btf_df_resolve(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1807) const struct resolve_vertex *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1808) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1809) btf_verifier_log_basic(env, v->t, "Unsupported resolve");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1810) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1811) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1812)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1813) static void btf_df_show(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1814) u32 type_id, void *data, u8 bits_offsets,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1815) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1816) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1817) btf_show(show, "<unsupported kind:%u>", BTF_INFO_KIND(t->info));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1818) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1819)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1820) static int btf_int_check_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1821) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1822) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1823) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1824) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1825) u32 int_data = btf_type_int(member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1826) u32 struct_bits_off = member->offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1827) u32 struct_size = struct_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1828) u32 nr_copy_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1829) u32 bytes_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1830)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1831) if (U32_MAX - struct_bits_off < BTF_INT_OFFSET(int_data)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1832) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1833) "bits_offset exceeds U32_MAX");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1834) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1835) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1836)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1837) struct_bits_off += BTF_INT_OFFSET(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1838) bytes_offset = BITS_ROUNDDOWN_BYTES(struct_bits_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1839) nr_copy_bits = BTF_INT_BITS(int_data) +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1840) BITS_PER_BYTE_MASKED(struct_bits_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1841)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1842) if (nr_copy_bits > BITS_PER_U128) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1843) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1844) "nr_copy_bits exceeds 128");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1845) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1846) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1847)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1848) if (struct_size < bytes_offset ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1849) struct_size - bytes_offset < BITS_ROUNDUP_BYTES(nr_copy_bits)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1850) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1851) "Member exceeds struct_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1852) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1853) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1854)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1855) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1856) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1857)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1858) static int btf_int_check_kflag_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1859) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1860) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1861) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1862) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1863) u32 struct_bits_off, nr_bits, nr_int_data_bits, bytes_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1864) u32 int_data = btf_type_int(member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1865) u32 struct_size = struct_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1866) u32 nr_copy_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1867)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1868) /* a regular int type is required for the kflag int member */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1869) if (!btf_type_int_is_regular(member_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1870) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1871) "Invalid member base type");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1872) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1873) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1874)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1875) /* check sanity of bitfield size */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1876) nr_bits = BTF_MEMBER_BITFIELD_SIZE(member->offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1877) struct_bits_off = BTF_MEMBER_BIT_OFFSET(member->offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1878) nr_int_data_bits = BTF_INT_BITS(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1879) if (!nr_bits) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1880) /* Not a bitfield member, member offset must be at byte
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1881) * boundary.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1882) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1883) if (BITS_PER_BYTE_MASKED(struct_bits_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1884) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1885) "Invalid member offset");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1886) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1887) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1888)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1889) nr_bits = nr_int_data_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1890) } else if (nr_bits > nr_int_data_bits) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1891) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1892) "Invalid member bitfield_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1893) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1894) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1895)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1896) bytes_offset = BITS_ROUNDDOWN_BYTES(struct_bits_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1897) nr_copy_bits = nr_bits + BITS_PER_BYTE_MASKED(struct_bits_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1898) if (nr_copy_bits > BITS_PER_U128) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1899) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1900) "nr_copy_bits exceeds 128");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1901) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1902) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1903)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1904) if (struct_size < bytes_offset ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1905) struct_size - bytes_offset < BITS_ROUNDUP_BYTES(nr_copy_bits)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1906) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1907) "Member exceeds struct_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1908) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1909) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1910)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1911) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1912) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1913)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1914) static s32 btf_int_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1915) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1916) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1917) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1918) u32 int_data, nr_bits, meta_needed = sizeof(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1919) u16 encoding;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1920)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1921) if (meta_left < meta_needed) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1922) btf_verifier_log_basic(env, t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1923) "meta_left:%u meta_needed:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1924) meta_left, meta_needed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1925) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1926) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1927)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1928) if (btf_type_vlen(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1929) btf_verifier_log_type(env, t, "vlen != 0");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1930) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1931) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1932)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1933) if (btf_type_kflag(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1934) btf_verifier_log_type(env, t, "Invalid btf_info kind_flag");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1935) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1936) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1937)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1938) int_data = btf_type_int(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1939) if (int_data & ~BTF_INT_MASK) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1940) btf_verifier_log_basic(env, t, "Invalid int_data:%x",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1941) int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1942) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1943) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1944)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1945) nr_bits = BTF_INT_BITS(int_data) + BTF_INT_OFFSET(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1946)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1947) if (nr_bits > BITS_PER_U128) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1948) btf_verifier_log_type(env, t, "nr_bits exceeds %zu",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1949) BITS_PER_U128);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1950) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1951) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1952)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1953) if (BITS_ROUNDUP_BYTES(nr_bits) > t->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1954) btf_verifier_log_type(env, t, "nr_bits exceeds type_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1955) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1956) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1957)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1958) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1959) * Only one of the encoding bits is allowed and it
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1960) * should be sufficient for the pretty print purpose (i.e. decoding).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1961) * Multiple bits can be allowed later if it is found
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1962) * to be insufficient.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1963) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1964) encoding = BTF_INT_ENCODING(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1965) if (encoding &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1966) encoding != BTF_INT_SIGNED &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1967) encoding != BTF_INT_CHAR &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1968) encoding != BTF_INT_BOOL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1969) btf_verifier_log_type(env, t, "Unsupported encoding");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1970) return -ENOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1971) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1972)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1973) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1974)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1975) return meta_needed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1976) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1977)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1978) static void btf_int_log(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1979) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1980) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1981) int int_data = btf_type_int(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1982)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1983) btf_verifier_log(env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1984) "size=%u bits_offset=%u nr_bits=%u encoding=%s",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1985) t->size, BTF_INT_OFFSET(int_data),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1986) BTF_INT_BITS(int_data),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1987) btf_int_encoding_str(BTF_INT_ENCODING(int_data)));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1988) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1989)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1990) static void btf_int128_print(struct btf_show *show, void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1991) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1992) /* data points to a __int128 number.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1993) * Suppose
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1994) * int128_num = *(__int128 *)data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1995) * The below formulas shows what upper_num and lower_num represents:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1996) * upper_num = int128_num >> 64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1997) * lower_num = int128_num & 0xffffffffFFFFFFFFULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1998) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1999) u64 upper_num, lower_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2000)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2001) #ifdef __BIG_ENDIAN_BITFIELD
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2002) upper_num = *(u64 *)data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2003) lower_num = *(u64 *)(data + 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2004) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2005) upper_num = *(u64 *)(data + 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2006) lower_num = *(u64 *)data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2007) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2008) if (upper_num == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2009) btf_show_type_value(show, "0x%llx", lower_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2010) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2011) btf_show_type_values(show, "0x%llx%016llx", upper_num,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2012) lower_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2013) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2014)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2015) static void btf_int128_shift(u64 *print_num, u16 left_shift_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2016) u16 right_shift_bits)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2017) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2018) u64 upper_num, lower_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2019)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2020) #ifdef __BIG_ENDIAN_BITFIELD
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2021) upper_num = print_num[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2022) lower_num = print_num[1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2023) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2024) upper_num = print_num[1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2025) lower_num = print_num[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2026) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2027)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2028) /* shake out un-needed bits by shift/or operations */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2029) if (left_shift_bits >= 64) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2030) upper_num = lower_num << (left_shift_bits - 64);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2031) lower_num = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2032) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2033) upper_num = (upper_num << left_shift_bits) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2034) (lower_num >> (64 - left_shift_bits));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2035) lower_num = lower_num << left_shift_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2036) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2037)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2038) if (right_shift_bits >= 64) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2039) lower_num = upper_num >> (right_shift_bits - 64);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2040) upper_num = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2041) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2042) lower_num = (lower_num >> right_shift_bits) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2043) (upper_num << (64 - right_shift_bits));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2044) upper_num = upper_num >> right_shift_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2045) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2046)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2047) #ifdef __BIG_ENDIAN_BITFIELD
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2048) print_num[0] = upper_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2049) print_num[1] = lower_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2050) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2051) print_num[0] = lower_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2052) print_num[1] = upper_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2053) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2054) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2055)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2056) static void btf_bitfield_show(void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2057) u8 nr_bits, struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2058) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2059) u16 left_shift_bits, right_shift_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2060) u8 nr_copy_bytes;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2061) u8 nr_copy_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2062) u64 print_num[2] = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2063)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2064) nr_copy_bits = nr_bits + bits_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2065) nr_copy_bytes = BITS_ROUNDUP_BYTES(nr_copy_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2066)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2067) memcpy(print_num, data, nr_copy_bytes);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2068)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2069) #ifdef __BIG_ENDIAN_BITFIELD
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2070) left_shift_bits = bits_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2071) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2072) left_shift_bits = BITS_PER_U128 - nr_copy_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2073) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2074) right_shift_bits = BITS_PER_U128 - nr_bits;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2075)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2076) btf_int128_shift(print_num, left_shift_bits, right_shift_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2077) btf_int128_print(show, print_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2078) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2079)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2080)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2081) static void btf_int_bits_show(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2082) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2083) void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2084) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2085) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2086) u32 int_data = btf_type_int(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2087) u8 nr_bits = BTF_INT_BITS(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2088) u8 total_bits_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2089)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2090) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2091) * bits_offset is at most 7.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2092) * BTF_INT_OFFSET() cannot exceed 128 bits.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2093) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2094) total_bits_offset = bits_offset + BTF_INT_OFFSET(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2095) data += BITS_ROUNDDOWN_BYTES(total_bits_offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2096) bits_offset = BITS_PER_BYTE_MASKED(total_bits_offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2097) btf_bitfield_show(data, bits_offset, nr_bits, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2098) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2099)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2100) static void btf_int_show(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2101) u32 type_id, void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2102) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2103) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2104) u32 int_data = btf_type_int(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2105) u8 encoding = BTF_INT_ENCODING(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2106) bool sign = encoding & BTF_INT_SIGNED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2107) u8 nr_bits = BTF_INT_BITS(int_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2108) void *safe_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2109)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2110) safe_data = btf_show_start_type(show, t, type_id, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2111) if (!safe_data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2112) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2113)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2114) if (bits_offset || BTF_INT_OFFSET(int_data) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2115) BITS_PER_BYTE_MASKED(nr_bits)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2116) btf_int_bits_show(btf, t, safe_data, bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2117) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2118) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2119)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2120) switch (nr_bits) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2121) case 128:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2122) btf_int128_print(show, safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2123) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2124) case 64:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2125) if (sign)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2126) btf_show_type_value(show, "%lld", *(s64 *)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2127) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2128) btf_show_type_value(show, "%llu", *(u64 *)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2129) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2130) case 32:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2131) if (sign)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2132) btf_show_type_value(show, "%d", *(s32 *)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2133) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2134) btf_show_type_value(show, "%u", *(u32 *)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2135) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2136) case 16:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2137) if (sign)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2138) btf_show_type_value(show, "%d", *(s16 *)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2139) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2140) btf_show_type_value(show, "%u", *(u16 *)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2141) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2142) case 8:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2143) if (show->state.array_encoding == BTF_INT_CHAR) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2144) /* check for null terminator */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2145) if (show->state.array_terminated)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2146) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2147) if (*(char *)data == '\0') {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2148) show->state.array_terminated = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2149) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2150) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2151) if (isprint(*(char *)data)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2152) btf_show_type_value(show, "'%c'",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2153) *(char *)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2154) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2155) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2156) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2157) if (sign)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2158) btf_show_type_value(show, "%d", *(s8 *)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2159) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2160) btf_show_type_value(show, "%u", *(u8 *)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2161) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2162) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2163) btf_int_bits_show(btf, t, safe_data, bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2164) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2165) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2166) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2167) btf_show_end_type(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2168) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2169)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2170) static const struct btf_kind_operations int_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2171) .check_meta = btf_int_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2172) .resolve = btf_df_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2173) .check_member = btf_int_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2174) .check_kflag_member = btf_int_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2175) .log_details = btf_int_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2176) .show = btf_int_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2177) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2178)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2179) static int btf_modifier_check_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2180) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2181) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2182) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2183) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2184) const struct btf_type *resolved_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2185) u32 resolved_type_id = member->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2186) struct btf_member resolved_member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2187) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2188)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2189) resolved_type = btf_type_id_size(btf, &resolved_type_id, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2190) if (!resolved_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2191) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2192) "Invalid member");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2193) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2194) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2195)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2196) resolved_member = *member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2197) resolved_member.type = resolved_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2198)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2199) return btf_type_ops(resolved_type)->check_member(env, struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2200) &resolved_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2201) resolved_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2202) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2204) static int btf_modifier_check_kflag_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2205) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2206) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2207) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2208) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2209) const struct btf_type *resolved_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2210) u32 resolved_type_id = member->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2211) struct btf_member resolved_member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2212) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2213)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2214) resolved_type = btf_type_id_size(btf, &resolved_type_id, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2215) if (!resolved_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2216) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2217) "Invalid member");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2218) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2219) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2220)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2221) resolved_member = *member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2222) resolved_member.type = resolved_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2223)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2224) return btf_type_ops(resolved_type)->check_kflag_member(env, struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2225) &resolved_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2226) resolved_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2227) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2229) static int btf_ptr_check_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2230) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2231) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2232) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2233) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2234) u32 struct_size, struct_bits_off, bytes_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2235)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2236) struct_size = struct_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2237) struct_bits_off = member->offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2238) bytes_offset = BITS_ROUNDDOWN_BYTES(struct_bits_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2239)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2240) if (BITS_PER_BYTE_MASKED(struct_bits_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2241) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2242) "Member is not byte aligned");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2243) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2244) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2245)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2246) if (struct_size - bytes_offset < sizeof(void *)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2247) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2248) "Member exceeds struct_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2249) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2250) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2251)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2252) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2253) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2254)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2255) static int btf_ref_type_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2256) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2257) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2258) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2259) if (btf_type_vlen(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2260) btf_verifier_log_type(env, t, "vlen != 0");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2261) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2262) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2263)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2264) if (btf_type_kflag(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2265) btf_verifier_log_type(env, t, "Invalid btf_info kind_flag");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2266) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2267) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2268)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2269) if (!BTF_TYPE_ID_VALID(t->type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2270) btf_verifier_log_type(env, t, "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2271) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2272) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2273)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2274) /* typedef type must have a valid name, and other ref types,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2275) * volatile, const, restrict, should have a null name.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2276) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2277) if (BTF_INFO_KIND(t->info) == BTF_KIND_TYPEDEF) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2278) if (!t->name_off ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2279) !btf_name_valid_identifier(env->btf, t->name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2280) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2281) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2282) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2283) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2284) if (t->name_off) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2285) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2286) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2287) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2288) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2289)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2290) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2291)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2292) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2293) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2294)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2295) static int btf_modifier_resolve(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2296) const struct resolve_vertex *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2297) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2298) const struct btf_type *t = v->t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2299) const struct btf_type *next_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2300) u32 next_type_id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2301) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2302)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2303) next_type = btf_type_by_id(btf, next_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2304) if (!next_type || btf_type_is_resolve_source_only(next_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2305) btf_verifier_log_type(env, v->t, "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2306) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2307) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2308)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2309) if (!env_type_is_resolve_sink(env, next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2310) !env_type_is_resolved(env, next_type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2311) return env_stack_push(env, next_type, next_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2312)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2313) /* Figure out the resolved next_type_id with size.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2314) * They will be stored in the current modifier's
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2315) * resolved_ids and resolved_sizes such that it can
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2316) * save us a few type-following when we use it later (e.g. in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2317) * pretty print).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2318) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2319) if (!btf_type_id_size(btf, &next_type_id, NULL)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2320) if (env_type_is_resolved(env, next_type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2321) next_type = btf_type_id_resolve(btf, &next_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2322)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2323) /* "typedef void new_void", "const void"...etc */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2324) if (!btf_type_is_void(next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2325) !btf_type_is_fwd(next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2326) !btf_type_is_func_proto(next_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2327) btf_verifier_log_type(env, v->t, "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2328) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2329) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2330) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2331)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2332) env_stack_pop_resolved(env, next_type_id, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2333)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2334) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2335) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2336)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2337) static int btf_var_resolve(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2338) const struct resolve_vertex *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2339) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2340) const struct btf_type *next_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2341) const struct btf_type *t = v->t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2342) u32 next_type_id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2343) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2344)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2345) next_type = btf_type_by_id(btf, next_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2346) if (!next_type || btf_type_is_resolve_source_only(next_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2347) btf_verifier_log_type(env, v->t, "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2348) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2349) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2350)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2351) if (!env_type_is_resolve_sink(env, next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2352) !env_type_is_resolved(env, next_type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2353) return env_stack_push(env, next_type, next_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2354)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2355) if (btf_type_is_modifier(next_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2356) const struct btf_type *resolved_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2357) u32 resolved_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2358)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2359) resolved_type_id = next_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2360) resolved_type = btf_type_id_resolve(btf, &resolved_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2361)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2362) if (btf_type_is_ptr(resolved_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2363) !env_type_is_resolve_sink(env, resolved_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2364) !env_type_is_resolved(env, resolved_type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2365) return env_stack_push(env, resolved_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2366) resolved_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2367) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2368)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2369) /* We must resolve to something concrete at this point, no
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2370) * forward types or similar that would resolve to size of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2371) * zero is allowed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2372) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2373) if (!btf_type_id_size(btf, &next_type_id, NULL)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2374) btf_verifier_log_type(env, v->t, "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2375) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2376) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2377)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2378) env_stack_pop_resolved(env, next_type_id, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2379)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2380) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2381) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2382)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2383) static int btf_ptr_resolve(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2384) const struct resolve_vertex *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2385) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2386) const struct btf_type *next_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2387) const struct btf_type *t = v->t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2388) u32 next_type_id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2389) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2390)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2391) next_type = btf_type_by_id(btf, next_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2392) if (!next_type || btf_type_is_resolve_source_only(next_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2393) btf_verifier_log_type(env, v->t, "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2394) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2395) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2396)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2397) if (!env_type_is_resolve_sink(env, next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2398) !env_type_is_resolved(env, next_type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2399) return env_stack_push(env, next_type, next_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2400)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2401) /* If the modifier was RESOLVED during RESOLVE_STRUCT_OR_ARRAY,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2402) * the modifier may have stopped resolving when it was resolved
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2403) * to a ptr (last-resolved-ptr).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2404) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2405) * We now need to continue from the last-resolved-ptr to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2406) * ensure the last-resolved-ptr will not referring back to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2407) * the currenct ptr (t).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2408) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2409) if (btf_type_is_modifier(next_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2410) const struct btf_type *resolved_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2411) u32 resolved_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2412)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2413) resolved_type_id = next_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2414) resolved_type = btf_type_id_resolve(btf, &resolved_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2415)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2416) if (btf_type_is_ptr(resolved_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2417) !env_type_is_resolve_sink(env, resolved_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2418) !env_type_is_resolved(env, resolved_type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2419) return env_stack_push(env, resolved_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2420) resolved_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2421) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2422)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2423) if (!btf_type_id_size(btf, &next_type_id, NULL)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2424) if (env_type_is_resolved(env, next_type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2425) next_type = btf_type_id_resolve(btf, &next_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2426)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2427) if (!btf_type_is_void(next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2428) !btf_type_is_fwd(next_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2429) !btf_type_is_func_proto(next_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2430) btf_verifier_log_type(env, v->t, "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2431) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2432) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2433) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2434)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2435) env_stack_pop_resolved(env, next_type_id, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2436)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2437) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2438) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2439)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2440) static void btf_modifier_show(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2441) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2442) u32 type_id, void *data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2443) u8 bits_offset, struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2444) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2445) if (btf->resolved_ids)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2446) t = btf_type_id_resolve(btf, &type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2447) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2448) t = btf_type_skip_modifiers(btf, type_id, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2449)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2450) btf_type_ops(t)->show(btf, t, type_id, data, bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2451) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2452)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2453) static void btf_var_show(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2454) u32 type_id, void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2455) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2456) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2457) t = btf_type_id_resolve(btf, &type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2458)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2459) btf_type_ops(t)->show(btf, t, type_id, data, bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2460) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2461)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2462) static void btf_ptr_show(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2463) u32 type_id, void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2464) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2465) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2466) void *safe_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2467)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2468) safe_data = btf_show_start_type(show, t, type_id, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2469) if (!safe_data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2470) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2471)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2472) /* It is a hashed value unless BTF_SHOW_PTR_RAW is specified */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2473) if (show->flags & BTF_SHOW_PTR_RAW)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2474) btf_show_type_value(show, "0x%px", *(void **)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2475) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2476) btf_show_type_value(show, "0x%p", *(void **)safe_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2477) btf_show_end_type(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2478) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2479)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2480) static void btf_ref_type_log(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2481) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2482) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2483) btf_verifier_log(env, "type_id=%u", t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2484) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2485)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2486) static struct btf_kind_operations modifier_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2487) .check_meta = btf_ref_type_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2488) .resolve = btf_modifier_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2489) .check_member = btf_modifier_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2490) .check_kflag_member = btf_modifier_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2491) .log_details = btf_ref_type_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2492) .show = btf_modifier_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2493) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2494)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2495) static struct btf_kind_operations ptr_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2496) .check_meta = btf_ref_type_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2497) .resolve = btf_ptr_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2498) .check_member = btf_ptr_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2499) .check_kflag_member = btf_generic_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2500) .log_details = btf_ref_type_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2501) .show = btf_ptr_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2502) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2503)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2504) static s32 btf_fwd_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2505) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2506) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2507) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2508) if (btf_type_vlen(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2509) btf_verifier_log_type(env, t, "vlen != 0");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2510) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2511) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2512)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2513) if (t->type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2514) btf_verifier_log_type(env, t, "type != 0");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2515) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2516) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2517)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2518) /* fwd type must have a valid name */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2519) if (!t->name_off ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2520) !btf_name_valid_identifier(env->btf, t->name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2521) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2522) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2523) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2524)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2525) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2526)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2527) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2528) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2529)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2530) static void btf_fwd_type_log(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2531) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2532) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2533) btf_verifier_log(env, "%s", btf_type_kflag(t) ? "union" : "struct");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2534) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2535)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2536) static struct btf_kind_operations fwd_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2537) .check_meta = btf_fwd_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2538) .resolve = btf_df_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2539) .check_member = btf_df_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2540) .check_kflag_member = btf_df_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2541) .log_details = btf_fwd_type_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2542) .show = btf_df_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2543) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2544)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2545) static int btf_array_check_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2546) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2547) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2548) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2549) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2550) u32 struct_bits_off = member->offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2551) u32 struct_size, bytes_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2552) u32 array_type_id, array_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2553) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2554)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2555) if (BITS_PER_BYTE_MASKED(struct_bits_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2556) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2557) "Member is not byte aligned");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2558) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2559) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2560)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2561) array_type_id = member->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2562) btf_type_id_size(btf, &array_type_id, &array_size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2563) struct_size = struct_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2564) bytes_offset = BITS_ROUNDDOWN_BYTES(struct_bits_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2565) if (struct_size - bytes_offset < array_size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2566) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2567) "Member exceeds struct_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2568) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2569) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2570)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2571) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2572) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2573)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2574) static s32 btf_array_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2575) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2576) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2577) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2578) const struct btf_array *array = btf_type_array(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2579) u32 meta_needed = sizeof(*array);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2580)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2581) if (meta_left < meta_needed) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2582) btf_verifier_log_basic(env, t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2583) "meta_left:%u meta_needed:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2584) meta_left, meta_needed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2585) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2586) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2587)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2588) /* array type should not have a name */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2589) if (t->name_off) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2590) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2591) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2592) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2593)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2594) if (btf_type_vlen(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2595) btf_verifier_log_type(env, t, "vlen != 0");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2596) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2597) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2598)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2599) if (btf_type_kflag(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2600) btf_verifier_log_type(env, t, "Invalid btf_info kind_flag");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2601) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2602) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2603)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2604) if (t->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2605) btf_verifier_log_type(env, t, "size != 0");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2606) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2607) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2608)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2609) /* Array elem type and index type cannot be in type void,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2610) * so !array->type and !array->index_type are not allowed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2611) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2612) if (!array->type || !BTF_TYPE_ID_VALID(array->type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2613) btf_verifier_log_type(env, t, "Invalid elem");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2614) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2615) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2616)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2617) if (!array->index_type || !BTF_TYPE_ID_VALID(array->index_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2618) btf_verifier_log_type(env, t, "Invalid index");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2619) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2620) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2621)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2622) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2623)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2624) return meta_needed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2625) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2626)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2627) static int btf_array_resolve(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2628) const struct resolve_vertex *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2629) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2630) const struct btf_array *array = btf_type_array(v->t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2631) const struct btf_type *elem_type, *index_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2632) u32 elem_type_id, index_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2633) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2634) u32 elem_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2635)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2636) /* Check array->index_type */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2637) index_type_id = array->index_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2638) index_type = btf_type_by_id(btf, index_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2639) if (btf_type_nosize_or_null(index_type) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2640) btf_type_is_resolve_source_only(index_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2641) btf_verifier_log_type(env, v->t, "Invalid index");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2642) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2643) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2644)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2645) if (!env_type_is_resolve_sink(env, index_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2646) !env_type_is_resolved(env, index_type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2647) return env_stack_push(env, index_type, index_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2648)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2649) index_type = btf_type_id_size(btf, &index_type_id, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2650) if (!index_type || !btf_type_is_int(index_type) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2651) !btf_type_int_is_regular(index_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2652) btf_verifier_log_type(env, v->t, "Invalid index");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2653) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2654) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2655)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2656) /* Check array->type */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2657) elem_type_id = array->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2658) elem_type = btf_type_by_id(btf, elem_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2659) if (btf_type_nosize_or_null(elem_type) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2660) btf_type_is_resolve_source_only(elem_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2661) btf_verifier_log_type(env, v->t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2662) "Invalid elem");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2663) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2664) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2665)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2666) if (!env_type_is_resolve_sink(env, elem_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2667) !env_type_is_resolved(env, elem_type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2668) return env_stack_push(env, elem_type, elem_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2669)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2670) elem_type = btf_type_id_size(btf, &elem_type_id, &elem_size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2671) if (!elem_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2672) btf_verifier_log_type(env, v->t, "Invalid elem");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2673) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2674) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2675)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2676) if (btf_type_is_int(elem_type) && !btf_type_int_is_regular(elem_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2677) btf_verifier_log_type(env, v->t, "Invalid array of int");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2678) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2679) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2680)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2681) if (array->nelems && elem_size > U32_MAX / array->nelems) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2682) btf_verifier_log_type(env, v->t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2683) "Array size overflows U32_MAX");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2684) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2685) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2686)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2687) env_stack_pop_resolved(env, elem_type_id, elem_size * array->nelems);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2688)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2689) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2690) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2691)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2692) static void btf_array_log(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2693) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2694) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2695) const struct btf_array *array = btf_type_array(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2696)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2697) btf_verifier_log(env, "type_id=%u index_type_id=%u nr_elems=%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2698) array->type, array->index_type, array->nelems);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2699) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2700)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2701) static void __btf_array_show(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2702) u32 type_id, void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2703) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2704) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2705) const struct btf_array *array = btf_type_array(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2706) const struct btf_kind_operations *elem_ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2707) const struct btf_type *elem_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2708) u32 i, elem_size = 0, elem_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2709) u16 encoding = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2710)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2711) elem_type_id = array->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2712) elem_type = btf_type_skip_modifiers(btf, elem_type_id, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2713) if (elem_type && btf_type_has_size(elem_type))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2714) elem_size = elem_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2715)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2716) if (elem_type && btf_type_is_int(elem_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2717) u32 int_type = btf_type_int(elem_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2718)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2719) encoding = BTF_INT_ENCODING(int_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2720)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2721) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2722) * BTF_INT_CHAR encoding never seems to be set for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2723) * char arrays, so if size is 1 and element is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2724) * printable as a char, we'll do that.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2725) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2726) if (elem_size == 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2727) encoding = BTF_INT_CHAR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2728) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2729)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2730) if (!btf_show_start_array_type(show, t, type_id, encoding, data))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2731) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2732)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2733) if (!elem_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2734) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2735) elem_ops = btf_type_ops(elem_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2736)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2737) for (i = 0; i < array->nelems; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2738)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2739) btf_show_start_array_member(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2740)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2741) elem_ops->show(btf, elem_type, elem_type_id, data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2742) bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2743) data += elem_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2744)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2745) btf_show_end_array_member(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2746)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2747) if (show->state.array_terminated)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2748) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2749) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2750) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2751) btf_show_end_array_type(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2752) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2753)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2754) static void btf_array_show(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2755) u32 type_id, void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2756) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2757) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2758) const struct btf_member *m = show->state.member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2759)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2760) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2761) * First check if any members would be shown (are non-zero).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2762) * See comments above "struct btf_show" definition for more
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2763) * details on how this works at a high-level.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2764) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2765) if (show->state.depth > 0 && !(show->flags & BTF_SHOW_ZERO)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2766) if (!show->state.depth_check) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2767) show->state.depth_check = show->state.depth + 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2768) show->state.depth_to_show = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2769) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2770) __btf_array_show(btf, t, type_id, data, bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2771) show->state.member = m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2772)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2773) if (show->state.depth_check != show->state.depth + 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2774) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2775) show->state.depth_check = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2776)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2777) if (show->state.depth_to_show <= show->state.depth)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2778) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2779) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2780) * Reaching here indicates we have recursed and found
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2781) * non-zero array member(s).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2782) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2783) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2784) __btf_array_show(btf, t, type_id, data, bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2785) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2786)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2787) static struct btf_kind_operations array_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2788) .check_meta = btf_array_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2789) .resolve = btf_array_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2790) .check_member = btf_array_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2791) .check_kflag_member = btf_generic_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2792) .log_details = btf_array_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2793) .show = btf_array_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2794) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2795)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2796) static int btf_struct_check_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2797) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2798) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2799) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2800) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2801) u32 struct_bits_off = member->offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2802) u32 struct_size, bytes_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2803)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2804) if (BITS_PER_BYTE_MASKED(struct_bits_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2805) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2806) "Member is not byte aligned");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2807) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2808) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2809)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2810) struct_size = struct_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2811) bytes_offset = BITS_ROUNDDOWN_BYTES(struct_bits_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2812) if (struct_size - bytes_offset < member_type->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2813) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2814) "Member exceeds struct_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2815) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2816) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2817)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2818) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2819) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2820)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2821) static s32 btf_struct_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2822) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2823) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2824) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2825) bool is_union = BTF_INFO_KIND(t->info) == BTF_KIND_UNION;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2826) const struct btf_member *member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2827) u32 meta_needed, last_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2828) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2829) u32 struct_size = t->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2830) u32 offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2831) u16 i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2832)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2833) meta_needed = btf_type_vlen(t) * sizeof(*member);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2834) if (meta_left < meta_needed) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2835) btf_verifier_log_basic(env, t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2836) "meta_left:%u meta_needed:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2837) meta_left, meta_needed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2838) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2839) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2840)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2841) /* struct type either no name or a valid one */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2842) if (t->name_off &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2843) !btf_name_valid_identifier(env->btf, t->name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2844) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2845) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2846) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2847)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2848) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2849)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2850) last_offset = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2851) for_each_member(i, t, member) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2852) if (!btf_name_offset_valid(btf, member->name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2853) btf_verifier_log_member(env, t, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2854) "Invalid member name_offset:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2855) member->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2856) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2857) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2858)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2859) /* struct member either no name or a valid one */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2860) if (member->name_off &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2861) !btf_name_valid_identifier(btf, member->name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2862) btf_verifier_log_member(env, t, member, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2863) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2864) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2865) /* A member cannot be in type void */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2866) if (!member->type || !BTF_TYPE_ID_VALID(member->type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2867) btf_verifier_log_member(env, t, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2868) "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2869) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2870) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2871)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2872) offset = btf_member_bit_offset(t, member);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2873) if (is_union && offset) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2874) btf_verifier_log_member(env, t, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2875) "Invalid member bits_offset");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2876) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2877) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2878)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2879) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2880) * ">" instead of ">=" because the last member could be
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2881) * "char a[0];"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2882) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2883) if (last_offset > offset) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2884) btf_verifier_log_member(env, t, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2885) "Invalid member bits_offset");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2886) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2887) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2888)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2889) if (BITS_ROUNDUP_BYTES(offset) > struct_size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2890) btf_verifier_log_member(env, t, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2891) "Member bits_offset exceeds its struct size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2892) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2893) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2894)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2895) btf_verifier_log_member(env, t, member, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2896) last_offset = offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2897) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2898)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2899) return meta_needed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2900) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2901)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2902) static int btf_struct_resolve(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2903) const struct resolve_vertex *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2904) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2905) const struct btf_member *member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2906) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2907) u16 i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2908)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2909) /* Before continue resolving the next_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2910) * ensure the last member is indeed resolved to a
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2911) * type with size info.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2912) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2913) if (v->next_member) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2914) const struct btf_type *last_member_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2915) const struct btf_member *last_member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2916) u16 last_member_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2917)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2918) last_member = btf_type_member(v->t) + v->next_member - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2919) last_member_type_id = last_member->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2920) if (WARN_ON_ONCE(!env_type_is_resolved(env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2921) last_member_type_id)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2922) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2923)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2924) last_member_type = btf_type_by_id(env->btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2925) last_member_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2926) if (btf_type_kflag(v->t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2927) err = btf_type_ops(last_member_type)->check_kflag_member(env, v->t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2928) last_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2929) last_member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2930) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2931) err = btf_type_ops(last_member_type)->check_member(env, v->t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2932) last_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2933) last_member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2934) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2935) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2936) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2937)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2938) for_each_member_from(i, v->next_member, v->t, member) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2939) u32 member_type_id = member->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2940) const struct btf_type *member_type = btf_type_by_id(env->btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2941) member_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2942)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2943) if (btf_type_nosize_or_null(member_type) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2944) btf_type_is_resolve_source_only(member_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2945) btf_verifier_log_member(env, v->t, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2946) "Invalid member");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2947) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2948) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2949)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2950) if (!env_type_is_resolve_sink(env, member_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2951) !env_type_is_resolved(env, member_type_id)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2952) env_stack_set_next_member(env, i + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2953) return env_stack_push(env, member_type, member_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2954) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2955)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2956) if (btf_type_kflag(v->t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2957) err = btf_type_ops(member_type)->check_kflag_member(env, v->t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2958) member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2959) member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2960) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2961) err = btf_type_ops(member_type)->check_member(env, v->t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2962) member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2963) member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2964) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2965) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2966) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2967)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2968) env_stack_pop_resolved(env, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2969)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2970) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2971) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2972)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2973) static void btf_struct_log(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2974) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2975) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2976) btf_verifier_log(env, "size=%u vlen=%u", t->size, btf_type_vlen(t));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2977) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2978)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2979) /* find 'struct bpf_spin_lock' in map value.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2980) * return >= 0 offset if found
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2981) * and < 0 in case of error
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2982) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2983) int btf_find_spin_lock(const struct btf *btf, const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2984) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2985) const struct btf_member *member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2986) u32 i, off = -ENOENT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2987)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2988) if (!__btf_type_is_struct(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2989) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2990)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2991) for_each_member(i, t, member) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2992) const struct btf_type *member_type = btf_type_by_id(btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2993) member->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2994) if (!__btf_type_is_struct(member_type))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2995) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2996) if (member_type->size != sizeof(struct bpf_spin_lock))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2997) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2998) if (strcmp(__btf_name_by_offset(btf, member_type->name_off),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2999) "bpf_spin_lock"))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3000) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3001) if (off != -ENOENT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3002) /* only one 'struct bpf_spin_lock' is allowed */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3003) return -E2BIG;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3004) off = btf_member_bit_offset(t, member);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3005) if (off % 8)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3006) /* valid C code cannot generate such BTF */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3007) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3008) off /= 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3009) if (off % __alignof__(struct bpf_spin_lock))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3010) /* valid struct bpf_spin_lock will be 4 byte aligned */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3011) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3012) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3013) return off;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3014) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3015)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3016) static void __btf_struct_show(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3017) u32 type_id, void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3018) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3019) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3020) const struct btf_member *member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3021) void *safe_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3022) u32 i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3023)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3024) safe_data = btf_show_start_struct_type(show, t, type_id, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3025) if (!safe_data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3026) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3027)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3028) for_each_member(i, t, member) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3029) const struct btf_type *member_type = btf_type_by_id(btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3030) member->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3031) const struct btf_kind_operations *ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3032) u32 member_offset, bitfield_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3033) u32 bytes_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3034) u8 bits8_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3035)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3036) btf_show_start_member(show, member);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3037)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3038) member_offset = btf_member_bit_offset(t, member);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3039) bitfield_size = btf_member_bitfield_size(t, member);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3040) bytes_offset = BITS_ROUNDDOWN_BYTES(member_offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3041) bits8_offset = BITS_PER_BYTE_MASKED(member_offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3042) if (bitfield_size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3043) safe_data = btf_show_start_type(show, member_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3044) member->type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3045) data + bytes_offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3046) if (safe_data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3047) btf_bitfield_show(safe_data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3048) bits8_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3049) bitfield_size, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3050) btf_show_end_type(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3051) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3052) ops = btf_type_ops(member_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3053) ops->show(btf, member_type, member->type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3054) data + bytes_offset, bits8_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3055) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3056)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3057) btf_show_end_member(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3058) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3059)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3060) btf_show_end_struct_type(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3061) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3062)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3063) static void btf_struct_show(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3064) u32 type_id, void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3065) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3066) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3067) const struct btf_member *m = show->state.member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3068)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3069) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3070) * First check if any members would be shown (are non-zero).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3071) * See comments above "struct btf_show" definition for more
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3072) * details on how this works at a high-level.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3073) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3074) if (show->state.depth > 0 && !(show->flags & BTF_SHOW_ZERO)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3075) if (!show->state.depth_check) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3076) show->state.depth_check = show->state.depth + 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3077) show->state.depth_to_show = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3078) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3079) __btf_struct_show(btf, t, type_id, data, bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3080) /* Restore saved member data here */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3081) show->state.member = m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3082) if (show->state.depth_check != show->state.depth + 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3083) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3084) show->state.depth_check = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3085)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3086) if (show->state.depth_to_show <= show->state.depth)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3087) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3088) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3089) * Reaching here indicates we have recursed and found
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3090) * non-zero child values.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3091) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3092) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3093)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3094) __btf_struct_show(btf, t, type_id, data, bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3095) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3096)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3097) static struct btf_kind_operations struct_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3098) .check_meta = btf_struct_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3099) .resolve = btf_struct_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3100) .check_member = btf_struct_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3101) .check_kflag_member = btf_generic_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3102) .log_details = btf_struct_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3103) .show = btf_struct_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3104) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3105)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3106) static int btf_enum_check_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3107) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3108) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3109) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3110) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3111) u32 struct_bits_off = member->offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3112) u32 struct_size, bytes_offset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3113)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3114) if (BITS_PER_BYTE_MASKED(struct_bits_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3115) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3116) "Member is not byte aligned");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3117) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3118) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3119)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3120) struct_size = struct_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3121) bytes_offset = BITS_ROUNDDOWN_BYTES(struct_bits_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3122) if (struct_size - bytes_offset < member_type->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3123) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3124) "Member exceeds struct_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3125) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3126) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3127)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3128) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3129) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3130)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3131) static int btf_enum_check_kflag_member(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3132) const struct btf_type *struct_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3133) const struct btf_member *member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3134) const struct btf_type *member_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3135) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3136) u32 struct_bits_off, nr_bits, bytes_end, struct_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3137) u32 int_bitsize = sizeof(int) * BITS_PER_BYTE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3138)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3139) struct_bits_off = BTF_MEMBER_BIT_OFFSET(member->offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3140) nr_bits = BTF_MEMBER_BITFIELD_SIZE(member->offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3141) if (!nr_bits) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3142) if (BITS_PER_BYTE_MASKED(struct_bits_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3143) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3144) "Member is not byte aligned");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3145) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3146) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3147)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3148) nr_bits = int_bitsize;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3149) } else if (nr_bits > int_bitsize) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3150) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3151) "Invalid member bitfield_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3152) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3153) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3154)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3155) struct_size = struct_type->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3156) bytes_end = BITS_ROUNDUP_BYTES(struct_bits_off + nr_bits);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3157) if (struct_size < bytes_end) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3158) btf_verifier_log_member(env, struct_type, member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3159) "Member exceeds struct_size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3160) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3161) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3162)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3163) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3164) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3165)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3166) static s32 btf_enum_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3167) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3168) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3169) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3170) const struct btf_enum *enums = btf_type_enum(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3171) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3172) u16 i, nr_enums;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3173) u32 meta_needed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3174)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3175) nr_enums = btf_type_vlen(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3176) meta_needed = nr_enums * sizeof(*enums);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3177)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3178) if (meta_left < meta_needed) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3179) btf_verifier_log_basic(env, t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3180) "meta_left:%u meta_needed:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3181) meta_left, meta_needed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3182) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3183) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3184)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3185) if (btf_type_kflag(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3186) btf_verifier_log_type(env, t, "Invalid btf_info kind_flag");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3187) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3188) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3189)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3190) if (t->size > 8 || !is_power_of_2(t->size)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3191) btf_verifier_log_type(env, t, "Unexpected size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3192) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3193) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3194)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3195) /* enum type either no name or a valid one */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3196) if (t->name_off &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3197) !btf_name_valid_identifier(env->btf, t->name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3198) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3199) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3200) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3201)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3202) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3204) for (i = 0; i < nr_enums; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3205) if (!btf_name_offset_valid(btf, enums[i].name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3206) btf_verifier_log(env, "\tInvalid name_offset:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3207) enums[i].name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3208) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3209) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3210)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3211) /* enum member must have a valid name */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3212) if (!enums[i].name_off ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3213) !btf_name_valid_identifier(btf, enums[i].name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3214) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3215) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3216) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3217)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3218) if (env->log.level == BPF_LOG_KERNEL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3219) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3220) btf_verifier_log(env, "\t%s val=%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3221) __btf_name_by_offset(btf, enums[i].name_off),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3222) enums[i].val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3223) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3224)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3225) return meta_needed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3226) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3227)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3228) static void btf_enum_log(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3229) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3230) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3231) btf_verifier_log(env, "size=%u vlen=%u", t->size, btf_type_vlen(t));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3232) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3233)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3234) static void btf_enum_show(const struct btf *btf, const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3235) u32 type_id, void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3236) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3237) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3238) const struct btf_enum *enums = btf_type_enum(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3239) u32 i, nr_enums = btf_type_vlen(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3240) void *safe_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3241) int v;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3242)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3243) safe_data = btf_show_start_type(show, t, type_id, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3244) if (!safe_data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3245) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3246)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3247) v = *(int *)safe_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3248)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3249) for (i = 0; i < nr_enums; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3250) if (v != enums[i].val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3251) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3252)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3253) btf_show_type_value(show, "%s",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3254) __btf_name_by_offset(btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3255) enums[i].name_off));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3256)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3257) btf_show_end_type(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3258) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3259) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3260)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3261) btf_show_type_value(show, "%d", v);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3262) btf_show_end_type(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3263) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3264)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3265) static struct btf_kind_operations enum_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3266) .check_meta = btf_enum_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3267) .resolve = btf_df_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3268) .check_member = btf_enum_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3269) .check_kflag_member = btf_enum_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3270) .log_details = btf_enum_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3271) .show = btf_enum_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3272) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3273)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3274) static s32 btf_func_proto_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3275) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3276) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3277) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3278) u32 meta_needed = btf_type_vlen(t) * sizeof(struct btf_param);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3279)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3280) if (meta_left < meta_needed) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3281) btf_verifier_log_basic(env, t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3282) "meta_left:%u meta_needed:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3283) meta_left, meta_needed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3284) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3285) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3286)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3287) if (t->name_off) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3288) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3289) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3290) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3291)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3292) if (btf_type_kflag(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3293) btf_verifier_log_type(env, t, "Invalid btf_info kind_flag");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3294) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3295) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3296)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3297) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3298)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3299) return meta_needed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3300) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3301)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3302) static void btf_func_proto_log(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3303) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3304) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3305) const struct btf_param *args = (const struct btf_param *)(t + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3306) u16 nr_args = btf_type_vlen(t), i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3307)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3308) btf_verifier_log(env, "return=%u args=(", t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3309) if (!nr_args) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3310) btf_verifier_log(env, "void");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3311) goto done;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3312) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3313)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3314) if (nr_args == 1 && !args[0].type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3315) /* Only one vararg */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3316) btf_verifier_log(env, "vararg");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3317) goto done;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3318) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3319)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3320) btf_verifier_log(env, "%u %s", args[0].type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3321) __btf_name_by_offset(env->btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3322) args[0].name_off));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3323) for (i = 1; i < nr_args - 1; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3324) btf_verifier_log(env, ", %u %s", args[i].type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3325) __btf_name_by_offset(env->btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3326) args[i].name_off));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3327)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3328) if (nr_args > 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3329) const struct btf_param *last_arg = &args[nr_args - 1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3330)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3331) if (last_arg->type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3332) btf_verifier_log(env, ", %u %s", last_arg->type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3333) __btf_name_by_offset(env->btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3334) last_arg->name_off));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3335) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3336) btf_verifier_log(env, ", vararg");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3337) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3338)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3339) done:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3340) btf_verifier_log(env, ")");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3341) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3342)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3343) static struct btf_kind_operations func_proto_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3344) .check_meta = btf_func_proto_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3345) .resolve = btf_df_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3346) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3347) * BTF_KIND_FUNC_PROTO cannot be directly referred by
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3348) * a struct's member.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3349) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3350) * It should be a funciton pointer instead.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3351) * (i.e. struct's member -> BTF_KIND_PTR -> BTF_KIND_FUNC_PROTO)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3352) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3353) * Hence, there is no btf_func_check_member().
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3354) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3355) .check_member = btf_df_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3356) .check_kflag_member = btf_df_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3357) .log_details = btf_func_proto_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3358) .show = btf_df_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3359) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3360)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3361) static s32 btf_func_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3362) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3363) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3364) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3365) if (!t->name_off ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3366) !btf_name_valid_identifier(env->btf, t->name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3367) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3368) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3369) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3370)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3371) if (btf_type_vlen(t) > BTF_FUNC_GLOBAL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3372) btf_verifier_log_type(env, t, "Invalid func linkage");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3373) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3374) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3375)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3376) if (btf_type_kflag(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3377) btf_verifier_log_type(env, t, "Invalid btf_info kind_flag");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3378) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3379) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3380)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3381) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3382)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3383) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3384) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3385)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3386) static struct btf_kind_operations func_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3387) .check_meta = btf_func_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3388) .resolve = btf_df_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3389) .check_member = btf_df_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3390) .check_kflag_member = btf_df_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3391) .log_details = btf_ref_type_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3392) .show = btf_df_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3393) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3394)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3395) static s32 btf_var_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3396) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3397) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3398) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3399) const struct btf_var *var;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3400) u32 meta_needed = sizeof(*var);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3401)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3402) if (meta_left < meta_needed) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3403) btf_verifier_log_basic(env, t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3404) "meta_left:%u meta_needed:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3405) meta_left, meta_needed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3406) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3407) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3408)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3409) if (btf_type_vlen(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3410) btf_verifier_log_type(env, t, "vlen != 0");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3411) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3412) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3413)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3414) if (btf_type_kflag(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3415) btf_verifier_log_type(env, t, "Invalid btf_info kind_flag");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3416) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3417) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3418)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3419) if (!t->name_off ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3420) !__btf_name_valid(env->btf, t->name_off, true)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3421) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3422) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3423) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3424)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3425) /* A var cannot be in type void */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3426) if (!t->type || !BTF_TYPE_ID_VALID(t->type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3427) btf_verifier_log_type(env, t, "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3428) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3429) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3430)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3431) var = btf_type_var(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3432) if (var->linkage != BTF_VAR_STATIC &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3433) var->linkage != BTF_VAR_GLOBAL_ALLOCATED) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3434) btf_verifier_log_type(env, t, "Linkage not supported");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3435) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3436) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3437)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3438) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3439)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3440) return meta_needed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3441) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3442)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3443) static void btf_var_log(struct btf_verifier_env *env, const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3444) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3445) const struct btf_var *var = btf_type_var(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3446)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3447) btf_verifier_log(env, "type_id=%u linkage=%u", t->type, var->linkage);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3448) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3449)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3450) static const struct btf_kind_operations var_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3451) .check_meta = btf_var_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3452) .resolve = btf_var_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3453) .check_member = btf_df_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3454) .check_kflag_member = btf_df_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3455) .log_details = btf_var_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3456) .show = btf_var_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3457) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3458)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3459) static s32 btf_datasec_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3460) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3461) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3462) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3463) const struct btf_var_secinfo *vsi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3464) u64 last_vsi_end_off = 0, sum = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3465) u32 i, meta_needed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3466)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3467) meta_needed = btf_type_vlen(t) * sizeof(*vsi);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3468) if (meta_left < meta_needed) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3469) btf_verifier_log_basic(env, t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3470) "meta_left:%u meta_needed:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3471) meta_left, meta_needed);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3472) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3473) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3474)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3475) if (!btf_type_vlen(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3476) btf_verifier_log_type(env, t, "vlen == 0");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3477) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3478) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3479)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3480) if (!t->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3481) btf_verifier_log_type(env, t, "size == 0");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3482) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3483) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3484)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3485) if (btf_type_kflag(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3486) btf_verifier_log_type(env, t, "Invalid btf_info kind_flag");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3487) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3488) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3489)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3490) if (!t->name_off ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3491) !btf_name_valid_section(env->btf, t->name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3492) btf_verifier_log_type(env, t, "Invalid name");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3493) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3494) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3495)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3496) btf_verifier_log_type(env, t, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3497)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3498) for_each_vsi(i, t, vsi) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3499) /* A var cannot be in type void */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3500) if (!vsi->type || !BTF_TYPE_ID_VALID(vsi->type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3501) btf_verifier_log_vsi(env, t, vsi,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3502) "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3503) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3504) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3505)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3506) if (vsi->offset < last_vsi_end_off || vsi->offset >= t->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3507) btf_verifier_log_vsi(env, t, vsi,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3508) "Invalid offset");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3509) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3510) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3511)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3512) if (!vsi->size || vsi->size > t->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3513) btf_verifier_log_vsi(env, t, vsi,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3514) "Invalid size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3515) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3516) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3517)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3518) last_vsi_end_off = vsi->offset + vsi->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3519) if (last_vsi_end_off > t->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3520) btf_verifier_log_vsi(env, t, vsi,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3521) "Invalid offset+size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3522) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3523) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3524)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3525) btf_verifier_log_vsi(env, t, vsi, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3526) sum += vsi->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3527) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3528)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3529) if (t->size < sum) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3530) btf_verifier_log_type(env, t, "Invalid btf_info size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3531) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3532) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3533)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3534) return meta_needed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3535) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3536)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3537) static int btf_datasec_resolve(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3538) const struct resolve_vertex *v)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3539) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3540) const struct btf_var_secinfo *vsi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3541) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3542) u16 i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3543)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3544) for_each_vsi_from(i, v->next_member, v->t, vsi) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3545) u32 var_type_id = vsi->type, type_id, type_size = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3546) const struct btf_type *var_type = btf_type_by_id(env->btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3547) var_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3548) if (!var_type || !btf_type_is_var(var_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3549) btf_verifier_log_vsi(env, v->t, vsi,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3550) "Not a VAR kind member");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3551) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3552) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3553)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3554) if (!env_type_is_resolve_sink(env, var_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3555) !env_type_is_resolved(env, var_type_id)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3556) env_stack_set_next_member(env, i + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3557) return env_stack_push(env, var_type, var_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3558) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3559)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3560) type_id = var_type->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3561) if (!btf_type_id_size(btf, &type_id, &type_size)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3562) btf_verifier_log_vsi(env, v->t, vsi, "Invalid type");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3563) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3564) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3565)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3566) if (vsi->size < type_size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3567) btf_verifier_log_vsi(env, v->t, vsi, "Invalid size");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3568) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3569) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3570) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3571)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3572) env_stack_pop_resolved(env, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3573) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3574) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3575)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3576) static void btf_datasec_log(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3577) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3578) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3579) btf_verifier_log(env, "size=%u vlen=%u", t->size, btf_type_vlen(t));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3580) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3581)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3582) static void btf_datasec_show(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3583) const struct btf_type *t, u32 type_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3584) void *data, u8 bits_offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3585) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3586) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3587) const struct btf_var_secinfo *vsi;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3588) const struct btf_type *var;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3589) u32 i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3590)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3591) if (!btf_show_start_type(show, t, type_id, data))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3592) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3593)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3594) btf_show_type_value(show, "section (\"%s\") = {",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3595) __btf_name_by_offset(btf, t->name_off));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3596) for_each_vsi(i, t, vsi) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3597) var = btf_type_by_id(btf, vsi->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3598) if (i)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3599) btf_show(show, ",");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3600) btf_type_ops(var)->show(btf, var, vsi->type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3601) data + vsi->offset, bits_offset, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3602) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3603) btf_show_end_type(show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3604) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3605)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3606) static const struct btf_kind_operations datasec_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3607) .check_meta = btf_datasec_check_meta,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3608) .resolve = btf_datasec_resolve,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3609) .check_member = btf_df_check_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3610) .check_kflag_member = btf_df_check_kflag_member,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3611) .log_details = btf_datasec_log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3612) .show = btf_datasec_show,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3613) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3614)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3615) static int btf_func_proto_check(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3616) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3617) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3618) const struct btf_type *ret_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3619) const struct btf_param *args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3620) const struct btf *btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3621) u16 nr_args, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3622) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3623)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3624) btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3625) args = (const struct btf_param *)(t + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3626) nr_args = btf_type_vlen(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3627)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3628) /* Check func return type which could be "void" (t->type == 0) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3629) if (t->type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3630) u32 ret_type_id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3631)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3632) ret_type = btf_type_by_id(btf, ret_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3633) if (!ret_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3634) btf_verifier_log_type(env, t, "Invalid return type");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3635) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3636) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3637)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3638) if (btf_type_needs_resolve(ret_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3639) !env_type_is_resolved(env, ret_type_id)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3640) err = btf_resolve(env, ret_type, ret_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3641) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3642) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3643) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3644)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3645) /* Ensure the return type is a type that has a size */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3646) if (!btf_type_id_size(btf, &ret_type_id, NULL)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3647) btf_verifier_log_type(env, t, "Invalid return type");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3648) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3649) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3650) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3651)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3652) if (!nr_args)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3653) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3654)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3655) /* Last func arg type_id could be 0 if it is a vararg */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3656) if (!args[nr_args - 1].type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3657) if (args[nr_args - 1].name_off) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3658) btf_verifier_log_type(env, t, "Invalid arg#%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3659) nr_args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3660) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3661) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3662) nr_args--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3663) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3664)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3665) err = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3666) for (i = 0; i < nr_args; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3667) const struct btf_type *arg_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3668) u32 arg_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3669)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3670) arg_type_id = args[i].type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3671) arg_type = btf_type_by_id(btf, arg_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3672) if (!arg_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3673) btf_verifier_log_type(env, t, "Invalid arg#%u", i + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3674) err = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3675) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3676) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3677)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3678) if (args[i].name_off &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3679) (!btf_name_offset_valid(btf, args[i].name_off) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3680) !btf_name_valid_identifier(btf, args[i].name_off))) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3681) btf_verifier_log_type(env, t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3682) "Invalid arg#%u", i + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3683) err = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3684) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3685) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3686)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3687) if (btf_type_needs_resolve(arg_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3688) !env_type_is_resolved(env, arg_type_id)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3689) err = btf_resolve(env, arg_type, arg_type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3690) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3691) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3692) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3693)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3694) if (!btf_type_id_size(btf, &arg_type_id, NULL)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3695) btf_verifier_log_type(env, t, "Invalid arg#%u", i + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3696) err = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3697) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3698) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3699) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3700)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3701) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3702) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3703)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3704) static int btf_func_check(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3705) const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3706) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3707) const struct btf_type *proto_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3708) const struct btf_param *args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3709) const struct btf *btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3710) u16 nr_args, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3711)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3712) btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3713) proto_type = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3714)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3715) if (!proto_type || !btf_type_is_func_proto(proto_type)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3716) btf_verifier_log_type(env, t, "Invalid type_id");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3717) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3718) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3719)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3720) args = (const struct btf_param *)(proto_type + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3721) nr_args = btf_type_vlen(proto_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3722) for (i = 0; i < nr_args; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3723) if (!args[i].name_off && args[i].type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3724) btf_verifier_log_type(env, t, "Invalid arg#%u", i + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3725) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3726) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3727) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3728)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3729) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3730) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3731)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3732) static const struct btf_kind_operations * const kind_ops[NR_BTF_KINDS] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3733) [BTF_KIND_INT] = &int_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3734) [BTF_KIND_PTR] = &ptr_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3735) [BTF_KIND_ARRAY] = &array_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3736) [BTF_KIND_STRUCT] = &struct_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3737) [BTF_KIND_UNION] = &struct_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3738) [BTF_KIND_ENUM] = &enum_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3739) [BTF_KIND_FWD] = &fwd_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3740) [BTF_KIND_TYPEDEF] = &modifier_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3741) [BTF_KIND_VOLATILE] = &modifier_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3742) [BTF_KIND_CONST] = &modifier_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3743) [BTF_KIND_RESTRICT] = &modifier_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3744) [BTF_KIND_FUNC] = &func_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3745) [BTF_KIND_FUNC_PROTO] = &func_proto_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3746) [BTF_KIND_VAR] = &var_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3747) [BTF_KIND_DATASEC] = &datasec_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3748) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3749)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3750) static s32 btf_check_meta(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3751) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3752) u32 meta_left)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3753) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3754) u32 saved_meta_left = meta_left;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3755) s32 var_meta_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3756)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3757) if (meta_left < sizeof(*t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3758) btf_verifier_log(env, "[%u] meta_left:%u meta_needed:%zu",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3759) env->log_type_id, meta_left, sizeof(*t));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3760) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3761) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3762) meta_left -= sizeof(*t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3763)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3764) if (t->info & ~BTF_INFO_MASK) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3765) btf_verifier_log(env, "[%u] Invalid btf_info:%x",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3766) env->log_type_id, t->info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3767) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3768) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3769)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3770) if (BTF_INFO_KIND(t->info) > BTF_KIND_MAX ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3771) BTF_INFO_KIND(t->info) == BTF_KIND_UNKN) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3772) btf_verifier_log(env, "[%u] Invalid kind:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3773) env->log_type_id, BTF_INFO_KIND(t->info));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3774) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3775) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3776)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3777) if (!btf_name_offset_valid(env->btf, t->name_off)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3778) btf_verifier_log(env, "[%u] Invalid name_offset:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3779) env->log_type_id, t->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3780) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3781) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3782)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3783) var_meta_size = btf_type_ops(t)->check_meta(env, t, meta_left);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3784) if (var_meta_size < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3785) return var_meta_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3786)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3787) meta_left -= var_meta_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3788)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3789) return saved_meta_left - meta_left;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3790) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3791)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3792) static int btf_check_all_metas(struct btf_verifier_env *env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3793) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3794) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3795) struct btf_header *hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3796) void *cur, *end;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3797)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3798) hdr = &btf->hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3799) cur = btf->nohdr_data + hdr->type_off;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3800) end = cur + hdr->type_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3801)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3802) env->log_type_id = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3803) while (cur < end) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3804) struct btf_type *t = cur;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3805) s32 meta_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3806)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3807) meta_size = btf_check_meta(env, t, end - cur);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3808) if (meta_size < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3809) return meta_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3810)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3811) btf_add_type(env, t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3812) cur += meta_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3813) env->log_type_id++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3814) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3815)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3816) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3817) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3818)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3819) static bool btf_resolve_valid(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3820) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3821) u32 type_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3822) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3823) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3824)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3825) if (!env_type_is_resolved(env, type_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3826) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3827)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3828) if (btf_type_is_struct(t) || btf_type_is_datasec(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3829) return !btf->resolved_ids[type_id] &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3830) !btf->resolved_sizes[type_id];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3831)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3832) if (btf_type_is_modifier(t) || btf_type_is_ptr(t) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3833) btf_type_is_var(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3834) t = btf_type_id_resolve(btf, &type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3835) return t &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3836) !btf_type_is_modifier(t) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3837) !btf_type_is_var(t) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3838) !btf_type_is_datasec(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3839) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3840)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3841) if (btf_type_is_array(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3842) const struct btf_array *array = btf_type_array(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3843) const struct btf_type *elem_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3844) u32 elem_type_id = array->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3845) u32 elem_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3846)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3847) elem_type = btf_type_id_size(btf, &elem_type_id, &elem_size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3848) return elem_type && !btf_type_is_modifier(elem_type) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3849) (array->nelems * elem_size ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3850) btf->resolved_sizes[type_id]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3851) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3852)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3853) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3854) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3855)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3856) static int btf_resolve(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3857) const struct btf_type *t, u32 type_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3858) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3859) u32 save_log_type_id = env->log_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3860) const struct resolve_vertex *v;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3861) int err = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3862)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3863) env->resolve_mode = RESOLVE_TBD;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3864) env_stack_push(env, t, type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3865) while (!err && (v = env_stack_peak(env))) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3866) env->log_type_id = v->type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3867) err = btf_type_ops(v->t)->resolve(env, v);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3868) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3869)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3870) env->log_type_id = type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3871) if (err == -E2BIG) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3872) btf_verifier_log_type(env, t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3873) "Exceeded max resolving depth:%u",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3874) MAX_RESOLVE_DEPTH);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3875) } else if (err == -EEXIST) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3876) btf_verifier_log_type(env, t, "Loop detected");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3877) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3878)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3879) /* Final sanity check */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3880) if (!err && !btf_resolve_valid(env, t, type_id)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3881) btf_verifier_log_type(env, t, "Invalid resolve state");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3882) err = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3883) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3884)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3885) env->log_type_id = save_log_type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3886) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3887) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3888)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3889) static int btf_check_all_types(struct btf_verifier_env *env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3890) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3891) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3892) u32 type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3893) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3894)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3895) err = env_resolve_init(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3896) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3897) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3898)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3899) env->phase++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3900) for (type_id = 1; type_id <= btf->nr_types; type_id++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3901) const struct btf_type *t = btf_type_by_id(btf, type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3902)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3903) env->log_type_id = type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3904) if (btf_type_needs_resolve(t) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3905) !env_type_is_resolved(env, type_id)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3906) err = btf_resolve(env, t, type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3907) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3908) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3909) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3910)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3911) if (btf_type_is_func_proto(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3912) err = btf_func_proto_check(env, t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3913) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3914) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3915) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3916)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3917) if (btf_type_is_func(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3918) err = btf_func_check(env, t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3919) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3920) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3921) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3922) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3923)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3924) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3925) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3926)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3927) static int btf_parse_type_sec(struct btf_verifier_env *env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3928) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3929) const struct btf_header *hdr = &env->btf->hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3930) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3931)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3932) /* Type section must align to 4 bytes */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3933) if (hdr->type_off & (sizeof(u32) - 1)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3934) btf_verifier_log(env, "Unaligned type_off");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3935) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3936) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3937)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3938) if (!hdr->type_len) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3939) btf_verifier_log(env, "No type found");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3940) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3941) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3942)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3943) err = btf_check_all_metas(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3944) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3945) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3946)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3947) return btf_check_all_types(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3948) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3949)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3950) static int btf_parse_str_sec(struct btf_verifier_env *env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3951) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3952) const struct btf_header *hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3953) struct btf *btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3954) const char *start, *end;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3955)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3956) hdr = &btf->hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3957) start = btf->nohdr_data + hdr->str_off;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3958) end = start + hdr->str_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3959)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3960) if (end != btf->data + btf->data_size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3961) btf_verifier_log(env, "String section is not at the end");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3962) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3963) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3964)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3965) if (!hdr->str_len || hdr->str_len - 1 > BTF_MAX_NAME_OFFSET ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3966) start[0] || end[-1]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3967) btf_verifier_log(env, "Invalid string section");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3968) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3969) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3970)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3971) btf->strings = start;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3972)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3973) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3974) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3975)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3976) static const size_t btf_sec_info_offset[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3977) offsetof(struct btf_header, type_off),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3978) offsetof(struct btf_header, str_off),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3979) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3980)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3981) static int btf_sec_info_cmp(const void *a, const void *b)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3982) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3983) const struct btf_sec_info *x = a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3984) const struct btf_sec_info *y = b;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3985)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3986) return (int)(x->off - y->off) ? : (int)(x->len - y->len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3987) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3988)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3989) static int btf_check_sec_info(struct btf_verifier_env *env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3990) u32 btf_data_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3991) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3992) struct btf_sec_info secs[ARRAY_SIZE(btf_sec_info_offset)];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3993) u32 total, expected_total, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3994) const struct btf_header *hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3995) const struct btf *btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3996)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3997) btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3998) hdr = &btf->hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3999)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4000) /* Populate the secs from hdr */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4001) for (i = 0; i < ARRAY_SIZE(btf_sec_info_offset); i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4002) secs[i] = *(struct btf_sec_info *)((void *)hdr +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4003) btf_sec_info_offset[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4004)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4005) sort(secs, ARRAY_SIZE(btf_sec_info_offset),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4006) sizeof(struct btf_sec_info), btf_sec_info_cmp, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4007)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4008) /* Check for gaps and overlap among sections */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4009) total = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4010) expected_total = btf_data_size - hdr->hdr_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4011) for (i = 0; i < ARRAY_SIZE(btf_sec_info_offset); i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4012) if (expected_total < secs[i].off) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4013) btf_verifier_log(env, "Invalid section offset");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4014) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4015) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4016) if (total < secs[i].off) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4017) /* gap */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4018) btf_verifier_log(env, "Unsupported section found");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4019) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4020) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4021) if (total > secs[i].off) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4022) btf_verifier_log(env, "Section overlap found");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4023) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4024) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4025) if (expected_total - total < secs[i].len) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4026) btf_verifier_log(env,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4027) "Total section length too long");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4028) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4029) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4030) total += secs[i].len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4031) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4032)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4033) /* There is data other than hdr and known sections */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4034) if (expected_total != total) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4035) btf_verifier_log(env, "Unsupported section found");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4036) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4037) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4038)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4039) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4040) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4041)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4042) static int btf_parse_hdr(struct btf_verifier_env *env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4043) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4044) u32 hdr_len, hdr_copy, btf_data_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4045) const struct btf_header *hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4046) struct btf *btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4047) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4048)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4049) btf = env->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4050) btf_data_size = btf->data_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4051)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4052) if (btf_data_size <
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4053) offsetof(struct btf_header, hdr_len) + sizeof(hdr->hdr_len)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4054) btf_verifier_log(env, "hdr_len not found");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4055) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4056) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4057)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4058) hdr = btf->data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4059) hdr_len = hdr->hdr_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4060) if (btf_data_size < hdr_len) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4061) btf_verifier_log(env, "btf_header not found");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4062) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4063) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4064)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4065) /* Ensure the unsupported header fields are zero */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4066) if (hdr_len > sizeof(btf->hdr)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4067) u8 *expected_zero = btf->data + sizeof(btf->hdr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4068) u8 *end = btf->data + hdr_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4069)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4070) for (; expected_zero < end; expected_zero++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4071) if (*expected_zero) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4072) btf_verifier_log(env, "Unsupported btf_header");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4073) return -E2BIG;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4074) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4075) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4076) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4077)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4078) hdr_copy = min_t(u32, hdr_len, sizeof(btf->hdr));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4079) memcpy(&btf->hdr, btf->data, hdr_copy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4080)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4081) hdr = &btf->hdr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4082)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4083) btf_verifier_log_hdr(env, btf_data_size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4084)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4085) if (hdr->magic != BTF_MAGIC) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4086) btf_verifier_log(env, "Invalid magic");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4087) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4088) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4089)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4090) if (hdr->version != BTF_VERSION) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4091) btf_verifier_log(env, "Unsupported version");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4092) return -ENOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4093) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4094)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4095) if (hdr->flags) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4096) btf_verifier_log(env, "Unsupported flags");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4097) return -ENOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4098) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4099)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4100) if (btf_data_size == hdr->hdr_len) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4101) btf_verifier_log(env, "No data");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4102) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4103) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4104)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4105) err = btf_check_sec_info(env, btf_data_size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4106) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4107) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4108)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4109) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4110) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4111)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4112) static struct btf *btf_parse(void __user *btf_data, u32 btf_data_size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4113) u32 log_level, char __user *log_ubuf, u32 log_size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4114) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4115) struct btf_verifier_env *env = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4116) struct bpf_verifier_log *log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4117) struct btf *btf = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4118) u8 *data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4119) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4120)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4121) if (btf_data_size > BTF_MAX_SIZE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4122) return ERR_PTR(-E2BIG);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4123)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4124) env = kzalloc(sizeof(*env), GFP_KERNEL | __GFP_NOWARN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4125) if (!env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4126) return ERR_PTR(-ENOMEM);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4127)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4128) log = &env->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4129) if (log_level || log_ubuf || log_size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4130) /* user requested verbose verifier output
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4131) * and supplied buffer to store the verification trace
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4132) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4133) log->level = log_level;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4134) log->ubuf = log_ubuf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4135) log->len_total = log_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4136)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4137) /* log attributes have to be sane */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4138) if (!bpf_verifier_log_attr_valid(log)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4139) err = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4140) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4141) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4142) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4143)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4144) btf = kzalloc(sizeof(*btf), GFP_KERNEL | __GFP_NOWARN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4145) if (!btf) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4146) err = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4147) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4148) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4149) env->btf = btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4150)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4151) data = kvmalloc(btf_data_size, GFP_KERNEL | __GFP_NOWARN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4152) if (!data) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4153) err = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4154) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4155) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4156)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4157) btf->data = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4158) btf->data_size = btf_data_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4159)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4160) if (copy_from_user(data, btf_data, btf_data_size)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4161) err = -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4162) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4163) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4164)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4165) err = btf_parse_hdr(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4166) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4167) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4168)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4169) btf->nohdr_data = btf->data + btf->hdr.hdr_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4170)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4171) err = btf_parse_str_sec(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4172) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4173) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4174)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4175) err = btf_parse_type_sec(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4176) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4177) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4178)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4179) if (log->level && bpf_verifier_log_full(log)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4180) err = -ENOSPC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4181) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4182) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4183)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4184) btf_verifier_env_free(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4185) refcount_set(&btf->refcnt, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4186) return btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4187)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4188) errout:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4189) btf_verifier_env_free(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4190) if (btf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4191) btf_free(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4192) return ERR_PTR(err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4193) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4194)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4195) extern char __weak __start_BTF[];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4196) extern char __weak __stop_BTF[];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4197) extern struct btf *btf_vmlinux;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4198)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4199) #define BPF_MAP_TYPE(_id, _ops)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4200) #define BPF_LINK_TYPE(_id, _name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4201) static union {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4202) struct bpf_ctx_convert {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4203) #define BPF_PROG_TYPE(_id, _name, prog_ctx_type, kern_ctx_type) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4204) prog_ctx_type _id##_prog; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4205) kern_ctx_type _id##_kern;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4206) #include <linux/bpf_types.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4207) #undef BPF_PROG_TYPE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4208) } *__t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4209) /* 't' is written once under lock. Read many times. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4210) const struct btf_type *t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4211) } bpf_ctx_convert;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4212) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4213) #define BPF_PROG_TYPE(_id, _name, prog_ctx_type, kern_ctx_type) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4214) __ctx_convert##_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4215) #include <linux/bpf_types.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4216) #undef BPF_PROG_TYPE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4217) __ctx_convert_unused, /* to avoid empty enum in extreme .config */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4218) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4219) static u8 bpf_ctx_convert_map[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4220) #define BPF_PROG_TYPE(_id, _name, prog_ctx_type, kern_ctx_type) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4221) [_id] = __ctx_convert##_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4222) #include <linux/bpf_types.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4223) #undef BPF_PROG_TYPE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4224) 0, /* avoid empty array */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4225) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4226) #undef BPF_MAP_TYPE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4227) #undef BPF_LINK_TYPE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4229) static const struct btf_member *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4230) btf_get_prog_ctx_type(struct bpf_verifier_log *log, struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4231) const struct btf_type *t, enum bpf_prog_type prog_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4232) int arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4233) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4234) const struct btf_type *conv_struct;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4235) const struct btf_type *ctx_struct;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4236) const struct btf_member *ctx_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4237) const char *tname, *ctx_tname;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4238)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4239) conv_struct = bpf_ctx_convert.t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4240) if (!conv_struct) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4241) bpf_log(log, "btf_vmlinux is malformed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4242) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4243) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4244) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4245) while (btf_type_is_modifier(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4246) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4247) if (!btf_type_is_struct(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4248) /* Only pointer to struct is supported for now.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4249) * That means that BPF_PROG_TYPE_TRACEPOINT with BTF
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4250) * is not supported yet.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4251) * BPF_PROG_TYPE_RAW_TRACEPOINT is fine.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4252) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4253) if (log->level & BPF_LOG_LEVEL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4254) bpf_log(log, "arg#%d type is not a struct\n", arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4255) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4256) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4257) tname = btf_name_by_offset(btf, t->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4258) if (!tname) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4259) bpf_log(log, "arg#%d struct doesn't have a name\n", arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4260) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4261) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4262) /* prog_type is valid bpf program type. No need for bounds check. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4263) ctx_type = btf_type_member(conv_struct) + bpf_ctx_convert_map[prog_type] * 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4264) /* ctx_struct is a pointer to prog_ctx_type in vmlinux.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4265) * Like 'struct __sk_buff'
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4266) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4267) ctx_struct = btf_type_by_id(btf_vmlinux, ctx_type->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4268) if (!ctx_struct)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4269) /* should not happen */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4270) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4271) ctx_tname = btf_name_by_offset(btf_vmlinux, ctx_struct->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4272) if (!ctx_tname) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4273) /* should not happen */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4274) bpf_log(log, "Please fix kernel include/linux/bpf_types.h\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4275) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4276) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4277) /* only compare that prog's ctx type name is the same as
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4278) * kernel expects. No need to compare field by field.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4279) * It's ok for bpf prog to do:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4280) * struct __sk_buff {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4281) * int socket_filter_bpf_prog(struct __sk_buff *skb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4282) * { // no fields of skb are ever used }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4283) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4284) if (strcmp(ctx_tname, tname))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4285) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4286) return ctx_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4287) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4288)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4289) static const struct bpf_map_ops * const btf_vmlinux_map_ops[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4290) #define BPF_PROG_TYPE(_id, _name, prog_ctx_type, kern_ctx_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4291) #define BPF_LINK_TYPE(_id, _name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4292) #define BPF_MAP_TYPE(_id, _ops) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4293) [_id] = &_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4294) #include <linux/bpf_types.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4295) #undef BPF_PROG_TYPE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4296) #undef BPF_LINK_TYPE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4297) #undef BPF_MAP_TYPE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4298) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4299)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4300) static int btf_vmlinux_map_ids_init(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4301) struct bpf_verifier_log *log)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4302) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4303) const struct bpf_map_ops *ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4304) int i, btf_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4305)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4306) for (i = 0; i < ARRAY_SIZE(btf_vmlinux_map_ops); ++i) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4307) ops = btf_vmlinux_map_ops[i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4308) if (!ops || (!ops->map_btf_name && !ops->map_btf_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4309) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4310) if (!ops->map_btf_name || !ops->map_btf_id) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4311) bpf_log(log, "map type %d is misconfigured\n", i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4312) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4313) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4314) btf_id = btf_find_by_name_kind(btf, ops->map_btf_name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4315) BTF_KIND_STRUCT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4316) if (btf_id < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4317) return btf_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4318) *ops->map_btf_id = btf_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4319) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4320)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4321) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4322) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4323)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4324) static int btf_translate_to_vmlinux(struct bpf_verifier_log *log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4325) struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4326) const struct btf_type *t,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4327) enum bpf_prog_type prog_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4328) int arg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4329) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4330) const struct btf_member *prog_ctx_type, *kern_ctx_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4331)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4332) prog_ctx_type = btf_get_prog_ctx_type(log, btf, t, prog_type, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4333) if (!prog_ctx_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4334) return -ENOENT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4335) kern_ctx_type = prog_ctx_type + 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4336) return kern_ctx_type->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4337) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4338)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4339) BTF_ID_LIST(bpf_ctx_convert_btf_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4340) BTF_ID(struct, bpf_ctx_convert)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4341)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4342) struct btf *btf_parse_vmlinux(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4343) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4344) struct btf_verifier_env *env = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4345) struct bpf_verifier_log *log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4346) struct btf *btf = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4347) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4348)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4349) env = kzalloc(sizeof(*env), GFP_KERNEL | __GFP_NOWARN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4350) if (!env)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4351) return ERR_PTR(-ENOMEM);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4352)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4353) log = &env->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4354) log->level = BPF_LOG_KERNEL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4355)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4356) btf = kzalloc(sizeof(*btf), GFP_KERNEL | __GFP_NOWARN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4357) if (!btf) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4358) err = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4359) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4360) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4361) env->btf = btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4362)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4363) btf->data = __start_BTF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4364) btf->data_size = __stop_BTF - __start_BTF;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4365)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4366) err = btf_parse_hdr(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4367) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4368) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4369)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4370) btf->nohdr_data = btf->data + btf->hdr.hdr_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4371)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4372) err = btf_parse_str_sec(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4373) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4374) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4375)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4376) err = btf_check_all_metas(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4377) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4378) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4379)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4380) /* btf_parse_vmlinux() runs under bpf_verifier_lock */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4381) bpf_ctx_convert.t = btf_type_by_id(btf, bpf_ctx_convert_btf_id[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4382)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4383) /* find bpf map structs for map_ptr access checking */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4384) err = btf_vmlinux_map_ids_init(btf, log);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4385) if (err < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4386) goto errout;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4387)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4388) bpf_struct_ops_init(btf, log);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4389)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4390) btf_verifier_env_free(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4391) refcount_set(&btf->refcnt, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4392) return btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4393)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4394) errout:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4395) btf_verifier_env_free(env);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4396) if (btf) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4397) kvfree(btf->types);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4398) kfree(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4399) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4400) return ERR_PTR(err);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4401) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4402)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4403) struct btf *bpf_prog_get_target_btf(const struct bpf_prog *prog)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4404) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4405) struct bpf_prog *tgt_prog = prog->aux->dst_prog;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4406)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4407) if (tgt_prog) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4408) return tgt_prog->aux->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4409) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4410) return btf_vmlinux;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4411) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4412) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4413)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4414) static bool is_string_ptr(struct btf *btf, const struct btf_type *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4415) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4416) /* t comes in already as a pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4417) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4418)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4419) /* allow const */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4420) if (BTF_INFO_KIND(t->info) == BTF_KIND_CONST)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4421) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4422)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4423) /* char, signed char, unsigned char */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4424) return btf_type_is_int(t) && t->size == 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4425) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4426)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4427) bool btf_ctx_access(int off, int size, enum bpf_access_type type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4428) const struct bpf_prog *prog,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4429) struct bpf_insn_access_aux *info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4430) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4431) const struct btf_type *t = prog->aux->attach_func_proto;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4432) struct bpf_prog *tgt_prog = prog->aux->dst_prog;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4433) struct btf *btf = bpf_prog_get_target_btf(prog);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4434) const char *tname = prog->aux->attach_func_name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4435) struct bpf_verifier_log *log = info->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4436) const struct btf_param *args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4437) u32 nr_args, arg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4438) int i, ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4439)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4440) if (off % 8) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4441) bpf_log(log, "func '%s' offset %d is not multiple of 8\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4442) tname, off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4443) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4444) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4445) arg = off / 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4446) args = (const struct btf_param *)(t + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4447) /* if (t == NULL) Fall back to default BPF prog with 5 u64 arguments */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4448) nr_args = t ? btf_type_vlen(t) : 5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4449) if (prog->aux->attach_btf_trace) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4450) /* skip first 'void *__data' argument in btf_trace_##name typedef */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4451) args++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4452) nr_args--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4453) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4454)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4455) if (arg > nr_args) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4456) bpf_log(log, "func '%s' doesn't have %d-th argument\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4457) tname, arg + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4458) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4459) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4460)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4461) if (arg == nr_args) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4462) switch (prog->expected_attach_type) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4463) case BPF_LSM_MAC:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4464) case BPF_TRACE_FEXIT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4465) /* When LSM programs are attached to void LSM hooks
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4466) * they use FEXIT trampolines and when attached to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4467) * int LSM hooks, they use MODIFY_RETURN trampolines.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4468) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4469) * While the LSM programs are BPF_MODIFY_RETURN-like
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4470) * the check:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4471) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4472) * if (ret_type != 'int')
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4473) * return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4474) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4475) * is _not_ done here. This is still safe as LSM hooks
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4476) * have only void and int return types.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4477) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4478) if (!t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4479) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4480) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4481) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4482) case BPF_MODIFY_RETURN:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4483) /* For now the BPF_MODIFY_RETURN can only be attached to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4484) * functions that return an int.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4485) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4486) if (!t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4487) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4488)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4489) t = btf_type_skip_modifiers(btf, t->type, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4490) if (!btf_type_is_small_int(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4491) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4492) "ret type %s not allowed for fmod_ret\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4493) btf_kind_str[BTF_INFO_KIND(t->info)]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4494) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4495) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4496) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4497) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4498) bpf_log(log, "func '%s' doesn't have %d-th argument\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4499) tname, arg + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4500) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4501) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4502) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4503) if (!t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4504) /* Default prog with 5 args */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4505) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4506) t = btf_type_by_id(btf, args[arg].type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4507) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4508)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4509) /* skip modifiers */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4510) while (btf_type_is_modifier(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4511) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4512) if (btf_type_is_small_int(t) || btf_type_is_enum(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4513) /* accessing a scalar */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4514) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4515) if (!btf_type_is_ptr(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4516) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4517) "func '%s' arg%d '%s' has type %s. Only pointer access is allowed\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4518) tname, arg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4519) __btf_name_by_offset(btf, t->name_off),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4520) btf_kind_str[BTF_INFO_KIND(t->info)]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4521) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4522) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4523)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4524) /* check for PTR_TO_RDONLY_BUF_OR_NULL or PTR_TO_RDWR_BUF_OR_NULL */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4525) for (i = 0; i < prog->aux->ctx_arg_info_size; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4526) const struct bpf_ctx_arg_aux *ctx_arg_info = &prog->aux->ctx_arg_info[i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4527)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4528) if (ctx_arg_info->offset == off &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4529) (ctx_arg_info->reg_type == PTR_TO_RDONLY_BUF_OR_NULL ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4530) ctx_arg_info->reg_type == PTR_TO_RDWR_BUF_OR_NULL)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4531) info->reg_type = ctx_arg_info->reg_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4532) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4533) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4534) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4535)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4536) if (t->type == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4537) /* This is a pointer to void.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4538) * It is the same as scalar from the verifier safety pov.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4539) * No further pointer walking is allowed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4540) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4541) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4542)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4543) if (is_string_ptr(btf, t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4544) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4545)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4546) /* this is a pointer to another type */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4547) for (i = 0; i < prog->aux->ctx_arg_info_size; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4548) const struct bpf_ctx_arg_aux *ctx_arg_info = &prog->aux->ctx_arg_info[i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4549)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4550) if (ctx_arg_info->offset == off) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4551) info->reg_type = ctx_arg_info->reg_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4552) info->btf_id = ctx_arg_info->btf_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4553) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4554) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4555) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4556)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4557) info->reg_type = PTR_TO_BTF_ID;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4558) if (tgt_prog) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4559) enum bpf_prog_type tgt_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4560)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4561) if (tgt_prog->type == BPF_PROG_TYPE_EXT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4562) tgt_type = tgt_prog->aux->saved_dst_prog_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4563) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4564) tgt_type = tgt_prog->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4565)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4566) ret = btf_translate_to_vmlinux(log, btf, t, tgt_type, arg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4567) if (ret > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4568) info->btf_id = ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4569) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4570) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4571) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4572) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4573) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4574)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4575) info->btf_id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4576) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4577) /* skip modifiers */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4578) while (btf_type_is_modifier(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4579) info->btf_id = t->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4580) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4581) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4582) if (!btf_type_is_struct(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4583) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4584) "func '%s' arg%d type %s is not a struct\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4585) tname, arg, btf_kind_str[BTF_INFO_KIND(t->info)]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4586) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4587) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4588) bpf_log(log, "func '%s' arg%d has btf_id %d type %s '%s'\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4589) tname, arg, info->btf_id, btf_kind_str[BTF_INFO_KIND(t->info)],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4590) __btf_name_by_offset(btf, t->name_off));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4591) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4592) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4593)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4594) enum bpf_struct_walk_result {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4595) /* < 0 error */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4596) WALK_SCALAR = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4597) WALK_PTR,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4598) WALK_STRUCT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4599) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4600)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4601) static int btf_struct_walk(struct bpf_verifier_log *log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4602) const struct btf_type *t, int off, int size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4603) u32 *next_btf_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4604) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4605) u32 i, moff, mtrue_end, msize = 0, total_nelems = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4606) const struct btf_type *mtype, *elem_type = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4607) const struct btf_member *member;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4608) const char *tname, *mname;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4609) u32 vlen, elem_id, mid;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4610)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4611) again:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4612) tname = __btf_name_by_offset(btf_vmlinux, t->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4613) if (!btf_type_is_struct(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4614) bpf_log(log, "Type '%s' is not a struct\n", tname);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4615) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4616) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4617)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4618) vlen = btf_type_vlen(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4619) if (off + size > t->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4620) /* If the last element is a variable size array, we may
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4621) * need to relax the rule.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4622) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4623) struct btf_array *array_elem;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4624)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4625) if (vlen == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4626) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4627)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4628) member = btf_type_member(t) + vlen - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4629) mtype = btf_type_skip_modifiers(btf_vmlinux, member->type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4630) NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4631) if (!btf_type_is_array(mtype))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4632) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4633)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4634) array_elem = (struct btf_array *)(mtype + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4635) if (array_elem->nelems != 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4636) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4637)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4638) moff = btf_member_bit_offset(t, member) / 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4639) if (off < moff)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4640) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4641)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4642) /* Only allow structure for now, can be relaxed for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4643) * other types later.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4644) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4645) t = btf_type_skip_modifiers(btf_vmlinux, array_elem->type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4646) NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4647) if (!btf_type_is_struct(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4648) goto error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4649)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4650) off = (off - moff) % t->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4651) goto again;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4652)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4653) error:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4654) bpf_log(log, "access beyond struct %s at off %u size %u\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4655) tname, off, size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4656) return -EACCES;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4657) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4658)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4659) for_each_member(i, t, member) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4660) /* offset of the field in bytes */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4661) moff = btf_member_bit_offset(t, member) / 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4662) if (off + size <= moff)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4663) /* won't find anything, field is already too far */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4664) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4665)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4666) if (btf_member_bitfield_size(t, member)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4667) u32 end_bit = btf_member_bit_offset(t, member) +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4668) btf_member_bitfield_size(t, member);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4669)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4670) /* off <= moff instead of off == moff because clang
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4671) * does not generate a BTF member for anonymous
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4672) * bitfield like the ":16" here:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4673) * struct {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4674) * int :16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4675) * int x:8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4676) * };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4677) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4678) if (off <= moff &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4679) BITS_ROUNDUP_BYTES(end_bit) <= off + size)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4680) return WALK_SCALAR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4681)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4682) /* off may be accessing a following member
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4683) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4684) * or
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4685) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4686) * Doing partial access at either end of this
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4687) * bitfield. Continue on this case also to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4688) * treat it as not accessing this bitfield
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4689) * and eventually error out as field not
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4690) * found to keep it simple.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4691) * It could be relaxed if there was a legit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4692) * partial access case later.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4693) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4694) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4695) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4696)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4697) /* In case of "off" is pointing to holes of a struct */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4698) if (off < moff)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4699) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4700)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4701) /* type of the field */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4702) mid = member->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4703) mtype = btf_type_by_id(btf_vmlinux, member->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4704) mname = __btf_name_by_offset(btf_vmlinux, member->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4705)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4706) mtype = __btf_resolve_size(btf_vmlinux, mtype, &msize,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4707) &elem_type, &elem_id, &total_nelems,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4708) &mid);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4709) if (IS_ERR(mtype)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4710) bpf_log(log, "field %s doesn't have size\n", mname);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4711) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4712) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4713)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4714) mtrue_end = moff + msize;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4715) if (off >= mtrue_end)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4716) /* no overlap with member, keep iterating */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4717) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4718)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4719) if (btf_type_is_array(mtype)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4720) u32 elem_idx;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4721)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4722) /* __btf_resolve_size() above helps to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4723) * linearize a multi-dimensional array.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4724) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4725) * The logic here is treating an array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4726) * in a struct as the following way:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4727) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4728) * struct outer {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4729) * struct inner array[2][2];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4730) * };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4731) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4732) * looks like:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4733) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4734) * struct outer {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4735) * struct inner array_elem0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4736) * struct inner array_elem1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4737) * struct inner array_elem2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4738) * struct inner array_elem3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4739) * };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4740) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4741) * When accessing outer->array[1][0], it moves
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4742) * moff to "array_elem2", set mtype to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4743) * "struct inner", and msize also becomes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4744) * sizeof(struct inner). Then most of the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4745) * remaining logic will fall through without
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4746) * caring the current member is an array or
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4747) * not.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4748) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4749) * Unlike mtype/msize/moff, mtrue_end does not
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4750) * change. The naming difference ("_true") tells
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4751) * that it is not always corresponding to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4752) * the current mtype/msize/moff.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4753) * It is the true end of the current
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4754) * member (i.e. array in this case). That
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4755) * will allow an int array to be accessed like
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4756) * a scratch space,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4757) * i.e. allow access beyond the size of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4758) * the array's element as long as it is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4759) * within the mtrue_end boundary.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4760) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4761)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4762) /* skip empty array */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4763) if (moff == mtrue_end)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4764) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4765)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4766) msize /= total_nelems;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4767) elem_idx = (off - moff) / msize;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4768) moff += elem_idx * msize;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4769) mtype = elem_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4770) mid = elem_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4771) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4772)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4773) /* the 'off' we're looking for is either equal to start
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4774) * of this field or inside of this struct
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4775) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4776) if (btf_type_is_struct(mtype)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4777) /* our field must be inside that union or struct */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4778) t = mtype;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4779)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4780) /* return if the offset matches the member offset */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4781) if (off == moff) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4782) *next_btf_id = mid;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4783) return WALK_STRUCT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4784) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4785)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4786) /* adjust offset we're looking for */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4787) off -= moff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4788) goto again;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4789) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4790)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4791) if (btf_type_is_ptr(mtype)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4792) const struct btf_type *stype;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4793) u32 id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4794)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4795) if (msize != size || off != moff) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4796) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4797) "cannot access ptr member %s with moff %u in struct %s with off %u size %u\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4798) mname, moff, tname, off, size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4799) return -EACCES;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4800) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4801) stype = btf_type_skip_modifiers(btf_vmlinux, mtype->type, &id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4802) if (btf_type_is_struct(stype)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4803) *next_btf_id = id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4804) return WALK_PTR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4805) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4806) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4807)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4808) /* Allow more flexible access within an int as long as
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4809) * it is within mtrue_end.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4810) * Since mtrue_end could be the end of an array,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4811) * that also allows using an array of int as a scratch
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4812) * space. e.g. skb->cb[].
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4813) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4814) if (off + size > mtrue_end) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4815) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4816) "access beyond the end of member %s (mend:%u) in struct %s with off %u size %u\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4817) mname, mtrue_end, tname, off, size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4818) return -EACCES;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4819) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4820)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4821) return WALK_SCALAR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4822) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4823) bpf_log(log, "struct %s doesn't have field at offset %d\n", tname, off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4824) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4825) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4826)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4827) int btf_struct_access(struct bpf_verifier_log *log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4828) const struct btf_type *t, int off, int size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4829) enum bpf_access_type atype __maybe_unused,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4830) u32 *next_btf_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4831) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4832) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4833) u32 id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4834)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4835) do {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4836) err = btf_struct_walk(log, t, off, size, &id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4837)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4838) switch (err) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4839) case WALK_PTR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4840) /* If we found the pointer or scalar on t+off,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4841) * we're done.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4842) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4843) *next_btf_id = id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4844) return PTR_TO_BTF_ID;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4845) case WALK_SCALAR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4846) return SCALAR_VALUE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4847) case WALK_STRUCT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4848) /* We found nested struct, so continue the search
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4849) * by diving in it. At this point the offset is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4850) * aligned with the new type, so set it to 0.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4851) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4852) t = btf_type_by_id(btf_vmlinux, id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4853) off = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4854) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4855) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4856) /* It's either error or unknown return value..
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4857) * scream and leave.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4858) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4859) if (WARN_ONCE(err > 0, "unknown btf_struct_walk return value"))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4860) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4861) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4862) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4863) } while (t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4864)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4865) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4866) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4867)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4868) bool btf_struct_ids_match(struct bpf_verifier_log *log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4869) int off, u32 id, u32 need_type_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4870) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4871) const struct btf_type *type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4872) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4873)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4874) /* Are we already done? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4875) if (need_type_id == id && off == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4876) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4877)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4878) again:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4879) type = btf_type_by_id(btf_vmlinux, id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4880) if (!type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4881) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4882) err = btf_struct_walk(log, type, off, 1, &id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4883) if (err != WALK_STRUCT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4884) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4885)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4886) /* We found nested struct object. If it matches
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4887) * the requested ID, we're done. Otherwise let's
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4888) * continue the search with offset 0 in the new
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4889) * type.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4890) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4891) if (need_type_id != id) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4892) off = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4893) goto again;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4894) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4895)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4896) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4897) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4898)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4899) static int __get_type_size(struct btf *btf, u32 btf_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4900) const struct btf_type **bad_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4901) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4902) const struct btf_type *t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4903)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4904) if (!btf_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4905) /* void */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4906) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4907) t = btf_type_by_id(btf, btf_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4908) while (t && btf_type_is_modifier(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4909) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4910) if (!t) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4911) *bad_type = btf->types[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4912) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4913) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4914) if (btf_type_is_ptr(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4915) /* kernel size of pointer. Not BPF's size of pointer*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4916) return sizeof(void *);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4917) if (btf_type_is_int(t) || btf_type_is_enum(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4918) return t->size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4919) *bad_type = t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4920) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4921) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4922)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4923) int btf_distill_func_proto(struct bpf_verifier_log *log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4924) struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4925) const struct btf_type *func,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4926) const char *tname,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4927) struct btf_func_model *m)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4928) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4929) const struct btf_param *args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4930) const struct btf_type *t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4931) u32 i, nargs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4932) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4933)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4934) if (!func) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4935) /* BTF function prototype doesn't match the verifier types.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4936) * Fall back to 5 u64 args.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4937) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4938) for (i = 0; i < 5; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4939) m->arg_size[i] = 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4940) m->ret_size = 8;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4941) m->nr_args = 5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4942) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4943) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4944) args = (const struct btf_param *)(func + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4945) nargs = btf_type_vlen(func);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4946) if (nargs >= MAX_BPF_FUNC_ARGS) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4947) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4948) "The function %s has %d arguments. Too many.\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4949) tname, nargs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4950) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4951) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4952) ret = __get_type_size(btf, func->type, &t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4953) if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4954) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4955) "The function %s return type %s is unsupported.\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4956) tname, btf_kind_str[BTF_INFO_KIND(t->info)]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4957) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4958) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4959) m->ret_size = ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4960)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4961) for (i = 0; i < nargs; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4962) if (i == nargs - 1 && args[i].type == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4963) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4964) "The function %s with variable args is unsupported.\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4965) tname);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4966) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4967) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4968) ret = __get_type_size(btf, args[i].type, &t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4969) if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4970) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4971) "The function %s arg%d type %s is unsupported.\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4972) tname, i, btf_kind_str[BTF_INFO_KIND(t->info)]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4973) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4974) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4975) if (ret == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4976) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4977) "The function %s has malformed void argument.\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4978) tname);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4979) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4980) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4981) m->arg_size[i] = ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4982) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4983) m->nr_args = nargs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4984) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4985) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4986)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4987) /* Compare BTFs of two functions assuming only scalars and pointers to context.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4988) * t1 points to BTF_KIND_FUNC in btf1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4989) * t2 points to BTF_KIND_FUNC in btf2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4990) * Returns:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4991) * EINVAL - function prototype mismatch
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4992) * EFAULT - verifier bug
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4993) * 0 - 99% match. The last 1% is validated by the verifier.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4994) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4995) static int btf_check_func_type_match(struct bpf_verifier_log *log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4996) struct btf *btf1, const struct btf_type *t1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4997) struct btf *btf2, const struct btf_type *t2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4998) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4999) const struct btf_param *args1, *args2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5000) const char *fn1, *fn2, *s1, *s2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5001) u32 nargs1, nargs2, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5002)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5003) fn1 = btf_name_by_offset(btf1, t1->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5004) fn2 = btf_name_by_offset(btf2, t2->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5005)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5006) if (btf_func_linkage(t1) != BTF_FUNC_GLOBAL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5007) bpf_log(log, "%s() is not a global function\n", fn1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5008) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5009) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5010) if (btf_func_linkage(t2) != BTF_FUNC_GLOBAL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5011) bpf_log(log, "%s() is not a global function\n", fn2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5012) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5013) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5014)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5015) t1 = btf_type_by_id(btf1, t1->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5016) if (!t1 || !btf_type_is_func_proto(t1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5017) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5018) t2 = btf_type_by_id(btf2, t2->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5019) if (!t2 || !btf_type_is_func_proto(t2))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5020) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5021)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5022) args1 = (const struct btf_param *)(t1 + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5023) nargs1 = btf_type_vlen(t1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5024) args2 = (const struct btf_param *)(t2 + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5025) nargs2 = btf_type_vlen(t2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5026)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5027) if (nargs1 != nargs2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5028) bpf_log(log, "%s() has %d args while %s() has %d args\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5029) fn1, nargs1, fn2, nargs2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5030) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5031) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5032)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5033) t1 = btf_type_skip_modifiers(btf1, t1->type, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5034) t2 = btf_type_skip_modifiers(btf2, t2->type, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5035) if (t1->info != t2->info) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5036) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5037) "Return type %s of %s() doesn't match type %s of %s()\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5038) btf_type_str(t1), fn1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5039) btf_type_str(t2), fn2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5040) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5041) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5042)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5043) for (i = 0; i < nargs1; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5044) t1 = btf_type_skip_modifiers(btf1, args1[i].type, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5045) t2 = btf_type_skip_modifiers(btf2, args2[i].type, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5046)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5047) if (t1->info != t2->info) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5048) bpf_log(log, "arg%d in %s() is %s while %s() has %s\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5049) i, fn1, btf_type_str(t1),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5050) fn2, btf_type_str(t2));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5051) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5052) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5053) if (btf_type_has_size(t1) && t1->size != t2->size) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5054) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5055) "arg%d in %s() has size %d while %s() has %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5056) i, fn1, t1->size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5057) fn2, t2->size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5058) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5059) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5060)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5061) /* global functions are validated with scalars and pointers
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5062) * to context only. And only global functions can be replaced.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5063) * Hence type check only those types.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5064) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5065) if (btf_type_is_int(t1) || btf_type_is_enum(t1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5066) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5067) if (!btf_type_is_ptr(t1)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5068) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5069) "arg%d in %s() has unrecognized type\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5070) i, fn1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5071) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5072) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5073) t1 = btf_type_skip_modifiers(btf1, t1->type, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5074) t2 = btf_type_skip_modifiers(btf2, t2->type, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5075) if (!btf_type_is_struct(t1)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5076) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5077) "arg%d in %s() is not a pointer to context\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5078) i, fn1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5079) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5080) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5081) if (!btf_type_is_struct(t2)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5082) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5083) "arg%d in %s() is not a pointer to context\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5084) i, fn2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5085) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5086) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5087) /* This is an optional check to make program writing easier.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5088) * Compare names of structs and report an error to the user.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5089) * btf_prepare_func_args() already checked that t2 struct
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5090) * is a context type. btf_prepare_func_args() will check
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5091) * later that t1 struct is a context type as well.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5092) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5093) s1 = btf_name_by_offset(btf1, t1->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5094) s2 = btf_name_by_offset(btf2, t2->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5095) if (strcmp(s1, s2)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5096) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5097) "arg%d %s(struct %s *) doesn't match %s(struct %s *)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5098) i, fn1, s1, fn2, s2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5099) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5100) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5101) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5102) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5103) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5104)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5105) /* Compare BTFs of given program with BTF of target program */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5106) int btf_check_type_match(struct bpf_verifier_log *log, const struct bpf_prog *prog,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5107) struct btf *btf2, const struct btf_type *t2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5108) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5109) struct btf *btf1 = prog->aux->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5110) const struct btf_type *t1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5111) u32 btf_id = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5112)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5113) if (!prog->aux->func_info) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5114) bpf_log(log, "Program extension requires BTF\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5115) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5116) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5117)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5118) btf_id = prog->aux->func_info[0].type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5119) if (!btf_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5120) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5121)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5122) t1 = btf_type_by_id(btf1, btf_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5123) if (!t1 || !btf_type_is_func(t1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5124) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5125)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5126) return btf_check_func_type_match(log, btf1, t1, btf2, t2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5127) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5128)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5129) /* Compare BTF of a function with given bpf_reg_state.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5130) * Returns:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5131) * EFAULT - there is a verifier bug. Abort verification.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5132) * EINVAL - there is a type mismatch or BTF is not available.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5133) * 0 - BTF matches with what bpf_reg_state expects.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5134) * Only PTR_TO_CTX and SCALAR_VALUE states are recognized.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5135) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5136) int btf_check_func_arg_match(struct bpf_verifier_env *env, int subprog,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5137) struct bpf_reg_state *reg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5138) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5139) struct bpf_verifier_log *log = &env->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5140) struct bpf_prog *prog = env->prog;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5141) struct btf *btf = prog->aux->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5142) const struct btf_param *args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5143) const struct btf_type *t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5144) u32 i, nargs, btf_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5145) const char *tname;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5146)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5147) if (!prog->aux->func_info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5148) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5149)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5150) btf_id = prog->aux->func_info[subprog].type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5151) if (!btf_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5152) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5153)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5154) if (prog->aux->func_info_aux[subprog].unreliable)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5155) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5156)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5157) t = btf_type_by_id(btf, btf_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5158) if (!t || !btf_type_is_func(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5159) /* These checks were already done by the verifier while loading
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5160) * struct bpf_func_info
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5161) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5162) bpf_log(log, "BTF of func#%d doesn't point to KIND_FUNC\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5163) subprog);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5164) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5165) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5166) tname = btf_name_by_offset(btf, t->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5167)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5168) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5169) if (!t || !btf_type_is_func_proto(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5170) bpf_log(log, "Invalid BTF of func %s\n", tname);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5171) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5172) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5173) args = (const struct btf_param *)(t + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5174) nargs = btf_type_vlen(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5175) if (nargs > 5) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5176) bpf_log(log, "Function %s has %d > 5 args\n", tname, nargs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5177) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5178) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5179) /* check that BTF function arguments match actual types that the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5180) * verifier sees.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5181) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5182) for (i = 0; i < nargs; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5183) t = btf_type_by_id(btf, args[i].type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5184) while (btf_type_is_modifier(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5185) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5186) if (btf_type_is_int(t) || btf_type_is_enum(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5187) if (reg[i + 1].type == SCALAR_VALUE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5188) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5189) bpf_log(log, "R%d is not a scalar\n", i + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5190) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5191) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5192) if (btf_type_is_ptr(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5193) if (reg[i + 1].type == SCALAR_VALUE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5194) bpf_log(log, "R%d is not a pointer\n", i + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5195) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5196) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5197) /* If function expects ctx type in BTF check that caller
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5198) * is passing PTR_TO_CTX.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5199) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5200) if (btf_get_prog_ctx_type(log, btf, t, prog->type, i)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5201) if (reg[i + 1].type != PTR_TO_CTX) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5202) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5203) "arg#%d expected pointer to ctx, but got %s\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5204) i, btf_kind_str[BTF_INFO_KIND(t->info)]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5205) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5206) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5207) if (check_ctx_reg(env, ®[i + 1], i + 1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5208) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5209) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5210) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5211) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5212) bpf_log(log, "Unrecognized arg#%d type %s\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5213) i, btf_kind_str[BTF_INFO_KIND(t->info)]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5214) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5215) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5216) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5217) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5218) /* Compiler optimizations can remove arguments from static functions
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5219) * or mismatched type can be passed into a global function.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5220) * In such cases mark the function as unreliable from BTF point of view.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5221) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5222) prog->aux->func_info_aux[subprog].unreliable = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5223) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5224) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5225)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5226) /* Convert BTF of a function into bpf_reg_state if possible
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5227) * Returns:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5228) * EFAULT - there is a verifier bug. Abort verification.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5229) * EINVAL - cannot convert BTF.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5230) * 0 - Successfully converted BTF into bpf_reg_state
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5231) * (either PTR_TO_CTX or SCALAR_VALUE).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5232) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5233) int btf_prepare_func_args(struct bpf_verifier_env *env, int subprog,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5234) struct bpf_reg_state *reg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5235) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5236) struct bpf_verifier_log *log = &env->log;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5237) struct bpf_prog *prog = env->prog;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5238) enum bpf_prog_type prog_type = prog->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5239) struct btf *btf = prog->aux->btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5240) const struct btf_param *args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5241) const struct btf_type *t;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5242) u32 i, nargs, btf_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5243) const char *tname;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5244)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5245) if (!prog->aux->func_info ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5246) prog->aux->func_info_aux[subprog].linkage != BTF_FUNC_GLOBAL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5247) bpf_log(log, "Verifier bug\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5248) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5249) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5250)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5251) btf_id = prog->aux->func_info[subprog].type_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5252) if (!btf_id) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5253) bpf_log(log, "Global functions need valid BTF\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5254) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5255) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5256)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5257) t = btf_type_by_id(btf, btf_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5258) if (!t || !btf_type_is_func(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5259) /* These checks were already done by the verifier while loading
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5260) * struct bpf_func_info
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5261) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5262) bpf_log(log, "BTF of func#%d doesn't point to KIND_FUNC\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5263) subprog);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5264) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5265) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5266) tname = btf_name_by_offset(btf, t->name_off);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5267)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5268) if (log->level & BPF_LOG_LEVEL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5269) bpf_log(log, "Validating %s() func#%d...\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5270) tname, subprog);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5271)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5272) if (prog->aux->func_info_aux[subprog].unreliable) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5273) bpf_log(log, "Verifier bug in function %s()\n", tname);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5274) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5275) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5276) if (prog_type == BPF_PROG_TYPE_EXT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5277) prog_type = prog->aux->dst_prog->type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5278)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5279) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5280) if (!t || !btf_type_is_func_proto(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5281) bpf_log(log, "Invalid type of function %s()\n", tname);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5282) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5283) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5284) args = (const struct btf_param *)(t + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5285) nargs = btf_type_vlen(t);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5286) if (nargs > 5) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5287) bpf_log(log, "Global function %s() with %d > 5 args. Buggy compiler.\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5288) tname, nargs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5289) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5290) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5291) /* check that function returns int */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5292) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5293) while (btf_type_is_modifier(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5294) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5295) if (!btf_type_is_int(t) && !btf_type_is_enum(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5296) bpf_log(log,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5297) "Global function %s() doesn't return scalar. Only those are supported.\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5298) tname);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5299) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5300) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5301) /* Convert BTF function arguments into verifier types.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5302) * Only PTR_TO_CTX and SCALAR are supported atm.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5303) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5304) for (i = 0; i < nargs; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5305) t = btf_type_by_id(btf, args[i].type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5306) while (btf_type_is_modifier(t))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5307) t = btf_type_by_id(btf, t->type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5308) if (btf_type_is_int(t) || btf_type_is_enum(t)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5309) reg[i + 1].type = SCALAR_VALUE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5310) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5311) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5312) if (btf_type_is_ptr(t) &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5313) btf_get_prog_ctx_type(log, btf, t, prog_type, i)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5314) reg[i + 1].type = PTR_TO_CTX;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5315) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5316) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5317) bpf_log(log, "Arg#%d type %s in %s() is not supported yet.\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5318) i, btf_kind_str[BTF_INFO_KIND(t->info)], tname);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5319) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5320) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5321) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5322) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5323)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5324) static void btf_type_show(const struct btf *btf, u32 type_id, void *obj,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5325) struct btf_show *show)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5326) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5327) const struct btf_type *t = btf_type_by_id(btf, type_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5328)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5329) show->btf = btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5330) memset(&show->state, 0, sizeof(show->state));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5331) memset(&show->obj, 0, sizeof(show->obj));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5332)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5333) btf_type_ops(t)->show(btf, t, type_id, obj, 0, show);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5334) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5335)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5336) static void btf_seq_show(struct btf_show *show, const char *fmt,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5337) va_list args)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5338) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5339) seq_vprintf((struct seq_file *)show->target, fmt, args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5340) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5341)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5342) int btf_type_seq_show_flags(const struct btf *btf, u32 type_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5343) void *obj, struct seq_file *m, u64 flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5344) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5345) struct btf_show sseq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5346)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5347) sseq.target = m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5348) sseq.showfn = btf_seq_show;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5349) sseq.flags = flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5350)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5351) btf_type_show(btf, type_id, obj, &sseq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5352)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5353) return sseq.state.status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5354) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5355)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5356) void btf_type_seq_show(const struct btf *btf, u32 type_id, void *obj,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5357) struct seq_file *m)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5358) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5359) (void) btf_type_seq_show_flags(btf, type_id, obj, m,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5360) BTF_SHOW_NONAME | BTF_SHOW_COMPACT |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5361) BTF_SHOW_ZERO | BTF_SHOW_UNSAFE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5362) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5363)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5364) struct btf_show_snprintf {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5365) struct btf_show show;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5366) int len_left; /* space left in string */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5367) int len; /* length we would have written */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5368) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5369)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5370) static void btf_snprintf_show(struct btf_show *show, const char *fmt,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5371) va_list args)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5372) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5373) struct btf_show_snprintf *ssnprintf = (struct btf_show_snprintf *)show;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5374) int len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5375)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5376) len = vsnprintf(show->target, ssnprintf->len_left, fmt, args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5377)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5378) if (len < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5379) ssnprintf->len_left = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5380) ssnprintf->len = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5381) } else if (len > ssnprintf->len_left) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5382) /* no space, drive on to get length we would have written */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5383) ssnprintf->len_left = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5384) ssnprintf->len += len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5385) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5386) ssnprintf->len_left -= len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5387) ssnprintf->len += len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5388) show->target += len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5389) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5390) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5391)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5392) int btf_type_snprintf_show(const struct btf *btf, u32 type_id, void *obj,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5393) char *buf, int len, u64 flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5394) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5395) struct btf_show_snprintf ssnprintf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5396)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5397) ssnprintf.show.target = buf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5398) ssnprintf.show.flags = flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5399) ssnprintf.show.showfn = btf_snprintf_show;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5400) ssnprintf.len_left = len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5401) ssnprintf.len = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5402)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5403) btf_type_show(btf, type_id, obj, (struct btf_show *)&ssnprintf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5404)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5405) /* If we encontered an error, return it. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5406) if (ssnprintf.show.state.status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5407) return ssnprintf.show.state.status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5408)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5409) /* Otherwise return length we would have written */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5410) return ssnprintf.len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5411) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5412)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5413) #ifdef CONFIG_PROC_FS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5414) static void bpf_btf_show_fdinfo(struct seq_file *m, struct file *filp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5415) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5416) const struct btf *btf = filp->private_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5417)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5418) seq_printf(m, "btf_id:\t%u\n", btf->id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5419) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5420) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5421)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5422) static int btf_release(struct inode *inode, struct file *filp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5423) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5424) btf_put(filp->private_data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5425) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5426) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5427)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5428) const struct file_operations btf_fops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5429) #ifdef CONFIG_PROC_FS
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5430) .show_fdinfo = bpf_btf_show_fdinfo,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5431) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5432) .release = btf_release,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5433) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5434)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5435) static int __btf_new_fd(struct btf *btf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5436) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5437) return anon_inode_getfd("btf", &btf_fops, btf, O_RDONLY | O_CLOEXEC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5438) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5439)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5440) int btf_new_fd(const union bpf_attr *attr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5441) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5442) struct btf *btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5443) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5444)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5445) btf = btf_parse(u64_to_user_ptr(attr->btf),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5446) attr->btf_size, attr->btf_log_level,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5447) u64_to_user_ptr(attr->btf_log_buf),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5448) attr->btf_log_size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5449) if (IS_ERR(btf))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5450) return PTR_ERR(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5451)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5452) ret = btf_alloc_id(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5453) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5454) btf_free(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5455) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5456) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5457)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5458) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5459) * The BTF ID is published to the userspace.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5460) * All BTF free must go through call_rcu() from
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5461) * now on (i.e. free by calling btf_put()).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5462) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5463)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5464) ret = __btf_new_fd(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5465) if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5466) btf_put(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5467)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5468) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5469) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5470)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5471) struct btf *btf_get_by_fd(int fd)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5472) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5473) struct btf *btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5474) struct fd f;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5475)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5476) f = fdget(fd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5477)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5478) if (!f.file)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5479) return ERR_PTR(-EBADF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5480)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5481) if (f.file->f_op != &btf_fops) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5482) fdput(f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5483) return ERR_PTR(-EINVAL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5484) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5485)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5486) btf = f.file->private_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5487) refcount_inc(&btf->refcnt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5488) fdput(f);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5489)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5490) return btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5491) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5492)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5493) int btf_get_info_by_fd(const struct btf *btf,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5494) const union bpf_attr *attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5495) union bpf_attr __user *uattr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5496) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5497) struct bpf_btf_info __user *uinfo;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5498) struct bpf_btf_info info;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5499) u32 info_copy, btf_copy;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5500) void __user *ubtf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5501) u32 uinfo_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5502)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5503) uinfo = u64_to_user_ptr(attr->info.info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5504) uinfo_len = attr->info.info_len;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5505)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5506) info_copy = min_t(u32, uinfo_len, sizeof(info));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5507) memset(&info, 0, sizeof(info));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5508) if (copy_from_user(&info, uinfo, info_copy))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5509) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5510)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5511) info.id = btf->id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5512) ubtf = u64_to_user_ptr(info.btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5513) btf_copy = min_t(u32, btf->data_size, info.btf_size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5514) if (copy_to_user(ubtf, btf->data, btf_copy))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5515) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5516) info.btf_size = btf->data_size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5517)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5518) if (copy_to_user(uinfo, &info, info_copy) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5519) put_user(info_copy, &uattr->info.info_len))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5520) return -EFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5521)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5522) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5523) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5524)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5525) int btf_get_fd_by_id(u32 id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5526) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5527) struct btf *btf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5528) int fd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5529)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5530) rcu_read_lock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5531) btf = idr_find(&btf_idr, id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5532) if (!btf || !refcount_inc_not_zero(&btf->refcnt))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5533) btf = ERR_PTR(-ENOENT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5534) rcu_read_unlock();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5535)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5536) if (IS_ERR(btf))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5537) return PTR_ERR(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5538)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5539) fd = __btf_new_fd(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5540) if (fd < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5541) btf_put(btf);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5542)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5543) return fd;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5544) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5545)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5546) u32 btf_id(const struct btf *btf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5547) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5548) return btf->id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5549) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5550)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5551) static int btf_id_cmp_func(const void *a, const void *b)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5552) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5553) const int *pa = a, *pb = b;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5554)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5555) return *pa - *pb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5556) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5557)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5558) bool btf_id_set_contains(const struct btf_id_set *set, u32 id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5559) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5560) return bsearch(&id, set->ids, set->cnt, sizeof(u32), btf_id_cmp_func) != NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5561) }