[PATCH v3 0/5] Defer the IOMMU translation in the CPU path and support access_type

Jim Shu posted 5 patches 3 weeks, 3 days ago
Patches applied successfully (tree, apply log)
git fetch https://github.com/patchew-project/qemu tags/patchew/20260506033642.3641390-1-jim.shu@sifive.com
Maintainers: Richard Henderson <richard.henderson@linaro.org>, Paolo Bonzini <pbonzini@redhat.com>, "Philippe Mathieu-Daudé" <philmd@linaro.org>, Zhao Liu <zhao1.liu@intel.com>, Peter Xu <peterx@redhat.com>, Michael Rolnik <mrolnik@gmail.com>, Song Gao <gaosong@loongson.cn>, Laurent Vivier <laurent@vivier.eu>, "Edgar E. Iglesias" <edgar.iglesias@gmail.com>, Aurelien Jarno <aurelien@aurel32.net>, Jiaxun Yang <jiaxun.yang@flygoat.com>, Aleksandar Rikalo <arikalo@gmail.com>, Stafford Horne <shorne@gmail.com>, Nicholas Piggin <npiggin@gmail.com>, Chinmay Rath <rathc@linux.ibm.com>, Glenn Miles <milesg@linux.ibm.com>, Harsh Prateek Bora <harshpb@linux.ibm.com>, Palmer Dabbelt <palmer@dabbelt.com>, Alistair Francis <alistair.francis@wdc.com>, Weiwei Li <liwei1518@gmail.com>, Daniel Henrique Barboza <daniel.barboza@oss.qualcomm.com>, Liu Zhiwei <zhiwei_liu@linux.alibaba.com>, Chao Liu <chao.liu.zevorn@gmail.com>, Yoshinori Sato <yoshinori.sato@nifty.com>, Ilya Leoshkevich <iii@linux.ibm.com>, David Hildenbrand <david@kernel.org>, Cornelia Huck <cohuck@redhat.com>, Eric Farman <farman@linux.ibm.com>, Matthew Rosato <mjrosato@linux.ibm.com>, Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk>, Artyom Tarasenko <atar4qemu@gmail.com>, Max Filippov <jcmvbkbc@gmail.com>
accel/tcg/cputlb.c                   | 247 +++++++++++++++++++++++++--
include/accel/tcg/iommu.h            |  17 +-
include/exec/cputlb.h                |  11 +-
include/exec/tlb-flags.h             |   4 +-
include/hw/core/cpu.h                |  15 ++
system/physmem.c                     |  60 ++++++-
target/alpha/helper.c                |   2 +-
target/avr/helper.c                  |   3 +-
target/i386/tcg/system/excp_helper.c |   3 +-
target/loongarch/tcg/tlb_helper.c    |   2 +-
target/m68k/helper.c                 |  10 +-
target/microblaze/helper.c           |   8 +-
target/mips/tcg/system/tlb_helper.c  |   4 +-
target/or1k/mmu.c                    |   2 +-
target/ppc/mmu_helper.c              |   2 +-
target/riscv/cpu_helper.c            |   2 +-
target/rx/cpu.c                      |   3 +-
target/s390x/tcg/excp_helper.c       |   2 +-
target/sh4/helper.c                  |   3 +-
target/sparc/mmu_helper.c            |   6 +-
target/tricore/helper.c              |   2 +-
target/xtensa/helper.c               |   3 +-
22 files changed, 354 insertions(+), 57 deletions(-)
[PATCH v3 0/5] Defer the IOMMU translation in the CPU path and support access_type
Posted by Jim Shu 3 weeks, 3 days ago
Incoming security protection devices feature more complex IOMMUMemoryRegion
implementation in the CPU path than ARM MPC device. For example,
RISC-V wgChecker [1] may permit the access with only RO/WO permissions.
Consequently, the IOMMUMemoryRegion could return different sections for
read & write access.

To support such IOMMUMemoryRegion behavior in the CPU path, the design
of IOMMU translation must be updated:

1. address_space_translate*() must now pass the access_type to
   IOMMUMemoryRegion.
2. Since IOMMU translation results are too complex to be fully stored
   in the CPU TLB. we will defer the translation until the actual access
   occurs. Also, TLB is allowed to store the untranslated IOMMU region.

To implement deferred IOMMU translation, this patchset introduces the
following changes:

