All of lore.kernel.org
 help / color / mirror / Atom feed
* x86 BPF JIT failed to load a program with continuous JMPs
@ 2020-11-03  4:00 Gary Lin
  0 siblings, 0 replies; only message in thread
From: Gary Lin @ 2020-11-03  4:00 UTC (permalink / raw)
  To: bpf; +Cc: andreas.taschner

Hi,

We recently got a bug report from a customer about the x86 BPF JIT, and
the bpf program is like this:

l0:     ldh [4]
l1:     jeq #0x537d, l2, l40
l2:     ld [0]
l3:     jeq #0xfa163e0d, l4, l40
l4:     ldh [12]
l5:     ldx #0xe
l6:     jeq #0x86dd, l41, l7
l7:     jeq #0x800, l8, l41
l8:     ld [x+16]
l9:     ja 41
  [... repeated ja 41 ]
l40:    ja 41
l41:    ret #0
l42:    ld #len
l43:    ret a

They declared a sock_filter array with a lot of "ja 41" in order to
replace them dynamically with other BPF instructions and attached the
program to a socket with setsockopt(SO_ATTACH_FILTER). It worked fine
with BPF interpreter until upgrading to the kernel with
BPF_JIT_ALWAYS_ON.

In the beginning, I thought it's rejected by the verifier due to
unreachable instructions. However, the verifier didn't involve since
it's attached through SO_ATTACH_FILTER. The program was sent to BPF
JIT directly and rejected with ENOTSUPP. In the end, I found that it
failed in bpf_int_jit_compile()(*). Every time do_jit() was invoked,
it removed one "ja 41" right before "ret #0", so bpf_int_jit_compile()
failed to remove all "ja 41" within 20 runs. If I reduced the number of
JMPs to 19, BPF JIT accepted the program. It seems a corner case that
BPF JIT could not handle.

A quick "fix" might be iterating do_jit() until the image converges,
but I guess the limited iteration is designed to bound the compilation
time of BPF JIT, so I'm not sure if this is a good option.

BTW, as a workaround, I suggested the customer to replace the JMPs with
0 offset JMPs so that do_jit() can optimize them out in 1 pass. But I
still would like to know how to handle this kind of programs properly.

Thanks

Gary Lin

(*) https://github.com/torvalds/linux/blob/v5.9/arch/x86/net/bpf_jit_comp.c#L1876-L1921


^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2020-11-03  4:01 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-11-03  4:00 x86 BPF JIT failed to load a program with continuous JMPs Gary Lin

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.