]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
bpf/verifier: Do not limit maximum direct offset into arena map
authorEmil Tsalapatis <emil@etsalapatis.com>
Tue, 16 Dec 2025 17:33:22 +0000 (12:33 -0500)
committerAndrii Nakryiko <andrii@kernel.org>
Tue, 16 Dec 2025 18:42:55 +0000 (10:42 -0800)
The verifier currently limits direct offsets into a map to 512MiB
to avoid overflow during pointer arithmetic. However, this prevents
arena maps from using direct addressing instructions to access data
at the end of > 512MiB arena maps. This is necessary when moving
arena globals to the end of the arena instead of the front.

Refactor the verifier code to remove the offset calculation during
direct value access calculations. This is possible because the only
two map types that implement .map_direct_value_addr() are arrays and
arenas, and they both do their own internal checks to ensure the
offset is within bounds.

Adjust selftests that expect the old error. These tests still fail
because the verifier identifies the access as out of bounds for the
map, so change them to expect an "invalid access to map value pointer"
error instead.

Signed-off-by: Emil Tsalapatis <emil@etsalapatis.com>
Signed-off-by: Andrii Nakryiko <andrii@kernel.org>
Link: https://lore.kernel.org/bpf/20251216173325.98465-3-emil@etsalapatis.com
kernel/bpf/verifier.c
tools/testing/selftests/bpf/verifier/direct_value_access.c

index a31c032b2dd6343ecd36313af32a667b80617604..d6b8a77fbe3bfce586d6b8a759a47426082ca507 100644 (file)
@@ -21132,11 +21132,6 @@ static int resolve_pseudo_ldimm64(struct bpf_verifier_env *env)
                        } else {
                                u32 off = insn[1].imm;
 
-                               if (off >= BPF_MAX_VAR_OFF) {
-                                       verbose(env, "direct value offset of %u is not allowed\n", off);
-                                       return -EINVAL;
-                               }
-
                                if (!map->ops->map_direct_value_addr) {
                                        verbose(env, "no direct value access support for this map type\n");
                                        return -EINVAL;
index c0648dc009b5274170bd5f7305441c6b45a62e8e..e569d119fb602f12d1ef4f564e2f12a8bf6d7084 100644 (file)
@@ -81,7 +81,7 @@
        },
        .fixup_map_array_48b = { 1 },
        .result = REJECT,
-       .errstr = "direct value offset of 4294967295 is not allowed",
+       .errstr = "invalid access to map value pointer, value_size=48 off=4294967295",
 },
 {
        "direct map access, write test 8",
        },
        .fixup_map_array_48b = { 1 },
        .result = REJECT,
-       .errstr = "direct value offset of 536870912 is not allowed",
+       .errstr = "invalid access to map value pointer, value_size=48 off=536870912",
 },
 {
        "direct map access, write test 13",