From: Ayan Kumar Halder <ayankuma@amd.com>
To: Ayan Kumar Halder <ayan.kumar.halder@amd.com>,
xen-devel@lists.xenproject.org
Cc: Stefano Stabellini <sstabellini@kernel.org>,
Julien Grall <julien@xen.org>,
Bertrand Marquis <bertrand.marquis@arm.com>,
Michal Orzel <michal.orzel@amd.com>,
Volodymyr Babchuk <Volodymyr_Babchuk@epam.com>
Subject: Re: [PATCH v3 6/6] arm/mpu: Enable read/write to protection regions for arm32
Date: Fri, 13 Jun 2025 10:30:54 +0100 [thread overview]
Message-ID: <41eef9a1-1f43-4f2f-b79a-89c0d0ec941b@amd.com> (raw)
In-Reply-To: <20250611143544.3453532-7-ayan.kumar.halder@amd.com>
On 11/06/2025 15:35, Ayan Kumar Halder wrote:
> Define prepare_selector(), read_protection_region() and
> write_protection_region() for arm32. Also, define
> GENERATE_{READ/WRITE}_PR_REG_OTHERS to access MPU regions from 32 to 255.
>
> Enable pr_{get/set}_{base/limit}(), region_is_valid() for arm32.
> Enable pr_of_addr() for arm32.
>
> Signed-off-by: Ayan Kumar Halder <ayan.kumar.halder@amd.com>
> ---
> Changes from :-
>
> v1 - 1. Enable write_protection_region() for aarch32.
>
> v2 - 1. Enable access to protection regions from 0 - 255.
>
> xen/arch/arm/include/asm/mpu.h | 2 -
> xen/arch/arm/mpu/arm32/Makefile | 1 +
> xen/arch/arm/mpu/arm32/mm.c | 165 ++++++++++++++++++++++++++++++++
> xen/arch/arm/mpu/mm.c | 2 -
> 4 files changed, 166 insertions(+), 4 deletions(-)
> create mode 100644 xen/arch/arm/mpu/arm32/mm.c
>
> diff --git a/xen/arch/arm/include/asm/mpu.h b/xen/arch/arm/include/asm/mpu.h
> index 8f06ddac0f..63560c613b 100644
> --- a/xen/arch/arm/include/asm/mpu.h
> +++ b/xen/arch/arm/include/asm/mpu.h
> @@ -25,7 +25,6 @@
>
> #ifndef __ASSEMBLY__
>
> -#ifdef CONFIG_ARM_64
> /*
> * Set base address of MPU protection region.
> *
> @@ -85,7 +84,6 @@ static inline bool region_is_valid(const pr_t *pr)
> {
> return pr->prlar.reg.en;
> }
> -#endif /* CONFIG_ARM_64 */
>
> #endif /* __ASSEMBLY__ */
>
> diff --git a/xen/arch/arm/mpu/arm32/Makefile b/xen/arch/arm/mpu/arm32/Makefile
> index e15ce2f7be..3da872322e 100644
> --- a/xen/arch/arm/mpu/arm32/Makefile
> +++ b/xen/arch/arm/mpu/arm32/Makefile
> @@ -1 +1,2 @@
> obj-y += domain-page.o
> +obj-y += mm.o
> diff --git a/xen/arch/arm/mpu/arm32/mm.c b/xen/arch/arm/mpu/arm32/mm.c
> new file mode 100644
> index 0000000000..5d3cb6dff7
> --- /dev/null
> +++ b/xen/arch/arm/mpu/arm32/mm.c
> @@ -0,0 +1,165 @@
> +/* SPDX-License-Identifier: GPL-2.0-only */
> +
> +#include <xen/bug.h>
> +#include <xen/types.h>
> +#include <asm/mpu.h>
> +#include <asm/sysregs.h>
> +#include <asm/system.h>
> +
> +#define PRBAR_EL2_(n) HPRBAR##n
> +#define PRLAR_EL2_(n) HPRLAR##n
> +
> +#define GENERATE_WRITE_PR_REG_CASE(num, pr) \
> + case num: \
> + { \
> + WRITE_SYSREG(pr->prbar.bits & ~MPU_REGION_RES0, PRBAR_EL2_(num)); \
> + WRITE_SYSREG(pr->prlar.bits & ~MPU_REGION_RES0, PRLAR_EL2_(num)); \
> + break; \
> + }
> +
> +#define GENERATE_WRITE_PR_REG_OTHERS(num, pr) \
> + case num: \
> + { \
> + WRITE_SYSREG(pr->prbar.bits & ~MPU_REGION_RES0, HPRBAR); \
> + WRITE_SYSREG(pr->prlar.bits & ~MPU_REGION_RES0, HPRLAR); \
> + break; \
> + }
> +
> +#define GENERATE_READ_PR_REG_CASE(num, pr) \
> + case num: \
> + { \
> + pr->prbar.bits = READ_SYSREG(PRBAR_EL2_(num)); \
> + pr->prlar.bits = READ_SYSREG(PRLAR_EL2_(num)); \
> + break; \
> + }
> +
> +#define GENERATE_READ_PR_REG_OTHERS(num, pr) \
> + case num: \
> + { \
> + pr->prbar.bits = READ_SYSREG(HPRBAR); \
> + pr->prlar.bits = READ_SYSREG(HPRLAR); \
> + break; \
> + }
> +
> +/*
> + * Armv8-R supports direct access and indirect access to the MPU regions through
> + * registers:
> + * - indirect access involves changing the MPU region selector, issuing an isb
> + * barrier and accessing the selected region through specific registers
> + * - direct access involves accessing specific registers that point to
> + * specific MPU regions, without changing the selector, avoiding the use of
> + * a barrier.
> + * For Arm32 the PR{B,L}AR<n>_ELx (for n=0..31) are used for direct access to the
> + * first 32 MPU regions.
> + * For MPU region numbered 32..255, one need to set the region number in PRSELR_ELx,
> + * followed by configuring PR{B,L}AR_ELx.
> + */
> +inline void prepare_selector(uint8_t *sel)
> +{
> + uint8_t cur_sel = *sel;
> +
> + if ( cur_sel > 0x1FU )
> + {
> + WRITE_SYSREG(cur_sel, PRSELR_EL2);
> + isb();
> + }
> +}
> +
> +void read_protection_region(pr_t *pr_read, uint8_t sel)
> +{
> + prepare_selector(&sel);
> +
> + switch ( sel )
> + {
> + GENERATE_READ_PR_REG_CASE(0, pr_read);
> + GENERATE_READ_PR_REG_CASE(1, pr_read);
> + GENERATE_READ_PR_REG_CASE(2, pr_read);
> + GENERATE_READ_PR_REG_CASE(3, pr_read);
> + GENERATE_READ_PR_REG_CASE(4, pr_read);
> + GENERATE_READ_PR_REG_CASE(5, pr_read);
> + GENERATE_READ_PR_REG_CASE(6, pr_read);
> + GENERATE_READ_PR_REG_CASE(7, pr_read);
> + GENERATE_READ_PR_REG_CASE(8, pr_read);
> + GENERATE_READ_PR_REG_CASE(9, pr_read);
> + GENERATE_READ_PR_REG_CASE(10, pr_read);
> + GENERATE_READ_PR_REG_CASE(11, pr_read);
> + GENERATE_READ_PR_REG_CASE(12, pr_read);
> + GENERATE_READ_PR_REG_CASE(13, pr_read);
> + GENERATE_READ_PR_REG_CASE(14, pr_read);
> + GENERATE_READ_PR_REG_CASE(15, pr_read);
> + GENERATE_READ_PR_REG_CASE(16, pr_read);
> + GENERATE_READ_PR_REG_CASE(17, pr_read);
> + GENERATE_READ_PR_REG_CASE(18, pr_read);
> + GENERATE_READ_PR_REG_CASE(19, pr_read);
> + GENERATE_READ_PR_REG_CASE(20, pr_read);
> + GENERATE_READ_PR_REG_CASE(21, pr_read);
> + GENERATE_READ_PR_REG_CASE(22, pr_read);
> + GENERATE_READ_PR_REG_CASE(23, pr_read);
> + GENERATE_READ_PR_REG_CASE(24, pr_read);
> + GENERATE_READ_PR_REG_CASE(25, pr_read);
> + GENERATE_READ_PR_REG_CASE(26, pr_read);
> + GENERATE_READ_PR_REG_CASE(27, pr_read);
> + GENERATE_READ_PR_REG_CASE(28, pr_read);
> + GENERATE_READ_PR_REG_CASE(29, pr_read);
> + GENERATE_READ_PR_REG_CASE(30, pr_read);
> + GENERATE_READ_PR_REG_CASE(31, pr_read);
> + GENERATE_READ_PR_REG_OTHERS(32 ... 255, pr_read);
This should be 32 ... 254 . Thanks Luca for pointing this out.
The max number of regions supported is 255 (not 256). It is the maximum
value of HMPUIR.
- Ayan
> + default:
> + BUG(); /* Can't happen */
> + break;
> + }
> +}
> +
> +void write_protection_region(const pr_t *pr_write, uint8_t sel)
> +{
> + prepare_selector(&sel);
> +
> + switch ( sel )
> + {
> + GENERATE_WRITE_PR_REG_CASE(0, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(1, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(2, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(3, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(4, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(5, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(6, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(7, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(8, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(9, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(10, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(11, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(12, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(13, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(14, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(15, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(16, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(17, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(18, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(19, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(20, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(21, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(22, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(23, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(24, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(25, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(26, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(27, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(28, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(29, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(30, pr_write);
> + GENERATE_WRITE_PR_REG_CASE(31, pr_write);
> + GENERATE_WRITE_PR_REG_OTHERS(32 ... 255, pr_write);
> + default:
> + BUG(); /* Can't happen */
> + break;
> + }
> +}
> +
> +/*
> + * Local variables:
> + * mode: C
> + * c-file-style: "BSD"
> + * c-basic-offset: 4
> + * indent-tabs-mode: nil
> + * End:
> + */
> diff --git a/xen/arch/arm/mpu/mm.c b/xen/arch/arm/mpu/mm.c
> index 7ab68fc8c7..ccfb37a67b 100644
> --- a/xen/arch/arm/mpu/mm.c
> +++ b/xen/arch/arm/mpu/mm.c
> @@ -39,7 +39,6 @@ static void __init __maybe_unused build_assertions(void)
> BUILD_BUG_ON(PAGE_SIZE != SZ_4K);
> }
>
> -#ifdef CONFIG_ARM_64
> pr_t pr_of_addr(paddr_t base, paddr_t limit, unsigned int flags)
> {
> unsigned int attr_idx = PAGE_AI_MASK(flags);
> @@ -110,7 +109,6 @@ pr_t pr_of_addr(paddr_t base, paddr_t limit, unsigned int flags)
>
> return region;
> }
> -#endif /* CONFIG_ARM_64 */
>
> void __init setup_mm(void)
> {
next prev parent reply other threads:[~2025-06-13 9:31 UTC|newest]
Thread overview: 23+ messages / expand[flat|nested] mbox.gz Atom feed top
2025-06-11 14:35 [PATCH v3 0/6] Enable R52 support for the first chunk of MPU support Ayan Kumar Halder
2025-06-11 14:35 ` [PATCH v3 1/6] arm/mpu: Introduce MPU memory region map structure Ayan Kumar Halder
2025-06-13 15:30 ` Luca Fancellu
2025-06-16 8:16 ` Julien Grall
2025-06-11 14:35 ` [PATCH v3 2/6] arm/mpu: Provide and populate MPU C data structures Ayan Kumar Halder
2025-06-13 15:39 ` Luca Fancellu
2025-06-16 8:25 ` Julien Grall
2025-06-11 14:35 ` [PATCH v3 3/6] arm/mpu: Move domain-page.c to arm32 specific dir Ayan Kumar Halder
2025-06-11 19:46 ` Luca Fancellu
2025-06-12 7:48 ` Ayan Kumar Halder
2025-06-11 14:35 ` [PATCH v3 4/6] arm/mpu: Move the functions to arm64 specific files Ayan Kumar Halder
2025-06-13 15:08 ` Luca Fancellu
2025-06-16 17:04 ` Ayan Kumar Halder
2025-06-11 14:35 ` [PATCH v3 5/6] arm/mpu: Define arm32 system registers Ayan Kumar Halder
2025-06-16 10:38 ` Hari Limaye
2025-06-16 17:06 ` Ayan Kumar Halder
2025-06-11 14:35 ` [PATCH v3 6/6] arm/mpu: Enable read/write to protection regions for arm32 Ayan Kumar Halder
2025-06-12 9:35 ` Luca Fancellu
2025-06-12 10:37 ` Ayan Kumar Halder
2025-06-13 7:00 ` Orzel, Michal
2025-06-13 9:30 ` Ayan Kumar Halder [this message]
2025-06-13 16:02 ` Luca Fancellu
2025-06-16 5:57 ` Luca Fancellu
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=41eef9a1-1f43-4f2f-b79a-89c0d0ec941b@amd.com \
--to=ayankuma@amd.com \
--cc=Volodymyr_Babchuk@epam.com \
--cc=ayan.kumar.halder@amd.com \
--cc=bertrand.marquis@arm.com \
--cc=julien@xen.org \
--cc=michal.orzel@amd.com \
--cc=sstabellini@kernel.org \
--cc=xen-devel@lists.xenproject.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
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.