forked from OSchip/llvm-project
9276ef05c8
Currently, for code like below, === inner_map = bpf_map_lookup_elem(outer_map, &port_key); if (!inner_map) { inner_map = &fallback_map; } === the compiler generates (pseudo) code like the below: === I1: r1 = bpf_map_lookup_elem(outer_map, &port_key); I2: r2 = 0 I3: if (r1 == r2) I4: r6 = &fallback_map I5: ... === During kernel verification process, After I1, r1 holds a state map_ptr_or_null. If I3 condition is not taken (path [I1, I2, I3, I5]), supposedly r1 should become map_ptr. Unfortunately, kernel does not recognize this pattern and r1 remains map_ptr_or_null at insn I5. This will cause verificaiton failure later on. Kernel, however, is able to recognize pattern "if (r1 == 0)" properly and give a map_ptr state to r1 in the above case. LLVM here generates suboptimal code which causes kernel verification failure. This patch fixes the issue by changing BPF insn pattern matching and lowering to generate proper codes if the righthand parameter of the above condition is a constant. A test case is also added. Signed-off-by: Yonghong Song <yhs@fb.com> llvm-svn: 308080 |
||
---|---|---|
.. | ||
alu8.ll | ||
atomics.ll | ||
basictest.ll | ||
byval.ll | ||
cc_args.ll | ||
cc_args_be.ll | ||
cc_ret.ll | ||
cmp.ll | ||
dwarfdump.ll | ||
ex1.ll | ||
fi_ri.ll | ||
intrinsics.ll | ||
lit.local.cfg | ||
load.ll | ||
loops.ll | ||
many_args1.ll | ||
many_args2.ll | ||
mem_offset.ll | ||
mem_offset_be.ll | ||
objdump_atomics.ll | ||
objdump_intrinsics.ll | ||
objdump_trivial.ll | ||
reloc.ll | ||
remove_truncate_1.ll | ||
remove_truncate_2.ll | ||
rodata_1.ll | ||
rodata_2.ll | ||
rodata_3.ll | ||
rodata_4.ll | ||
sanity.ll | ||
sdiv_error.ll | ||
select_ri.ll | ||
setcc.ll | ||
shifts.ll | ||
sockex2.ll | ||
struct_ret1.ll | ||
struct_ret2.ll | ||
undef.ll | ||
vararg1.ll | ||
warn-call.ll | ||
warn-stack.ll |