1. tlb_set_page_full() no longer translates the IOMMU region
   immediately. Instead, it stores the untranslated region directly in
   the TLB. A new slow-path flag, TLB_IOMMU, is introduced to force
   access into the slow path when a region has not yet been translated
   in the TLB entry.

2. When the CPU utilizes a TLB entry in the slow path, it should perform
   the lazy IOMMU translation of the access_type first. The resulting
   translated region and access type are stored in CPUTLBEntryFull.
   Since the slow path always performs lazy translation first, we can
   switch the CPUTLBEntryFull content to the correct access type before
   use.

3. To accelerate memory access in the fast path, lazy translation can
   update the addend of the CPUTLBEntry when translating the region to a
   host memory region. We restrict the IOMMU region to have a single
   non-zero 'addend' across all permissions. If a second 'addend' is
   present for a CPUTLBEntry, QEMU will trigger an assertion. This
   limitation is sufficient for security devices, as their "secondary"
   region is typically an IO region used to emulate device error
   handling when access is rejected.

4. To support non-slow TLB flags, lazy translation can update the TLB
   flags in the 'addr_idx' of the CPUTLBEntry. Lazy translation only
   updates the flags for the permissions specified in @prot. This
   ensures that each access_type of a translated region to maintains
   independent TLB flags. For example, TLB_DIRTY of memory region will
   not be "polluted" from other permission that translated to different
   region.

Both RISC-V wgChecker [1] and RISC-V IOPMP [2] devices require this
feature.

[1] RISC-V WG:
https://patchew.org/QEMU/20251021155548.584543-1-jim.shu@sifive.com/
[2] RISC-V IOPMP:
https://patchew.org/QEMU/20250312093735.1517740-1-ethan84@andestech.com/

Changed since v2:
- Fix unused initialized memory error

Changed since v1:
- Remove the ping-pong TLB entry behavior. Instead, defer the IOMMU
  translation until actual access in the CPU path. Provide a IOMMU
  lazy translation function with the special handling of 'addend'
  and 'addr_idx' fields of CPUTLBEntry.
- Fix the checkpatch warning.

Jim Shu (5):
  accel/tcg: Pass access_type as an argument of tlb_set_page*()
  accel/tcg: address_space_translate*() will pass the correct
    iommu_flags
  accel/tcg: Provide early AS translate function
  accel/tcg: Add IOMMU lazy translation function
  accel/tcg: Support IOMMU lazy translation in CPU TLB

 accel/tcg/cputlb.c                   | 247 +++++++++++++++++++++++++--
 include/accel/tcg/iommu.h            |  17 +-
 include/exec/cputlb.h                |  11 +-
 include/exec/tlb-flags.h             |   4 +-
 include/hw/core/cpu.h                |  15 ++
 system/physmem.c                     |  60 ++++++-
 target/alpha/helper.c                |   2 +-
 target/avr/helper.c                  |   3 +-
 target/i386/tcg/system/excp_helper.c |   3 +-
 target/loongarch/tcg/tlb_helper.c    |   2 +-
 target/m68k/helper.c                 |  10 +-
 target/microblaze/helper.c           |   8 +-
 target/mips/tcg/system/tlb_helper.c  |   4 +-
 target/or1k/mmu.c                    |   2 +-
 target/ppc/mmu_helper.c              |   2 +-
 target/riscv/cpu_helper.c            |   2 +-
 target/rx/cpu.c                      |   3 +-
 target/s390x/tcg/excp_helper.c       |   2 +-
 target/sh4/helper.c                  |   3 +-
 target/sparc/mmu_helper.c            |   6 +-
 target/tricore/helper.c              |   2 +-
 target/xtensa/helper.c               |   3 +-
 22 files changed, 354 insertions(+), 57 deletions(-)

-- 
2.43.0
Re: [PATCH v3 0/5] Defer the IOMMU translation in the CPU path and support access_type
Posted by Jim Shu 1 week, 1 day ago
Hi all,

Gentle ping on this patch.
Any suggestion is welcome.

Thanks,
Jim Shu





