mirror of
https://github.com/torvalds/linux.git
synced 2026-05-27 08:33:17 +02:00
s390/bpf: Do not increment tailcall count when prog is NULL
Currently tail calling a non-existent prog results in tailcall count increment. This is what the interpreter is doing, but this is clearly wrong, so replace load-and-increment and compare-and-jump with load and compare-and-jump, conditionally followed by increment and store. Reported-by: Hari Bathini <hbathini@linux.ibm.com> Signed-off-by: Ilya Leoshkevich <iii@linux.ibm.com> Link: https://lore.kernel.org/r/20260217161058.101346-1-iii@linux.ibm.com Signed-off-by: Alexei Starovoitov <ast@kernel.org>
This commit is contained in:
parent
3733f4be28
commit
e4094d56c5
|
|
@ -1862,20 +1862,21 @@ static noinline int bpf_jit_insn(struct bpf_jit *jit, struct bpf_prog *fp,
|
|||
jit->prg);
|
||||
|
||||
/*
|
||||
* if (tail_call_cnt++ >= MAX_TAIL_CALL_CNT)
|
||||
* if (tail_call_cnt >= MAX_TAIL_CALL_CNT)
|
||||
* goto out;
|
||||
*
|
||||
* tail_call_cnt is read into %w0, which needs to be preserved
|
||||
* until it's incremented and flushed.
|
||||
*/
|
||||
|
||||
off = jit->frame_off +
|
||||
offsetof(struct prog_frame, tail_call_cnt);
|
||||
/* lhi %w0,1 */
|
||||
EMIT4_IMM(0xa7080000, REG_W0, 1);
|
||||
/* laal %w1,%w0,off(%r15) */
|
||||
EMIT6_DISP_LH(0xeb000000, 0x00fa, REG_W1, REG_W0, REG_15, off);
|
||||
/* clij %w1,MAX_TAIL_CALL_CNT-1,0x2,out */
|
||||
/* ly %w0,off(%r15) */
|
||||
EMIT6_DISP_LH(0xe3000000, 0x0058, REG_W0, REG_0, REG_15, off);
|
||||
/* clij %w0,MAX_TAIL_CALL_CNT,0xa,out */
|
||||
patch_2_clij = jit->prg;
|
||||
EMIT6_PCREL_RIEC(0xec000000, 0x007f, REG_W1, MAX_TAIL_CALL_CNT - 1,
|
||||
2, jit->prg);
|
||||
EMIT6_PCREL_RIEC(0xec000000, 0x007f, REG_W0, MAX_TAIL_CALL_CNT,
|
||||
0xa, jit->prg);
|
||||
|
||||
/*
|
||||
* prog = array->ptrs[index];
|
||||
|
|
@ -1894,6 +1895,12 @@ static noinline int bpf_jit_insn(struct bpf_jit *jit, struct bpf_prog *fp,
|
|||
patch_3_brc = jit->prg;
|
||||
EMIT4_PCREL_RIC(0xa7040000, 8, jit->prg);
|
||||
|
||||
/* tail_call_cnt++; */
|
||||
/* ahi %w0,1 */
|
||||
EMIT4_IMM(0xa70a0000, REG_W0, 1);
|
||||
/* sty %w0,off(%r15) */
|
||||
EMIT6_DISP_LH(0xe3000000, 0x0050, REG_W0, REG_0, REG_15, off);
|
||||
|
||||
/*
|
||||
* Restore registers before calling function
|
||||
*/
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user