mbox series

[bpf-next,v2,00/15] bpf: Support new insns from cpu v4

Message ID 20230713060718.388258-1-yhs@fb.com (mailing list archive)
Headers show
Series bpf: Support new insns from cpu v4 | expand

Message

Yonghong Song July 13, 2023, 6:07 a.m. UTC
In previous discussion ([1]), it is agreed that we should introduce
cpu version 4 (llvm flag -mcpu=v4) which contains some instructions
which can simplify code, make code easier to understand, fix the
existing problem, or simply for feature completeness. More specifically,
the following new insns are proposed:
  . sign extended load
  . sign extended mov
  . bswap
  . signed div/mod
  . ja with 32-bit offset

This patch set added kernel support for insns proposed in [1] except
BPF_ST which already has full kernel support. Beside the above proposed
insns, LLVM will generate BPF_ST insn as well under -mcpu=v4 ([2]).

The patchset implements interpreter and jit support for these new
insns as well as necessary verifier support.

To test this patch set, you need to have latest llvm from 'main' branch
of llvm-project repo and apply [2] on top of it.

  [1] https://lore.kernel.org/bpf/4bfe98be-5333-1c7e-2f6d-42486c8ec039@meta.com/
  [2] https://reviews.llvm.org/D144829

Changelogs:
  RFCv1 -> v2:
   . add more verifier supports for signed extend load and mov insns.
   . rename some insn names to be more consistent with intel practice.
   . add cpuv4 test runner for test progs.
   . add more unit and C tests.
   . add documentation.

Yonghong Song (15):
  bpf: Support new sign-extension load insns
  bpf: Fix sign-extension ctx member accesses
  bpf: Support new sign-extension mov insns
  bpf: Support new unconditional bswap instruction
  bpf: Support new signed div/mod instructions.
  bpf: Fix jit blinding with new sdiv/smov insns
  bpf: Support new 32bit offset jmp instruction
  selftests/bpf: Add a cpuv4 test runner for cpu=v4 testing
  selftests/bpf: Add unit tests for new sign-extension load insns
  selftests/bpf: Add unit tests for new sign-extension mov insns
  selftests/bpf: Add unit tests for new bswap insns
  selftests/bpf: Add unit tests for new sdiv/smod insns
  selftests/bpf: Add unit tests for new gotol insn
  selftests/bpf: Test ldsx with more complex cases
  docs/bpf: Add documentation for new instructions

 Documentation/bpf/bpf_design_QA.rst           |   5 -
 .../bpf/standardization/instruction-set.rst   | 100 ++-
 arch/x86/net/bpf_jit_comp.c                   | 131 ++-
 include/linux/filter.h                        |  14 +-
 include/uapi/linux/bpf.h                      |   1 +
 kernel/bpf/cgroup.c                           |  14 +-
 kernel/bpf/core.c                             | 174 +++-
 kernel/bpf/verifier.c                         | 315 ++++++--
 tools/include/uapi/linux/bpf.h                |   1 +
 tools/testing/selftests/bpf/.gitignore        |   2 +
 tools/testing/selftests/bpf/Makefile          |  18 +-
 .../selftests/bpf/bpf_testmod/bpf_testmod.c   |   9 +-
 .../selftests/bpf/prog_tests/test_ldsx_insn.c |  88 ++
 .../selftests/bpf/prog_tests/verifier.c       |  10 +
 .../selftests/bpf/progs/test_ldsx_insn.c      |  75 ++
 .../selftests/bpf/progs/verifier_bswap.c      |  45 ++
 .../selftests/bpf/progs/verifier_gotol.c      |  30 +
 .../selftests/bpf/progs/verifier_ldsx.c       | 115 +++
 .../selftests/bpf/progs/verifier_movsx.c      | 177 ++++
 .../selftests/bpf/progs/verifier_sdiv.c       | 763 ++++++++++++++++++
 20 files changed, 1929 insertions(+), 158 deletions(-)
 create mode 100644 tools/testing/selftests/bpf/prog_tests/test_ldsx_insn.c
 create mode 100644 tools/testing/selftests/bpf/progs/test_ldsx_insn.c
 create mode 100644 tools/testing/selftests/bpf/progs/verifier_bswap.c
 create mode 100644 tools/testing/selftests/bpf/progs/verifier_gotol.c
 create mode 100644 tools/testing/selftests/bpf/progs/verifier_ldsx.c
 create mode 100644 tools/testing/selftests/bpf/progs/verifier_movsx.c
 create mode 100644 tools/testing/selftests/bpf/progs/verifier_sdiv.c

