[RFC PATCH 0/7] kasan: RISC-V support for KASAN_SW_TAGS using pointer masking

Andrey Konovalov andreyknvl at gmail.com
Wed Aug 14 09:03:12 PDT 2024


On Wed, Aug 14, 2024 at 10:56 AM Samuel Holland
<samuel.holland at sifive.com> wrote:
>
> This series implements support for software tag-based KASAN using the
> RISC-V pointer masking extension[1], which supports 7 and/or 16-bit
> tags. This implementation uses 7-bit tags, so it is compatible with
> either hardware mode. Patch 3 adds supports for KASAN_SW_TAGS with tag
> widths other than 8 bits.

This is awesome!

> Pointer masking is an optional ISA extension, and it must be enabled
> using an SBI call to firmware on each CPU. If the SBI call fails on the
> boot CPU, KASAN is globally disabled. Patch 2 adds support for boot-time
> disabling of KASAN_SW_TAGS.
>
> The SBI call is part of the upcoming SBI Firmware Features (FWFT)
> extension[2][3]. Since generic FWFT support is not yet merged to Linux,
> I open-coded the sbi_ecall() in this RFC to keep this series focused.
>
> With my RISC-V KASAN fixes series[4] applied, this implementation passes
> all but one of the KASAN KUnit tests. It fails vmalloc_percpu(), which
> also fails on arm64:

Hm, this test passes on arm64 for me. Could you share the kernel
config that you used?


>
>       ...
>       ok 65 vmalloc_oob
>       ok 66 vmap_tags
>       ok 67 vm_map_ram_tags
>       # vmalloc_percpu: EXPECTATION FAILED at mm/kasan/kasan_test.c:1785
>       Expected (u8)((u8)((u64)(c_ptr) >> 57)) < (u8)0x7f, but
>           (u8)((u8)((u64)(c_ptr) >> 57)) == 127 (0x7f)
>           (u8)0x7f == 127 (0x7f)
>       # vmalloc_percpu: EXPECTATION FAILED at mm/kasan/kasan_test.c:1785
>       Expected (u8)((u8)((u64)(c_ptr) >> 57)) < (u8)0x7f, but
>           (u8)((u8)((u64)(c_ptr) >> 57)) == 127 (0x7f)
>           (u8)0x7f == 127 (0x7f)
>       # vmalloc_percpu: EXPECTATION FAILED at mm/kasan/kasan_test.c:1785
>       Expected (u8)((u8)((u64)(c_ptr) >> 57)) < (u8)0x7f, but
>           (u8)((u8)((u64)(c_ptr) >> 57)) == 127 (0x7f)
>           (u8)0x7f == 127 (0x7f)
>       # vmalloc_percpu: EXPECTATION FAILED at mm/kasan/kasan_test.c:1785
>       Expected (u8)((u8)((u64)(c_ptr) >> 57)) < (u8)0x7f, but
>           (u8)((u8)((u64)(c_ptr) >> 57)) == 127 (0x7f)
>           (u8)0x7f == 127 (0x7f)
>       not ok 68 vmalloc_percpu
>       ok 69 match_all_not_assigned
>       ok 70 match_all_ptr_tag
>       ...
>   # kasan: pass:62 fail:1 skip:8 total:71
>   # Totals: pass:62 fail:1 skip:8 total:71
>
> I'm not sure how I'm supposed to hook in to the percpu allocator.
>
> When running with hardware or firmware that doesn't support pointer
> masking, the kernel still boots successfully:
>
>   kasan: test: Can't run KASAN tests with KASAN disabled
>       # kasan:     # failed to initialize (-1)
>   not ok 1 kasan
>
> If stack tagging is enabled but pointer masking is unsupported, an extra
> change (patch 7) is required so all pointers to stack variables are
> tagged with KASAN_TAG_KERENL and can be dereferenced. I'm not sure if
> this change should be RISC-V specific or made more generic.
>
> This series can be tested by applying patch series to LLVM[5], QEMU[6],
> and OpenSBI[7].
>
> [1]: https://github.com/riscv/riscv-j-extension/releases/download/pointer-masking-v1.0.0-rc2/pointer-masking-v1.0.0-rc2.pdf
> [2]: https://github.com/riscv-non-isa/riscv-sbi-doc/blob/master/src/ext-firmware-features.adoc
> [3]: https://github.com/riscv-non-isa/riscv-sbi-doc/pull/161
> [4]: https://lore.kernel.org/linux-riscv/20240801033725.28816-1-samuel.holland@sifive.com/
> [5]: https://github.com/SiFiveHolland/llvm-project/commits/up/riscv64-kernel-hwasan
> [6]: https://lore.kernel.org/qemu-devel/20240511101053.1875596-1-me@deliversmonkey.space/
> [7]: https://lists.infradead.org/pipermail/opensbi/2024-August/007244.html
>
>
> Samuel Holland (7):
>   kasan: sw_tags: Use arithmetic shift for shadow computation
>   kasan: sw_tags: Check kasan_flag_enabled at runtime
>   kasan: sw_tags: Support tag widths less than 8 bits
>   riscv: Do not rely on KASAN to define the memory layout
>   riscv: Align the sv39 linear map to 16 GiB
>   riscv: Implement KASAN_SW_TAGS
>   kasan: sw_tags: Support runtime stack tagging control for RISC-V
>
>  Documentation/arch/riscv/vm-layout.rst | 10 ++---
>  Documentation/dev-tools/kasan.rst      | 14 +++---
>  arch/arm64/Kconfig                     | 10 ++---
>  arch/arm64/include/asm/kasan.h         |  6 ++-
>  arch/arm64/include/asm/memory.h        |  8 ++++
>  arch/arm64/include/asm/uaccess.h       |  1 +
>  arch/arm64/mm/kasan_init.c             |  7 ++-
>  arch/riscv/Kconfig                     |  4 +-
>  arch/riscv/include/asm/cache.h         |  4 ++
>  arch/riscv/include/asm/kasan.h         | 29 +++++++++++-
>  arch/riscv/include/asm/page.h          | 21 +++++++--
>  arch/riscv/include/asm/pgtable.h       |  6 +++
>  arch/riscv/include/asm/tlbflush.h      |  4 +-
>  arch/riscv/kernel/setup.c              |  6 +++
>  arch/riscv/kernel/smpboot.c            |  8 +++-
>  arch/riscv/lib/Makefile                |  2 +
>  arch/riscv/lib/kasan_sw_tags.S         | 61 ++++++++++++++++++++++++++
>  arch/riscv/mm/init.c                   |  2 +-
>  arch/riscv/mm/kasan_init.c             | 30 ++++++++++++-
>  arch/riscv/mm/physaddr.c               |  4 ++
>  include/linux/kasan-enabled.h          | 15 +++----
>  include/linux/kasan-tags.h             | 13 +++---
>  include/linux/kasan.h                  | 10 ++++-
>  mm/kasan/hw_tags.c                     | 10 -----
>  mm/kasan/kasan.h                       |  2 +
>  mm/kasan/sw_tags.c                     |  9 ++++
>  mm/kasan/tags.c                        | 10 +++++
>  scripts/Makefile.kasan                 |  5 +++
>  scripts/gdb/linux/mm.py                |  5 ++-
>  29 files changed, 255 insertions(+), 61 deletions(-)
>  create mode 100644 arch/riscv/lib/kasan_sw_tags.S
>
> --
> 2.45.1
>



More information about the linux-riscv mailing list