On Wed, May 6, 2026 at 11:36 AM Jim Shu <jim.shu@sifive.com> wrote:
>
> Incoming security protection devices feature more complex IOMMUMemoryRegion
> implementation in the CPU path than ARM MPC device. For example,
> RISC-V wgChecker [1] may permit the access with only RO/WO permissions.
> Consequently, the IOMMUMemoryRegion could return different sections for
> read & write access.
>
> To support such IOMMUMemoryRegion behavior in the CPU path, the design
> of IOMMU translation must be updated:
>
> 1. address_space_translate*() must now pass the access_type to
>    IOMMUMemoryRegion.
> 2. Since IOMMU translation results are too complex to be fully stored
>    in the CPU TLB. we will defer the translation until the actual access
>    occurs. Also, TLB is allowed to store the untranslated IOMMU region.
>
> To implement deferred IOMMU translation, this patchset introduces the
> following changes:
>
> 1. tlb_set_page_full() no longer translates the IOMMU region
>    immediately. Instead, it stores the untranslated region directly in
>    the TLB. A new slow-path flag, TLB_IOMMU, is introduced to force
>    access into the slow path when a region has not yet been translated
>    in the TLB entry.
>
> 2. When the CPU utilizes a TLB entry in the slow path, it should perform
>    the lazy IOMMU translation of the access_type first. The resulting
>    translated region and access type are stored in CPUTLBEntryFull.
>    Since the slow path always performs lazy translation first, we can
>    switch the CPUTLBEntryFull content to the correct access type before
>    use.
>
> 3. To accelerate memory access in the fast path, lazy translation can
>    update the addend of the CPUTLBEntry when translating the region to a
>    host memory region. We restrict the IOMMU region to have a single
>    non-zero 'addend' across all permissions. If a second 'addend' is
>    present for a CPUTLBEntry, QEMU will trigger an assertion. This
>    limitation is sufficient for security devices, as their "secondary"
>    region is typically an IO region used to emulate device error
>    handling when access is rejected.
>
> 4. To support non-slow TLB flags, lazy translation can update the TLB
>    flags in the 'addr_idx' of the CPUTLBEntry. Lazy translation only
>    updates the flags for the permissions specified in @prot. This
>    ensures that each access_type of a translated region to maintains
>    independent TLB flags. For example, TLB_DIRTY of memory region will
>    not be "polluted" from other permission that translated to different
>    region.
>
> Both RISC-V wgChecker [1] and RISC-V IOPMP [2] devices require this
> feature.
>
> [1] RISC-V WG:
> https://patchew.org/QEMU/20251021155548.584543-1-jim.shu@sifive.com/
> [2] RISC-V IOPMP:
> https://patchew.org/QEMU/20250312093735.1517740-1-ethan84@andestech.com/
>
> Changed since v2:
> - Fix unused initialized memory error
>
> Changed since v1:
> - Remove the ping-pong TLB entry behavior. Instead, defer the IOMMU
>   translation until actual access in the CPU path. Provide a IOMMU
>   lazy translation function with the special handling of 'addend'
>   and 'addr_idx' fields of CPUTLBEntry.
> - Fix the checkpatch warning.
>
> Jim Shu (5):
>   accel/tcg: Pass access_type as an argument of tlb_set_page*()
>   accel/tcg: address_space_translate*() will pass the correct
>     iommu_flags
>   accel/tcg: Provide early AS translate function
>   accel/tcg: Add IOMMU lazy translation function
>   accel/tcg: Support IOMMU lazy translation in CPU TLB
>
>  accel/tcg/cputlb.c                   | 247 +++++++++++++++++++++++++--
>  include/accel/tcg/iommu.h            |  17 +-
>  include/exec/cputlb.h                |  11 +-
>  include/exec/tlb-flags.h             |   4 +-
>  include/hw/core/cpu.h                |  15 ++
>  system/physmem.c                     |  60 ++++++-
>  target/alpha/helper.c                |   2 +-
>  target/avr/helper.c                  |   3 +-
>  target/i386/tcg/system/excp_helper.c |   3 +-
>  target/loongarch/tcg/tlb_helper.c    |   2 +-
>  target/m68k/helper.c                 |  10 +-
>  target/microblaze/helper.c           |   8 +-
>  target/mips/tcg/system/tlb_helper.c  |   4 +-
>  target/or1k/mmu.c                    |   2 +-
>  target/ppc/mmu_helper.c              |   2 +-
>  target/riscv/cpu_helper.c            |   2 +-
>  target/rx/cpu.c                      |   3 +-
>  target/s390x/tcg/excp_helper.c       |   2 +-
>  target/sh4/helper.c                  |   3 +-
>  target/sparc/mmu_helper.c            |   6 +-
>  target/tricore/helper.c              |   2 +-
>  target/xtensa/helper.c               |   3 +-
>  22 files changed, 354 insertions(+), 57 deletions(-)
>
> --
> 2.43.0
>