Comments

Eduard Zingerman July 17, 2023, 1:39 a.m. UTC | #1
On Wed, 2023-07-12 at 23:07 -0700, Yonghong Song wrote:
> > In previous discussion ([1]), it is agreed that we should introduce
> > cpu version 4 (llvm flag -mcpu=v4) which contains some instructions
> > which can simplify code, make code easier to understand, fix the
> > existing problem, or simply for feature completeness. More specifically,
> > the following new insns are proposed:
> >   . sign extended load
> >   . sign extended mov
> >   . bswap
> >   . signed div/mod
> >   . ja with 32-bit offset
> > 
> > This patch set added kernel support for insns proposed in [1] except
> > BPF_ST which already has full kernel support. Beside the above proposed
> > insns, LLVM will generate BPF_ST insn as well under -mcpu=v4 ([2]).
> > 
> > The patchset implements interpreter and jit support for these new
> > insns as well as necessary verifier support.

Hi Yonghong,

Sorry for delayed response, I'm still in the middle of the series.
I've tested this patch-set using updated LLVM version and have
a few notes:
- kernel/bpf/disasm.c needs an update to handle new instructions;
- test_verifier test 'invalid 64-bit BPF_END' from basic_instr.c
 is failing because '.code = BPF_ALU64 | BPF_END | BPF_TO_LE'
 is now valid;
- I've looked through the usage of BPF_LDX and found that there
 is a function seccomp.c:seccomp_check_filter(), that directly
 checks possible CLASS / CODE combinations. Should this function
 be updated to handle new instructions?

Thanks,
Eduard

