Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

selftests/bpf: Add few tests for alu32 shift value tracking and zext

Add few more alu32 shift tests using div-by-zero on provably dead paths
to check both verifier and JIT xlation resp. runtime correctness.

If the verifier mistracks the result, it rejects due to the div by 0;
if the JIT computes a wrong value, then runtime hits the dead path and
retval changes.

# LDLIBS=-static PKG_CONFIG='pkg-config --static' ./vmtest.sh -- ./test_progs -t verifier_subreg
[...]
#644/76 verifier_subreg/arsh32_imm1_value:OK
#644/77 verifier_subreg/lsh32_reg0_zero_extend_check:OK
#644/78 verifier_subreg/rsh32_reg0_zero_extend_check:OK
#644/79 verifier_subreg/arsh32_reg0_zero_extend_check:OK
#644/80 verifier_subreg/lsh32_imm31_value:OK
#644/81 verifier_subreg/rsh32_imm31_value:OK
#644/82 verifier_subreg/arsh32_imm31_value:OK
#644/83 verifier_subreg/lsh32_unknown_precise_bounds:OK
#644/84 verifier_subreg/rsh32_unknown_bounds:OK
#644 verifier_subreg:OK
Summary: 1/84 PASSED, 0 SKIPPED, 0 FAILED

Signed-off-by: Daniel Borkmann <daniel@iogearbox.net>
Link: https://lore.kernel.org/r/20260327220629.343327-1-daniel@iogearbox.net
Signed-off-by: Alexei Starovoitov <ast@kernel.org>

authored by

Daniel Borkmann and committed by
Alexei Starovoitov
398ad123 101a9d9d