> > 
> > To test this patch set, you need to have latest llvm from 'main' branch
> > of llvm-project repo and apply [2] on top of it.
> > 
> >   [1] https://lore.kernel.org/bpf/4bfe98be-5333-1c7e-2f6d-42486c8ec039@meta.com/
> >   [2] https://reviews.llvm.org/D144829
> > 
> > Changelogs:
> >   RFCv1 -> v2:
> >    . add more verifier supports for signed extend load and mov insns.
> >    . rename some insn names to be more consistent with intel practice.
> >    . add cpuv4 test runner for test progs.
> >    . add more unit and C tests.
> >    . add documentation.
> > 
> > Yonghong Song (15):
> >   bpf: Support new sign-extension load insns
> >   bpf: Fix sign-extension ctx member accesses
> >   bpf: Support new sign-extension mov insns
> >   bpf: Support new unconditional bswap instruction
> >   bpf: Support new signed div/mod instructions.
> >   bpf: Fix jit blinding with new sdiv/smov insns
> >   bpf: Support new 32bit offset jmp instruction
> >   selftests/bpf: Add a cpuv4 test runner for cpu=v4 testing
> >   selftests/bpf: Add unit tests for new sign-extension load insns
> >   selftests/bpf: Add unit tests for new sign-extension mov insns
> >   selftests/bpf: Add unit tests for new bswap insns
> >   selftests/bpf: Add unit tests for new sdiv/smod insns
> >   selftests/bpf: Add unit tests for new gotol insn
> >   selftests/bpf: Test ldsx with more complex cases
> >   docs/bpf: Add documentation for new instructions
> > 
> >  Documentation/bpf/bpf_design_QA.rst           |   5 -
> >  .../bpf/standardization/instruction-set.rst   | 100 ++-
> >  arch/x86/net/bpf_jit_comp.c                   | 131 ++-
> >  include/linux/filter.h                        |  14 +-
> >  include/uapi/linux/bpf.h                      |   1 +
> >  kernel/bpf/cgroup.c                           |  14 +-
> >  kernel/bpf/core.c                             | 174 +++-
> >  kernel/bpf/verifier.c                         | 315 ++++++--
> >  tools/include/uapi/linux/bpf.h                |   1 +
> >  tools/testing/selftests/bpf/.gitignore        |   2 +
> >  tools/testing/selftests/bpf/Makefile          |  18 +-
> >  .../selftests/bpf/bpf_testmod/bpf_testmod.c   |   9 +-
> >  .../selftests/bpf/prog_tests/test_ldsx_insn.c |  88 ++
> >  .../selftests/bpf/prog_tests/verifier.c       |  10 +
> >  .../selftests/bpf/progs/test_ldsx_insn.c      |  75 ++
> >  .../selftests/bpf/progs/verifier_bswap.c      |  45 ++
> >  .../selftests/bpf/progs/verifier_gotol.c      |  30 +
> >  .../selftests/bpf/progs/verifier_ldsx.c       | 115 +++
> >  .../selftests/bpf/progs/verifier_movsx.c      | 177 ++++
> >  .../selftests/bpf/progs/verifier_sdiv.c       | 763 ++++++++++++++++++
> >  20 files changed, 1929 insertions(+), 158 deletions(-)
> >  create mode 100644 tools/testing/selftests/bpf/prog_tests/test_ldsx_insn.c
> >  create mode 100644 tools/testing/selftests/bpf/progs/test_ldsx_insn.c
> >  create mode 100644 tools/testing/selftests/bpf/progs/verifier_bswap.c
> >  create mode 100644 tools/testing/selftests/bpf/progs/verifier_gotol.c
> >  create mode 100644 tools/testing/selftests/bpf/progs/verifier_ldsx.c
> >  create mode 100644 tools/testing/selftests/bpf/progs/verifier_movsx.c
> >  create mode 100644 tools/testing/selftests/bpf/progs/verifier_sdiv.c
> >
Alexei Starovoitov July 17, 2023, 4:56 p.m. UTC | #2
On Sun, Jul 16, 2023 at 6:39 PM Eduard Zingerman <eddyz87@gmail.com> wrote:
> - I've looked through the usage of BPF_LDX and found that there
>  is a function seccomp.c:seccomp_check_filter(), that directly
>  checks possible CLASS / CODE combinations. Should this function
>  be updated to handle new instructions?

This is classic bpf. Why would it change? What is the concern?
Eduard Zingerman July 17, 2023, 5:04 p.m. UTC | #3
On Mon, 2023-07-17 at 09:56 -0700, Alexei Starovoitov wrote:
> On Sun, Jul 16, 2023 at 6:39 PM Eduard Zingerman <eddyz87@gmail.com> wrote:
> > - I've looked through the usage of BPF_LDX and found that there
> >  is a function seccomp.c:seccomp_check_filter(), that directly
> >  checks possible CLASS / CODE combinations. Should this function
> >  be updated to handle new instructions?
> 
> This is classic bpf. Why would it change? What is the concern?

Sorry, I missed the call to `bpf_check_classic()` in filter.c:bpf_prepare_filter().
Yonghong Song July 17, 2023, 9:52 p.m. UTC | #4
On 7/16/23 6:39 PM, Eduard Zingerman wrote:
> On Wed, 2023-07-12 at 23:07 -0700, Yonghong Song wrote:
>>> In previous discussion ([1]), it is agreed that we should introduce
>>> cpu version 4 (llvm flag -mcpu=v4) which contains some instructions
>>> which can simplify code, make code easier to understand, fix the
>>> existing problem, or simply for feature completeness. More specifically,
>>> the following new insns are proposed:
>>>    . sign extended load
>>>    . sign extended mov
>>>    . bswap
>>>    . signed div/mod
>>>    . ja with 32-bit offset
>>>
>>> This patch set added kernel support for insns proposed in [1] except
>>> BPF_ST which already has full kernel support. Beside the above proposed
>>> insns, LLVM will generate BPF_ST insn as well under -mcpu=v4 ([2]).
>>>
>>> The patchset implements interpreter and jit support for these new
>>> insns as well as necessary verifier support.
> 
> Hi Yonghong,
> 
> Sorry for delayed response, I'm still in the middle of the series.
> I've tested this patch-set using updated LLVM version and have
> a few notes:
> - kernel/bpf/disasm.c needs an update to handle new instructions;

Thanks for pointing this out. My bad. I have disasm.c patch in
RFCv1, but somehow during cherry-pick process, I missed it in v2.
Will add it back to next revision.

> - test_verifier test 'invalid 64-bit BPF_END' from basic_instr.c
>   is failing because '.code = BPF_ALU64 | BPF_END | BPF_TO_LE'
>   is now valid;

I didn't run 'test_verifier'. Thanks for pointing it out.
Will run it and fix the problem in the next revision.

> - I've looked through the usage of BPF_LDX and found that there
>   is a function seccomp.c:seccomp_check_filter(), that directly
>   checks possible CLASS / CODE combinations. Should this function
>   be updated to handle new instructions?
> 
> Thanks,
> Eduard
> 
>>>
>>> To test this patch set, you need to have latest llvm from 'main' branch
>>> of llvm-project repo and apply [2] on top of it.
>>>
>>>    [1] https://lore.kernel.org/bpf/4bfe98be-5333-1c7e-2f6d-42486c8ec039@meta.com/
>>>    [2] https://reviews.llvm.org/D144829
>>>
>>> Changelogs:
>>>    RFCv1 -> v2:
>>>     . add more verifier supports for signed extend load and mov insns.
>>>     . rename some insn names to be more consistent with intel practice.
>>>     . add cpuv4 test runner for test progs.
>>>     . add more unit and C tests.
>>>     . add documentation.
>>>
>>> Yonghong Song (15):
>>>    bpf: Support new sign-extension load insns
>>>    bpf: Fix sign-extension ctx member accesses
>>>    bpf: Support new sign-extension mov insns
>>>    bpf: Support new unconditional bswap instruction
>>>    bpf: Support new signed div/mod instructions.
>>>    bpf: Fix jit blinding with new sdiv/smov insns
>>>    bpf: Support new 32bit offset jmp instruction
>>>    selftests/bpf: Add a cpuv4 test runner for cpu=v4 testing
>>>    selftests/bpf: Add unit tests for new sign-extension load insns
>>>    selftests/bpf: Add unit tests for new sign-extension mov insns
>>>    selftests/bpf: Add unit tests for new bswap insns
>>>    selftests/bpf: Add unit tests for new sdiv/smod insns
>>>    selftests/bpf: Add unit tests for new gotol insn
>>>    selftests/bpf: Test ldsx with more complex cases
>>>    docs/bpf: Add documentation for new instructions
>>>
>>>   Documentation/bpf/bpf_design_QA.rst           |   5 -
>>>   .../bpf/standardization/instruction-set.rst   | 100 ++-
>>>   arch/x86/net/bpf_jit_comp.c                   | 131 ++-
>>>   include/linux/filter.h                        |  14 +-
>>>   include/uapi/linux/bpf.h                      |   1 +
>>>   kernel/bpf/cgroup.c                           |  14 +-
>>>   kernel/bpf/core.c                             | 174 +++-
>>>   kernel/bpf/verifier.c                         | 315 ++++++--
>>>   tools/include/uapi/linux/bpf.h                |   1 +
>>>   tools/testing/selftests/bpf/.gitignore        |   2 +
>>>   tools/testing/selftests/bpf/Makefile          |  18 +-
>>>   .../selftests/bpf/bpf_testmod/bpf_testmod.c   |   9 +-
>>>   .../selftests/bpf/prog_tests/test_ldsx_insn.c |  88 ++
>>>   .../selftests/bpf/prog_tests/verifier.c       |  10 +
>>>   .../selftests/bpf/progs/test_ldsx_insn.c      |  75 ++
>>>   .../selftests/bpf/progs/verifier_bswap.c      |  45 ++
>>>   .../selftests/bpf/progs/verifier_gotol.c      |  30 +
>>>   .../selftests/bpf/progs/verifier_ldsx.c       | 115 +++
>>>   .../selftests/bpf/progs/verifier_movsx.c      | 177 ++++
>>>   .../selftests/bpf/progs/verifier_sdiv.c       | 763 ++++++++++++++++++
>>>   20 files changed, 1929 insertions(+), 158 deletions(-)
>>>   create mode 100644 tools/testing/selftests/bpf/prog_tests/test_ldsx_insn.c
>>>   create mode 100644 tools/testing/selftests/bpf/progs/test_ldsx_insn.c
>>>   create mode 100644 tools/testing/selftests/bpf/progs/verifier_bswap.c
>>>   create mode 100644 tools/testing/selftests/bpf/progs/verifier_gotol.c
>>>   create mode 100644 tools/testing/selftests/bpf/progs/verifier_ldsx.c
>>>   create mode 100644 tools/testing/selftests/bpf/progs/verifier_movsx.c
>>>   create mode 100644 tools/testing/selftests/bpf/progs/verifier_sdiv.c
>>>
>
Jose E. Marchesi July 21, 2023, 2:56 p.m. UTC | #5
Hi Yonghong.