+165
+165
tools/testing/selftests/bpf/progs/verifier_subreg.c
··· 823 823 : __clobber_all); 824 824 } 825 825 826 + SEC("socket") 827 + __success __retval(42) 828 + __naked void arsh32_imm1_value(void) 829 + { 830 + asm volatile (" \ 831 + r0 = 42; \ 832 + r1 = -2147483648; \ 833 + w1 s>>= 1; /* r1 = 0xC0000000 */ \ 834 + r2 = 0xC0000000 ll; \ 835 + if r1 == r2 goto l0_%=; \ 836 + r0 /= 0; /* unreachable */ \ 837 + l0_%=: exit; \ 838 + " : 839 + : 840 + : __clobber_all); 841 + } 842 + 843 + SEC("socket") 844 + __success __retval(1) 845 + __naked void lsh32_reg0_zero_extend_check(void) 846 + { 847 + asm volatile (" \ 848 + r6 = 1; \ 849 + call %[bpf_get_prandom_u32]; \ 850 + r1 = 0x1000000000 ll; \ 851 + r0 |= r1; \ 852 + w1 = 0; \ 853 + w0 <<= w1; /* reg shift by 0 */ \ 854 + r0 >>= 32; /* must be 0 */ \ 855 + if r0 == 0 goto l0_%=; \ 856 + r6 /= 0; /* unreachable */ \ 857 + l0_%=: r0 = r6; \ 858 + exit; \ 859 + " : 860 + : __imm(bpf_get_prandom_u32) 861 + : __clobber_all); 862 + } 863 + 864 + SEC("socket") 865 + __success __retval(1) 866 + __naked void rsh32_reg0_zero_extend_check(void) 867 + { 868 + asm volatile (" \ 869 + r6 = 1; \ 870 + call %[bpf_get_prandom_u32]; \ 871 + r1 = 0x1000000000 ll; \ 872 + r0 |= r1; \ 873 + w1 = 0; \ 874 + w0 >>= w1; /* reg rsh by 0 */ \ 875 + r0 >>= 32; /* must be 0 */ \ 876 + if r0 == 0 goto l0_%=; \ 877 + r6 /= 0; /* unreachable */ \ 878 + l0_%=: r0 = r6; \ 879 + exit; \ 880 + " : 881 + : __imm(bpf_get_prandom_u32) 882 + : __clobber_all); 883 + } 884 + 885 + SEC("socket") 886 + __success __retval(1) 887 + __naked void arsh32_reg0_zero_extend_check(void) 888 + { 889 + asm volatile (" \ 890 + r6 = 1; \ 891 + call %[bpf_get_prandom_u32]; \ 892 + r1 = 0x1000000000 ll; \ 893 + r0 |= r1; \ 894 + w1 = 0; \ 895 + w0 s>>= w1; /* reg arsh by 0 */ \ 896 + r0 >>= 32; /* must be 0 */ \ 897 + if r0 == 0 goto l0_%=; \ 898 + r6 /= 0; /* unreachable */ \ 899 + l0_%=: r0 = r6; \ 900 + exit; \ 901 + " : 902 + : __imm(bpf_get_prandom_u32) 903 + : __clobber_all); 904 + } 905 + 906 + SEC("socket") 907 + __success __retval(42) 908 + __naked void lsh32_imm31_value(void) 909 + { 910 + asm volatile (" \ 911 + r0 = 42; \ 912 + r1 = 1; \ 913 + w1 <<= 31; /* r1 = 0x80000000 */ \ 914 + r2 = 0x80000000 ll; \ 915 + if r1 == r2 goto l0_%=; \ 916 + r0 /= 0; /* unreachable */ \ 917 + l0_%=: exit; \ 918 + " : 919 + : 920 + : __clobber_all); 921 + } 922 + 923 + SEC("socket") 924 + __success __retval(42) 925 + __naked void rsh32_imm31_value(void) 926 + { 927 + asm volatile (" \ 928 + r0 = 42; \ 929 + r1 = -2147483648; /* 0x80000000 */ \ 930 + w1 >>= 31; /* r1 = 1 */ \ 931 + if r1 == 1 goto l0_%=; \ 932 + r0 /= 0; /* unreachable */ \ 933 + l0_%=: exit; \ 934 + " : 935 + : 936 + : __clobber_all); 937 + } 938 + 939 + SEC("socket") 940 + __success __retval(42) 941 + __naked void arsh32_imm31_value(void) 942 + { 943 + asm volatile (" \ 944 + r0 = 42; \ 945 + r1 = -2147483648; /* 0x80000000 */ \ 946 + w1 s>>= 31; /* r1 = 0xFFFFFFFF */ \ 947 + r2 = 0xFFFFFFFF ll; \ 948 + if r1 == r2 goto l0_%=; \ 949 + r0 /= 0; /* unreachable */ \ 950 + l0_%=: exit; \ 951 + " : 952 + : 953 + : __clobber_all); 954 + } 955 + 956 + SEC("socket") 957 + __success __retval(1) 958 + __naked void lsh32_unknown_precise_bounds(void) 959 + { 960 + asm volatile (" \ 961 + r6 = 1; \ 962 + call %[bpf_get_prandom_u32]; \ 963 + w0 &= 3; /* u32: [0, 3] */ \ 964 + w0 <<= 1; /* u32: [0, 6] */ \ 965 + if w0 < 7 goto l0_%=; \ 966 + r6 /= 0; /* unreachable */ \ 967 + l0_%=: r0 = r6; \ 968 + exit; \ 969 + " : 970 + : __imm(bpf_get_prandom_u32) 971 + : __clobber_all); 972 + } 973 + 974 + SEC("socket") 975 + __success __retval(1) 976 + __naked void rsh32_unknown_bounds(void) 977 + { 978 + asm volatile (" \ 979 + r6 = 1; \ 980 + call %[bpf_get_prandom_u32]; \ 981 + w0 >>= 28; /* u32: [0, 15] */ \ 982 + if w0 < 16 goto l0_%=; \ 983 + r6 /= 0; /* unreachable */ \ 984 + l0_%=: r0 = r6; \ 985 + exit; \ 986 + " : 987 + : __imm(bpf_get_prandom_u32) 988 + : __clobber_all); 989 + } 990 + 826 991 char _license[] SEC("license") = "GPL";