>>>>    . sign extended load
>>>>    . sign extended mov
>>>>    . bswap
>>>>    . signed div/mod
>>>>    . ja with 32-bit offset

I am adding the V4 BPF instructions to binutils.  Where is the precise
"pseudo-c" syntax used by the new instructions documented?

For ALU sdiv/smod we are using:

   rd s/= rs
   rd s%= rs

For ALU32 sdiv/smod we are using:

   wd s/= ws
   wd s%= ws

For ALU movs instruction I just made up:

   rd s= (i8) rs
   rd s= (i16) rs
   rd s= (i32) rs

For ALU32 movs I just made up:

   wd s= (i8) ws
   wd s= (i16) ws
   wd s= (i32) ws

Thanks!
Jose E. Marchesi July 24, 2023, 12:17 a.m. UTC | #6
> Hi Yonghong.
>
>>>>>    . sign extended load
>>>>>    . sign extended mov
>>>>>    . bswap
>>>>>    . signed div/mod
>>>>>    . ja with 32-bit offset
>
> I am adding the V4 BPF instructions to binutils.  Where is the precise
> "pseudo-c" syntax used by the new instructions documented?

I looked at the tests in https://reviews.llvm.org/D144829 and:

> For ALU sdiv/smod we are using:
>
>    rd s/= rs
>    rd s%= rs

Looks like I chose wisely, just by chance 8-)

> For ALU movs instruction I just made up:
>
>    rd s= (i8) rs
>    rd s= (i16) rs
>    rd s= (i32) rs

Just changed that in binutils [1] to

  rd = (s8) rs
  rd = (s16) rs
  rd = (s32) rs

> For ALU32 movs I just made up:
>
>    wd s= (i8) ws
>    wd s= (i16) ws
>    wd s= (i32) ws

Just changed that in binutils [1] to

  wd = (s8) ws
  wd = (s16) ws
  wd = (s32) ws

[1] https://sourceware.org/pipermail/binutils/2023-July/128544.html
Jose E. Marchesi July 24, 2023, 1:04 a.m. UTC | #7
>> Hi Yonghong.
>>
>>>>>>    . sign extended load
>>>>>>    . sign extended mov
>>>>>>    . bswap
>>>>>>    . signed div/mod
>>>>>>    . ja with 32-bit offset
>>
>> I am adding the V4 BPF instructions to binutils.  Where is the precise
>> "pseudo-c" syntax used by the new instructions documented?
>
> I looked at the tests in https://reviews.llvm.org/D144829 and:
>
>> For ALU sdiv/smod we are using:
>>
>>    rd s/= rs
>>    rd s%= rs
>
> Looks like I chose wisely, just by chance 8-)
>
>> For ALU movs instruction I just made up:
>>
>>    rd s= (i8) rs
>>    rd s= (i16) rs
>>    rd s= (i32) rs
>
> Just changed that in binutils [1] to
>
>   rd = (s8) rs
>   rd = (s16) rs
>   rd = (s32) rs
>
>> For ALU32 movs I just made up:
>>
>>    wd s= (i8) ws
>>    wd s= (i16) ws
>>    wd s= (i32) ws
>
> Just changed that in binutils [1] to
>
>   wd = (s8) ws
>   wd = (s16) ws
>   wd = (s32) ws
>
> [1] https://sourceware.org/pipermail/binutils/2023-July/128544.html

And finally for byte swap instructions:

    rd = bswap16 rd
    rd = bswap32 rd
    rd = bswap64 rd

https://sourceware.org/pipermail/binutils/2023-July/128546.html

So, at this point we should have support for all the new BPF V4
instructions in the binutils opcodes, assembler and disassembler.

We are working now in getting GCC making good use of them.
Salud!
Yonghong Song July 24, 2023, 2:35 a.m. UTC | #8
On 7/23/23 6:04 PM, Jose E. Marchesi wrote:
> 
>>> Hi Yonghong.
>>>
>>>>>>>     . sign extended load
>>>>>>>     . sign extended mov
>>>>>>>     . bswap
>>>>>>>     . signed div/mod
>>>>>>>     . ja with 32-bit offset
>>>
>>> I am adding the V4 BPF instructions to binutils.  Where is the precise
>>> "pseudo-c" syntax used by the new instructions documented?
>>
>> I looked at the tests in https://reviews.llvm.org/D144829  and:
>>
>>> For ALU sdiv/smod we are using:
>>>
>>>     rd s/= rs
>>>     rd s%= rs
>>
>> Looks like I chose wisely, just by chance 8-)
>>
>>> For ALU movs instruction I just made up:
>>>
>>>     rd s= (i8) rs
>>>     rd s= (i16) rs
>>>     rd s= (i32) rs
>>
>> Just changed that in binutils [1] to
>>
>>    rd = (s8) rs
>>    rd = (s16) rs
>>    rd = (s32) rs
>>
>>> For ALU32 movs I just made up:
>>>
>>>     wd s= (i8) ws
>>>     wd s= (i16) ws
>>>     wd s= (i32) ws
>>
>> Just changed that in binutils [1] to
>>
>>    wd = (s8) ws
>>    wd = (s16) ws
>>    wd = (s32) ws
>>
>> [1] https://sourceware.org/pipermail/binutils/2023-July/128544.html
> 
> And finally for byte swap instructions:
> 
>      rd = bswap16 rd
>      rd = bswap32 rd
>      rd = bswap64 rd
> 
> https://sourceware.org/pipermail/binutils/2023-July/128546.html
> 
> So, at this point we should have support for all the new BPF V4
> instructions in the binutils opcodes, assembler and disassembler.
> 
> We are working now in getting GCC making good use of them.

Sounds great. Thanks!
I plan to push cpu v4 to llvm18 which should be available in the
next week.

> Salud!