From nobody Thu Oct 30 18:55:07 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) client-ip=192.237.175.120; envelope-from=xen-devel-bounces@lists.xenproject.org; helo=lists.xenproject.org; Authentication-Results: mx.zohomail.com; spf=pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) smtp.mailfrom=xen-devel-bounces@lists.xenproject.org; dmarc=fail(p=none dis=none) header.from=arm.com Return-Path: Received: from lists.xenproject.org (lists.xenproject.org [192.237.175.120]) by mx.zohomail.com with SMTPS id 175386517875940.27832979365803; Wed, 30 Jul 2025 01:46:18 -0700 (PDT) Received: from list by lists.xenproject.org with outflank-mailman.1063530.1429233 (Exim 4.92) (envelope-from ) id 1uh2Rd-0007DE-05; Wed, 30 Jul 2025 08:45:53 +0000 Received: by outflank-mailman (output) from mailman id 1063530.1429233; Wed, 30 Jul 2025 08:45:52 +0000 Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rc-0007D7-Sn; Wed, 30 Jul 2025 08:45:52 +0000 Received: by outflank-mailman (input) for mailman id 1063530; Wed, 30 Jul 2025 08:45:51 +0000 Received: from se1-gles-sth1-in.inumbo.com ([159.253.27.254] helo=se1-gles-sth1.inumbo.com) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rb-0006zM-JZ for xen-devel@lists.xenproject.org; Wed, 30 Jul 2025 08:45:51 +0000 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by se1-gles-sth1.inumbo.com (Halon) with ESMTP id 987d4913-6d21-11f0-a320-13f23c93f187; Wed, 30 Jul 2025 10:45:51 +0200 (CEST) Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 6C0721BC0; Wed, 30 Jul 2025 01:45:42 -0700 (PDT) Received: from PWQ0QT7DJ1.arm.com (unknown [10.57.73.135]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 098FF3F66E; Wed, 30 Jul 2025 01:45:48 -0700 (PDT) X-Outflank-Mailman: Message body and most headers restored to incoming version X-BeenThere: xen-devel@lists.xenproject.org List-Id: Xen developer discussion List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , Errors-To: xen-devel-bounces@lists.xenproject.org Precedence: list Sender: "Xen-devel" X-Inumbo-ID: 987d4913-6d21-11f0-a320-13f23c93f187 From: Hari Limaye To: xen-devel@lists.xenproject.org Cc: luca.fancellu@arm.com, Stefano Stabellini , Julien Grall , Bertrand Marquis , Michal Orzel , Volodymyr Babchuk Subject: [PATCH 1/5] arm/mpu: Implement setup_frametable_mappings for MPU systems Date: Wed, 30 Jul 2025 09:45:30 +0100 Message-ID: X-Mailer: git-send-email 2.42.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-ZM-MESSAGEID: 1753865181109116600 Content-Type: text/plain; charset="utf-8" From: Luca Fancellu Implement the MPU variant of `setup_frametable_mappings`. This function will be called by `setup_mm` when an implementation for MPU systems is added in a follow up commit. Signed-off-by: Luca Fancellu Signed-off-by: Hari Limaye Reviewed-by: Ayan Kumarb Halder Reviewed-by: Michal Orzel Tested-by: Ayan Kumarb Halder --- xen/arch/arm/mpu/mm.c | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/xen/arch/arm/mpu/mm.c b/xen/arch/arm/mpu/mm.c index c6891607ec..6a16fa348d 100644 --- a/xen/arch/arm/mpu/mm.c +++ b/xen/arch/arm/mpu/mm.c @@ -168,6 +168,25 @@ int mpumap_contains_region(pr_t *table, uint8_t nr_reg= ions, paddr_t base, return MPUMAP_REGION_NOTFOUND; } =20 +/* Map a frame table to cover physical addresses ps through pe */ +void __init setup_frametable_mappings(paddr_t ps, paddr_t pe) +{ + mfn_t base_mfn; + unsigned long nr_pdxs =3D mfn_to_pdx(mfn_add(maddr_to_mfn(pe), -1)) - + mfn_to_pdx(maddr_to_mfn(ps)) + 1; + unsigned long frametable_size =3D nr_pdxs * sizeof(struct page_info); + + frametable_base_pdx =3D paddr_to_pdx(ps); + frametable_size =3D ROUNDUP(frametable_size, PAGE_SIZE); + + base_mfn =3D alloc_boot_pages(frametable_size >> PAGE_SHIFT, 1); + frame_table =3D (struct page_info *)mfn_to_virt(mfn_x(base_mfn)); + + memset(&frame_table[0], 0, nr_pdxs * sizeof(struct page_info)); + memset(&frame_table[nr_pdxs], -1, + frametable_size - (nr_pdxs * sizeof(struct page_info))); +} + /* * Allocate an entry for a new EL2 MPU region in the bitmap xen_mpumap_mas= k. * @param idx Set to the index of the allocated EL2 MPU region on succes= s. --=20 2.34.1 From nobody Thu Oct 30 18:55:07 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) client-ip=192.237.175.120; envelope-from=xen-devel-bounces@lists.xenproject.org; helo=lists.xenproject.org; Authentication-Results: mx.zohomail.com; spf=pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) smtp.mailfrom=xen-devel-bounces@lists.xenproject.org; dmarc=fail(p=none dis=none) header.from=arm.com Return-Path: Received: from lists.xenproject.org (lists.xenproject.org [192.237.175.120]) by mx.zohomail.com with SMTPS id 1753865173532841.5714522442477; Wed, 30 Jul 2025 01:46:13 -0700 (PDT) Received: from list by lists.xenproject.org with outflank-mailman.1063531.1429243 (Exim 4.92) (envelope-from ) id 1uh2Rg-0007So-5p; Wed, 30 Jul 2025 08:45:56 +0000 Received: by outflank-mailman (output) from mailman id 1063531.1429243; Wed, 30 Jul 2025 08:45:56 +0000 Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rg-0007Sf-2Z; Wed, 30 Jul 2025 08:45:56 +0000 Received: by outflank-mailman (input) for mailman id 1063531; Wed, 30 Jul 2025 08:45:55 +0000 Received: from se1-gles-sth1-in.inumbo.com ([159.253.27.254] helo=se1-gles-sth1.inumbo.com) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rf-0006zM-7H for xen-devel@lists.xenproject.org; Wed, 30 Jul 2025 08:45:55 +0000 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by se1-gles-sth1.inumbo.com (Halon) with ESMTP id 9a72fa0e-6d21-11f0-a320-13f23c93f187; Wed, 30 Jul 2025 10:45:54 +0200 (CEST) Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id A2C8A1515; Wed, 30 Jul 2025 01:45:45 -0700 (PDT) Received: from PWQ0QT7DJ1.arm.com (unknown [10.57.73.135]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 439EB3F66E; Wed, 30 Jul 2025 01:45:52 -0700 (PDT) X-Outflank-Mailman: Message body and most headers restored to incoming version X-BeenThere: xen-devel@lists.xenproject.org List-Id: Xen developer discussion List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , Errors-To: xen-devel-bounces@lists.xenproject.org Precedence: list Sender: "Xen-devel" X-Inumbo-ID: 9a72fa0e-6d21-11f0-a320-13f23c93f187 From: Hari Limaye To: xen-devel@lists.xenproject.org Cc: luca.fancellu@arm.com, Stefano Stabellini , Julien Grall , Bertrand Marquis , Michal Orzel , Volodymyr Babchuk Subject: [PATCH 2/5] arm/mpu: Implement setup_mm for MPU systems Date: Wed, 30 Jul 2025 09:45:31 +0100 Message-ID: X-Mailer: git-send-email 2.42.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-ZM-MESSAGEID: 1753865175224116600 Content-Type: text/plain; charset="utf-8" From: Luca Fancellu Implement `setup_mm` for MPU systems. This variant doesn't need to set up the direct map. Signed-off-by: Luca Fancellu Signed-off-by: Hari Limaye Reviewed-by: Ayan Kumarb Halder Tested-by: Ayan Kumarb Halder --- xen/arch/arm/mpu/mm.c | 64 ++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 63 insertions(+), 1 deletion(-) diff --git a/xen/arch/arm/mpu/mm.c b/xen/arch/arm/mpu/mm.c index 6a16fa348d..0b05103180 100644 --- a/xen/arch/arm/mpu/mm.c +++ b/xen/arch/arm/mpu/mm.c @@ -8,9 +8,12 @@ #include #include #include +#include +#include #include #include #include +#include #include =20 struct page_info *frame_table; @@ -364,9 +367,68 @@ int map_pages_to_xen(unsigned long virt, mfn_t mfn, un= signed long nr_mfns, return xen_mpumap_update(virt, mfn_to_maddr(mfn_add(mfn, nr_mfns)), fl= ags); } =20 +/* + * Heap must be statically configured in Device Tree through "xen,static-h= eap" + * on MPU systems. + */ +static void __init setup_staticheap_mappings(void) +{ + const struct membanks *reserved_mem =3D bootinfo_get_reserved_mem(); + unsigned int bank =3D 0; + + for ( ; bank < reserved_mem->nr_banks; bank++ ) + { + if ( reserved_mem->bank[bank].type =3D=3D MEMBANK_STATIC_HEAP ) + { + paddr_t bank_start =3D round_pgup(reserved_mem->bank[bank].sta= rt); + paddr_t bank_size =3D round_pgdown(reserved_mem->bank[bank].si= ze); + paddr_t bank_end =3D bank_start + bank_size; + + /* Map static heap with one MPU protection region */ + if ( xen_mpumap_update(bank_start, bank_end, PAGE_HYPERVISOR) ) + panic("Failed to map static heap\n"); + + break; + } + } + + if ( bank =3D=3D reserved_mem->nr_banks ) + panic("No static heap memory bank found\n"); +} + void __init setup_mm(void) { - BUG_ON("unimplemented"); + const struct membanks *mem =3D bootinfo_get_mem(); + paddr_t ram_start =3D INVALID_PADDR, ram_end =3D 0, ram_size =3D 0; + + if ( !mem->nr_banks ) + panic("No memory bank\n"); + + init_pdx(); + + populate_boot_allocator(); + + total_pages =3D 0; + for ( unsigned int bank =3D 0 ; bank < mem->nr_banks; bank++ ) + { + paddr_t bank_start =3D round_pgup(mem->bank[bank].start); + paddr_t bank_size =3D round_pgdown(mem->bank[bank].size); + paddr_t bank_end =3D bank_start + bank_size; + + ram_size =3D ram_size + bank_size; + ram_start =3D min(ram_start, bank_start); + ram_end =3D max(ram_end, bank_end); + } + + setup_staticheap_mappings(); + + total_pages +=3D ram_size >> PAGE_SHIFT; + max_page =3D PFN_DOWN(ram_end); + + setup_frametable_mappings(ram_start, ram_end); + + init_staticmem_pages(); + init_sharedmem_pages(); } =20 int modify_xen_mappings(unsigned long s, unsigned long e, unsigned int nf) --=20 2.34.1 From nobody Thu Oct 30 18:55:07 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) client-ip=192.237.175.120; envelope-from=xen-devel-bounces@lists.xenproject.org; helo=lists.xenproject.org; Authentication-Results: mx.zohomail.com; spf=pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) smtp.mailfrom=xen-devel-bounces@lists.xenproject.org; dmarc=fail(p=none dis=none) header.from=arm.com Return-Path: Received: from lists.xenproject.org (lists.xenproject.org [192.237.175.120]) by mx.zohomail.com with SMTPS id 1753865177630235.29726288771246; Wed, 30 Jul 2025 01:46:17 -0700 (PDT) Received: from list by lists.xenproject.org with outflank-mailman.1063534.1429262 (Exim 4.92) (envelope-from ) id 1uh2Rk-000807-Pa; Wed, 30 Jul 2025 08:46:00 +0000 Received: by outflank-mailman (output) from mailman id 1063534.1429262; Wed, 30 Jul 2025 08:46:00 +0000 Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rk-0007zu-MP; Wed, 30 Jul 2025 08:46:00 +0000 Received: by outflank-mailman (input) for mailman id 1063534; Wed, 30 Jul 2025 08:46:00 +0000 Received: from se1-gles-flk1-in.inumbo.com ([94.247.172.50] helo=se1-gles-flk1.inumbo.com) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rk-0007SQ-0M for xen-devel@lists.xenproject.org; Wed, 30 Jul 2025 08:46:00 +0000 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by se1-gles-flk1.inumbo.com (Halon) with ESMTP id 9c55ff6a-6d21-11f0-b895-0df219b8e170; Wed, 30 Jul 2025 10:45:57 +0200 (CEST) Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 899F11515; Wed, 30 Jul 2025 01:45:49 -0700 (PDT) Received: from PWQ0QT7DJ1.arm.com (unknown [10.57.73.135]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 2A5A23F66E; Wed, 30 Jul 2025 01:45:56 -0700 (PDT) X-Outflank-Mailman: Message body and most headers restored to incoming version X-BeenThere: xen-devel@lists.xenproject.org List-Id: Xen developer discussion List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , Errors-To: xen-devel-bounces@lists.xenproject.org Precedence: list Sender: "Xen-devel" X-Inumbo-ID: 9c55ff6a-6d21-11f0-b895-0df219b8e170 From: Hari Limaye To: xen-devel@lists.xenproject.org Cc: luca.fancellu@arm.com, Stefano Stabellini , Julien Grall , Bertrand Marquis , Michal Orzel , Volodymyr Babchuk Subject: [PATCH 3/5] arm/mpu: Implement transient mapping Date: Wed, 30 Jul 2025 09:45:32 +0100 Message-ID: X-Mailer: git-send-email 2.42.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-ZM-MESSAGEID: 1753865179347116600 Content-Type: text/plain; charset="utf-8" From: Luca Fancellu Add a scheme to distinguish transient MPU regions, to identify MPU regions which will be mapped for a short period of time. Signed-off-by: Luca Fancellu Signed-off-by: Hari Limaye Reviewed-by: Ayan Kumar Halder Tested-by: Ayan Kumar Halder --- xen/arch/arm/include/asm/arm32/mpu.h | 2 ++ xen/arch/arm/include/asm/arm64/mpu.h | 2 ++ xen/arch/arm/include/asm/mpu/mm.h | 14 +++++++++++++- xen/arch/arm/include/asm/mpu/regions.inc | 19 +++++++++++++++++-- xen/arch/arm/mpu/mm.c | 23 ++++++++++++++--------- 5 files changed, 48 insertions(+), 12 deletions(-) diff --git a/xen/arch/arm/include/asm/arm32/mpu.h b/xen/arch/arm/include/as= m/arm32/mpu.h index 0a6930b3a0..9906d98809 100644 --- a/xen/arch/arm/include/asm/arm32/mpu.h +++ b/xen/arch/arm/include/asm/arm32/mpu.h @@ -39,6 +39,8 @@ typedef union { typedef struct { prbar_t prbar; prlar_t prlar; + bool transient; + uint8_t pad[7]; /* Pad structure to 16 Bytes */ } pr_t; =20 #endif /* __ASSEMBLY__ */ diff --git a/xen/arch/arm/include/asm/arm64/mpu.h b/xen/arch/arm/include/as= m/arm64/mpu.h index f0ce344e78..1d1843eda0 100644 --- a/xen/arch/arm/include/asm/arm64/mpu.h +++ b/xen/arch/arm/include/asm/arm64/mpu.h @@ -38,6 +38,8 @@ typedef union { typedef struct { prbar_t prbar; prlar_t prlar; + bool transient; + uint8_t pad[15]; /* Pad structure to 32 Bytes */ } pr_t; =20 #endif /* __ASSEMBLY__ */ diff --git a/xen/arch/arm/include/asm/mpu/mm.h b/xen/arch/arm/include/asm/m= pu/mm.h index c32fac8905..56ca411af4 100644 --- a/xen/arch/arm/include/asm/mpu/mm.h +++ b/xen/arch/arm/include/asm/mpu/mm.h @@ -60,6 +60,16 @@ static inline void context_sync_mpu(void) isb(); } =20 +static inline bool region_is_transient(pr_t *pr) +{ + return pr->transient; +} + +static inline void region_set_transient(pr_t *pr, bool transient) +{ + pr->transient =3D transient; +} + /* * The following API requires context_sync_mpu() after being used to modif= y MPU * regions: @@ -80,9 +90,11 @@ void write_protection_region(const pr_t *pr_write, uint8= _t sel); * @param base Base address of the range to map (inclusive). * @param limit Limit address of the range to map (exclusive). * @param flags Flags for the memory range to map. + * @param transient True for a temporary mapping, otherwise False. * @return 0 on success, negative on error. */ -int xen_mpumap_update(paddr_t base, paddr_t limit, unsigned int flags); +int xen_mpumap_update(paddr_t base, paddr_t limit, unsigned int flags, + bool transient); =20 /* * Creates a pr_t structure describing a protection region. diff --git a/xen/arch/arm/include/asm/mpu/regions.inc b/xen/arch/arm/includ= e/asm/mpu/regions.inc index 23fead3b21..f9892fe3d8 100644 --- a/xen/arch/arm/include/asm/mpu/regions.inc +++ b/xen/arch/arm/include/asm/mpu/regions.inc @@ -14,19 +14,31 @@ #define PRLAR_ELx_EN 0x1 =20 #ifdef CONFIG_ARM_64 -#define XEN_MPUMAP_ENTRY_SHIFT 0x4 /* 16 byte structure */ +#define XEN_MPUMAP_ENTRY_SHIFT 0x5 /* 32 byte structure */ +#define XEN_MPUMAP_ENTRY_ZERO_OFFSET 0x10 /* {PRBAR, PRLAR} is 16 bytes = */ =20 .macro store_pair reg1, reg2, dst stp \reg1, \reg2, [\dst] .endm =20 +.macro zero_pair dst, offset, tmp1, tmp2 + stp xzr, xzr, [\dst, \offset] +.endm + #else -#define XEN_MPUMAP_ENTRY_SHIFT 0x3 /* 8 byte structure */ +#define XEN_MPUMAP_ENTRY_SHIFT 0x4 /* 16 byte structure */ +#define XEN_MPUMAP_ENTRY_ZERO_OFFSET 0x8 /* {PRBAR, PRLAR} is 8 bytes = */ =20 .macro store_pair reg1, reg2, dst strd \reg1, \reg2, [\dst] .endm =20 +.macro zero_pair dst, offset, tmp1, tmp2 + mov \tmp1, #0 + mov \tmp2, #0 + strd \tmp1, \tmp2, [\dst, \offset] +.endm + #endif =20 /* @@ -97,6 +109,9 @@ =20 3: =20 + /* Clear the rest of the xen_mpumap entry. Clobbers prbar and prlar. */ + zero_pair \base, #XEN_MPUMAP_ENTRY_ZERO_OFFSET, \prbar, \prlar + add \sel, \sel, #1 =20 1: diff --git a/xen/arch/arm/mpu/mm.c b/xen/arch/arm/mpu/mm.c index 0b05103180..38474bcfa2 100644 --- a/xen/arch/arm/mpu/mm.c +++ b/xen/arch/arm/mpu/mm.c @@ -251,13 +251,14 @@ static void disable_mpu_region_from_index(uint8_t ind= ex) * Update the entry in the MPU memory region mapping table (xen_mpumap) fo= r the * given memory range and flags, creating one if none exists. * - * @param base Base address (inclusive). - * @param limit Limit address (exclusive). - * @param flags Region attributes (a combination of PAGE_HYPERVISOR_XXX) + * @param base Base address (inclusive). + * @param limit Limit address (exclusive). + * @param flags Region attributes (a combination of PAGE_HYPERVISOR_XX= X) + * @param transient True for a temporary mapping, otherwise False. * @return 0 on success, otherwise negative on error. */ static int xen_mpumap_update_entry(paddr_t base, paddr_t limit, - unsigned int flags) + unsigned int flags, bool transient) { bool flags_has_page_present; uint8_t idx; @@ -297,6 +298,7 @@ static int xen_mpumap_update_entry(paddr_t base, paddr_= t limit, return -ENOENT; =20 xen_mpumap[idx] =3D pr_of_addr(base, limit, flags); + region_set_transient(&xen_mpumap[idx], transient); =20 write_protection_region(&xen_mpumap[idx], idx); } @@ -316,7 +318,8 @@ static int xen_mpumap_update_entry(paddr_t base, paddr_= t limit, return 0; } =20 -int xen_mpumap_update(paddr_t base, paddr_t limit, unsigned int flags) +int xen_mpumap_update(paddr_t base, paddr_t limit, unsigned int flags, + bool transient) { int rc; =20 @@ -342,7 +345,7 @@ int xen_mpumap_update(paddr_t base, paddr_t limit, unsi= gned int flags) =20 spin_lock(&xen_mpumap_lock); =20 - rc =3D xen_mpumap_update_entry(base, limit, flags); + rc =3D xen_mpumap_update_entry(base, limit, flags, transient); if ( !rc ) context_sync_mpu(); =20 @@ -357,14 +360,15 @@ int destroy_xen_mappings(unsigned long s, unsigned lo= ng e) ASSERT(IS_ALIGNED(e, PAGE_SIZE)); ASSERT(s < e); =20 - return xen_mpumap_update(s, e, 0); + return xen_mpumap_update(s, e, 0, false); } =20 int map_pages_to_xen(unsigned long virt, mfn_t mfn, unsigned long nr_mfns, unsigned int flags) { /* MPU systems have no translation, ma =3D=3D va, so pass virt directl= y */ - return xen_mpumap_update(virt, mfn_to_maddr(mfn_add(mfn, nr_mfns)), fl= ags); + return xen_mpumap_update(virt, mfn_to_maddr(mfn_add(mfn, nr_mfns)), fl= ags, + false); } =20 /* @@ -385,7 +389,8 @@ static void __init setup_staticheap_mappings(void) paddr_t bank_end =3D bank_start + bank_size; =20 /* Map static heap with one MPU protection region */ - if ( xen_mpumap_update(bank_start, bank_end, PAGE_HYPERVISOR) ) + if ( xen_mpumap_update(bank_start, bank_end, PAGE_HYPERVISOR, + false) ) panic("Failed to map static heap\n"); =20 break; --=20 2.34.1 From nobody Thu Oct 30 18:55:07 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) client-ip=192.237.175.120; envelope-from=xen-devel-bounces@lists.xenproject.org; helo=lists.xenproject.org; Authentication-Results: mx.zohomail.com; spf=pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) smtp.mailfrom=xen-devel-bounces@lists.xenproject.org; dmarc=fail(p=none dis=none) header.from=arm.com Return-Path: Received: from lists.xenproject.org (lists.xenproject.org [192.237.175.120]) by mx.zohomail.com with SMTPS id 1753865183037770.9673176457756; Wed, 30 Jul 2025 01:46:23 -0700 (PDT) Received: from list by lists.xenproject.org with outflank-mailman.1063536.1429273 (Exim 4.92) (envelope-from ) id 1uh2Ro-0008Je-27; Wed, 30 Jul 2025 08:46:04 +0000 Received: by outflank-mailman (output) from mailman id 1063536.1429273; Wed, 30 Jul 2025 08:46:04 +0000 Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rn-0008JR-UR; Wed, 30 Jul 2025 08:46:03 +0000 Received: by outflank-mailman (input) for mailman id 1063536; Wed, 30 Jul 2025 08:46:02 +0000 Received: from se1-gles-sth1-in.inumbo.com ([159.253.27.254] helo=se1-gles-sth1.inumbo.com) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rm-0006zM-NQ for xen-devel@lists.xenproject.org; Wed, 30 Jul 2025 08:46:02 +0000 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by se1-gles-sth1.inumbo.com (Halon) with ESMTP id 9eed65ea-6d21-11f0-a320-13f23c93f187; Wed, 30 Jul 2025 10:46:01 +0200 (CEST) Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 44A841515; Wed, 30 Jul 2025 01:45:53 -0700 (PDT) Received: from PWQ0QT7DJ1.arm.com (unknown [10.57.73.135]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id D83133F66E; Wed, 30 Jul 2025 01:45:59 -0700 (PDT) X-Outflank-Mailman: Message body and most headers restored to incoming version X-BeenThere: xen-devel@lists.xenproject.org List-Id: Xen developer discussion List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , Errors-To: xen-devel-bounces@lists.xenproject.org Precedence: list Sender: "Xen-devel" X-Inumbo-ID: 9eed65ea-6d21-11f0-a320-13f23c93f187 From: Hari Limaye To: xen-devel@lists.xenproject.org Cc: luca.fancellu@arm.com, Stefano Stabellini , Julien Grall , Bertrand Marquis , Michal Orzel , Volodymyr Babchuk Subject: [PATCH 4/5] arm/mpu: Implement ioremap_attr for MPU Date: Wed, 30 Jul 2025 09:45:33 +0100 Message-ID: X-Mailer: git-send-email 2.42.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-ZM-MESSAGEID: 1753865185400116600 Content-Type: text/plain; charset="utf-8" From: Luca Fancellu Introduce helpers (un)map_mm_range() in order to allow the temporary mapping of a range of memory, and use these to implement the function `ioremap_attr` for MPU systems. Signed-off-by: Luca Fancellu Signed-off-by: Hari Limaye Reviewed-by: Ayan Kumar Halder Tested-by: Ayan Kumar Halder --- xen/arch/arm/include/asm/mpu/mm.h | 22 +++++ xen/arch/arm/mpu/mm.c | 150 ++++++++++++++++++++++++++++-- 2 files changed, 163 insertions(+), 9 deletions(-) diff --git a/xen/arch/arm/include/asm/mpu/mm.h b/xen/arch/arm/include/asm/m= pu/mm.h index 56ca411af4..177550f5bd 100644 --- a/xen/arch/arm/include/asm/mpu/mm.h +++ b/xen/arch/arm/include/asm/mpu/mm.h @@ -106,6 +106,28 @@ int xen_mpumap_update(paddr_t base, paddr_t limit, uns= igned int flags, */ pr_t pr_of_addr(paddr_t base, paddr_t limit, unsigned int flags); =20 +/* + * Maps a temporary range of memory with attributes `flags`; if the range = is + * already mapped with the same attributes, including an inclusive match, = the + * existing mapping is returned. This API is intended for mappings that ex= ist + * transiently for a short period between calls to this function and + * `unmap_mm_range`. + * + * @param start Base address of the range to map (inclusive). + * @param end Limit address of the range to map (exclusive). + * @param flags Flags for the memory range to map. + * @return Pointer to start of region on success, NULL on error. + */ +void *map_mm_range(paddr_t start, paddr_t end, unsigned int flags); + +/* + * Unmaps a temporary range of memory if it was previously mapped by + * map_mm_range, otherwise it does not remove the mapping. + * + * @param start Base address of the range to map (inclusive). + */ +void unmap_mm_range(paddr_t start); + /* * Checks whether a given memory range is present in the provided table of * MPU protection regions. diff --git a/xen/arch/arm/mpu/mm.c b/xen/arch/arm/mpu/mm.c index 38474bcfa2..cf6f95ef85 100644 --- a/xen/arch/arm/mpu/mm.c +++ b/xen/arch/arm/mpu/mm.c @@ -318,31 +318,39 @@ static int xen_mpumap_update_entry(paddr_t base, padd= r_t limit, return 0; } =20 -int xen_mpumap_update(paddr_t base, paddr_t limit, unsigned int flags, - bool transient) +static bool check_mpu_mapping(paddr_t base, paddr_t limit, unsigned int fl= ags) { - int rc; - if ( flags_has_rwx(flags) ) { printk("Mappings should not be both Writeable and Executable\n"); - return -EINVAL; + return false; } =20 if ( base >=3D limit ) { printk("Base address %#"PRIpaddr" must be smaller than limit addre= ss %#"PRIpaddr"\n", base, limit); - return -EINVAL; + return false; } =20 if ( !IS_ALIGNED(base, PAGE_SIZE) || !IS_ALIGNED(limit, PAGE_SIZE) ) { printk("base address %#"PRIpaddr", or limit address %#"PRIpaddr" i= s not page aligned\n", base, limit); - return -EINVAL; + return false; } =20 + return true; +} + +int xen_mpumap_update(paddr_t base, paddr_t limit, unsigned int flags, + bool transient) +{ + int rc; + + if ( !check_mpu_mapping(base, limit, flags) ) + return -EINVAL; + spin_lock(&xen_mpumap_lock); =20 rc =3D xen_mpumap_update_entry(base, limit, flags, transient); @@ -453,10 +461,134 @@ void free_init_memory(void) BUG_ON("unimplemented"); } =20 +static uint8_t is_mm_range_mapped(paddr_t start, paddr_t end) +{ + int rc; + uint8_t idx; + + ASSERT(spin_is_locked(&xen_mpumap_lock)); + + rc =3D mpumap_contains_region(xen_mpumap, max_mpu_regions, start, end,= &idx); + if ( rc < 0 ) + panic("Cannot handle overlapping MPU memory protection regions\n"= ); + + /* + * 'idx' will be INVALID_REGION_IDX for rc =3D=3D MPUMAP_REGION_NOTFOU= ND and + * it will be a proper region index when rc >=3D MPUMAP_REGION_FOUND. + */ + return idx; +} + +static bool is_mm_attr_match(pr_t *region, unsigned int attributes) +{ + bool ret =3D true; + + if ( region->prbar.reg.ro !=3D PAGE_RO_MASK(attributes) ) + { + printk(XENLOG_WARNING + "Mismatched Access Permission attributes (%#x0 instead of %= #x0)\n", + region->prbar.reg.ro, PAGE_RO_MASK(attributes)); + ret =3D false; + } + + if ( region->prbar.reg.xn !=3D PAGE_XN_MASK(attributes) ) + { + printk(XENLOG_WARNING + "Mismatched Execute Never attributes (%#x instead of %#x)\n= ", + region->prbar.reg.xn, PAGE_XN_MASK(attributes)); + ret =3D false; + } + + if ( region->prlar.reg.ai !=3D PAGE_AI_MASK(attributes) ) + { + printk(XENLOG_WARNING + "Mismatched Memory Attribute Index (%#x instead of %#x)\n", + region->prlar.reg.ai, PAGE_AI_MASK(attributes)); + ret =3D false; + } + + return ret; +} + +void *map_mm_range(paddr_t start, paddr_t end, unsigned int flags) +{ + paddr_t start_pg =3D round_pgdown(start); + paddr_t end_pg =3D round_pgup(end); + void *ret =3D NULL; + uint8_t idx; + + if ( !check_mpu_mapping(start_pg, end_pg, flags) ) + return NULL; + + spin_lock(&xen_mpumap_lock); + + idx =3D is_mm_range_mapped(start_pg, end_pg); + if ( idx !=3D INVALID_REGION_IDX ) + { + /* Already mapped with different attributes */ + if ( !is_mm_attr_match(&xen_mpumap[idx], flags) ) + { + printk(XENLOG_WARNING + "Range %#"PRIpaddr"-%#"PRIpaddr" already mapped with di= fferent flags\n", + start_pg, end_pg); + goto out; + } + + /* Already mapped with same attributes */ + ret =3D maddr_to_virt(start); + goto out; + } + + if ( !xen_mpumap_update_entry(start_pg, end_pg, flags, true) ) + { + context_sync_mpu(); + ret =3D maddr_to_virt(start); + } + + out: + spin_unlock(&xen_mpumap_lock); + + return ret; +} + +void unmap_mm_range(paddr_t start) +{ + uint8_t idx; + + spin_lock(&xen_mpumap_lock); + + /* + * Mappings created via map_mm_range are at least PAGE_SIZE. Find the = idx + * of the MPU memory region containing `start` mapped through map_mm_r= ange. + */ + idx =3D is_mm_range_mapped(start, start + PAGE_SIZE); + if ( idx =3D=3D INVALID_REGION_IDX ) + { + printk(XENLOG_ERR + "Failed to unmap_mm_range MPU memory region at %#"PRIpaddr"= \n", + start); + goto out; + } + + /* This API is only meant to unmap transient regions */ + if ( !region_is_transient(&xen_mpumap[idx]) ) + goto out; + + /* Disable MPU memory region and clear the associated entry in xen_mpu= map */ + disable_mpu_region_from_index(idx); + context_sync_mpu(); + + out: + spin_unlock(&xen_mpumap_lock); +} + void __iomem *ioremap_attr(paddr_t start, size_t len, unsigned int flags) { - BUG_ON("unimplemented"); - return NULL; + if ( !map_mm_range(start, start + len, flags) ) + return NULL; + + /* Mapped or already mapped */ + return maddr_to_virt(start); } =20 /* --=20 2.34.1 From nobody Thu Oct 30 18:55:07 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) client-ip=192.237.175.120; envelope-from=xen-devel-bounces@lists.xenproject.org; helo=lists.xenproject.org; Authentication-Results: mx.zohomail.com; spf=pass (zohomail.com: domain of lists.xenproject.org designates 192.237.175.120 as permitted sender) smtp.mailfrom=xen-devel-bounces@lists.xenproject.org; dmarc=fail(p=none dis=none) header.from=arm.com Return-Path: Received: from lists.xenproject.org (lists.xenproject.org [192.237.175.120]) by mx.zohomail.com with SMTPS id 1753865184844592.0520446981282; Wed, 30 Jul 2025 01:46:24 -0700 (PDT) Received: from list by lists.xenproject.org with outflank-mailman.1063539.1429283 (Exim 4.92) (envelope-from ) id 1uh2Rt-0000Q1-CZ; Wed, 30 Jul 2025 08:46:09 +0000 Received: by outflank-mailman (output) from mailman id 1063539.1429283; Wed, 30 Jul 2025 08:46:09 +0000 Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rt-0000PZ-7p; Wed, 30 Jul 2025 08:46:09 +0000 Received: by outflank-mailman (input) for mailman id 1063539; Wed, 30 Jul 2025 08:46:07 +0000 Received: from se1-gles-sth1-in.inumbo.com ([159.253.27.254] helo=se1-gles-sth1.inumbo.com) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1uh2Rr-0006zM-JM for xen-devel@lists.xenproject.org; Wed, 30 Jul 2025 08:46:07 +0000 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by se1-gles-sth1.inumbo.com (Halon) with ESMTP id a1d9d7d1-6d21-11f0-a320-13f23c93f187; Wed, 30 Jul 2025 10:46:06 +0200 (CEST) Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.121.207.14]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id 203E11515; Wed, 30 Jul 2025 01:45:58 -0700 (PDT) Received: from PWQ0QT7DJ1.arm.com (unknown [10.57.73.135]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id A7B2A3F66E; Wed, 30 Jul 2025 01:46:03 -0700 (PDT) X-Outflank-Mailman: Message body and most headers restored to incoming version X-BeenThere: xen-devel@lists.xenproject.org List-Id: Xen developer discussion List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , Errors-To: xen-devel-bounces@lists.xenproject.org Precedence: list Sender: "Xen-devel" X-Inumbo-ID: a1d9d7d1-6d21-11f0-a320-13f23c93f187 From: Hari Limaye To: xen-devel@lists.xenproject.org Cc: luca.fancellu@arm.com, Penny Zheng , Stefano Stabellini , Julien Grall , Bertrand Marquis , Michal Orzel , Volodymyr Babchuk , Andrew Cooper , Anthony PERARD , Jan Beulich , =?UTF-8?q?Roger=20Pau=20Monn=C3=A9?= , Penny Zheng , Wei Chen Subject: [PATCH 5/5] xen/arm: map static memory on demand Date: Wed, 30 Jul 2025 09:45:34 +0100 Message-ID: X-Mailer: git-send-email 2.42.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-ZM-MESSAGEID: 1753865185314116600 Content-Type: text/plain; charset="utf-8" From: Penny Zheng In the function `init_staticmem_pages` we need to have mapped static memory banks for initialization. Unlike on an MMU system, we cannot map the entire RAM on an MPU system as we have a limited number of MPU memory regions. To solve this, transiently map the static memory banks for initialization. Signed-off-by: Penny Zheng Signed-off-by: Wei Chen Signed-off-by: Luca Fancellu Signed-off-by: Hari Limaye Reviewed-by: Ayan Kumar Halder Tested-by: Ayan Kumar Halder --- xen/arch/arm/include/asm/mmu/mm.h | 3 +++ xen/arch/arm/include/asm/mpu/mm.h | 4 ++++ xen/arch/arm/mpu/setup.c | 11 +++++++++++ xen/include/xen/static-memory.h | 8 ++++++++ 4 files changed, 26 insertions(+) diff --git a/xen/arch/arm/include/asm/mmu/mm.h b/xen/arch/arm/include/asm/m= mu/mm.h index 7f4d59137d..645a0ea3cb 100644 --- a/xen/arch/arm/include/asm/mmu/mm.h +++ b/xen/arch/arm/include/asm/mmu/mm.h @@ -110,6 +110,9 @@ void dump_pt_walk(paddr_t ttbr, paddr_t addr, extern void switch_ttbr(uint64_t ttbr); extern void relocate_and_switch_ttbr(uint64_t ttbr); =20 +static inline void map_staticmem_pages_to_xen(paddr_t start, paddr_t end) = {} +static inline void unmap_staticmem_pages_to_xen(paddr_t start, paddr_t end= ) {} + #endif /* __ARM_MMU_MM_H__ */ =20 /* diff --git a/xen/arch/arm/include/asm/mpu/mm.h b/xen/arch/arm/include/asm/m= pu/mm.h index 177550f5bd..118034bbdc 100644 --- a/xen/arch/arm/include/asm/mpu/mm.h +++ b/xen/arch/arm/include/asm/mpu/mm.h @@ -128,6 +128,10 @@ void *map_mm_range(paddr_t start, paddr_t end, unsigne= d int flags); */ void unmap_mm_range(paddr_t start); =20 +/* {un}map_staticmem_pages_to_xen used while initializing static memory ba= nks */ +void map_staticmem_pages_to_xen(paddr_t start, paddr_t end); +void unmap_staticmem_pages_to_xen(paddr_t start, paddr_t end); + /* * Checks whether a given memory range is present in the provided table of * MPU protection regions. diff --git a/xen/arch/arm/mpu/setup.c b/xen/arch/arm/mpu/setup.c index 163573b932..dbc3107333 100644 --- a/xen/arch/arm/mpu/setup.c +++ b/xen/arch/arm/mpu/setup.c @@ -83,6 +83,17 @@ void * __init early_fdt_map(paddr_t fdt_paddr) return fdt_virt; } =20 +void __init map_staticmem_pages_to_xen(paddr_t start, paddr_t end) +{ + if ( !map_mm_range(start, end, PAGE_HYPERVISOR) ) + panic("Unable to map staticmem pages to Xen!"); +} + +void __init unmap_staticmem_pages_to_xen(paddr_t start, paddr_t end) +{ + unmap_mm_range(start); +} + /* * copy_from_paddr - copy data from a physical address * @dst: destination virtual address diff --git a/xen/include/xen/static-memory.h b/xen/include/xen/static-memor= y.h index e445aa8057..d99abac113 100644 --- a/xen/include/xen/static-memory.h +++ b/xen/include/xen/static-memory.h @@ -18,7 +18,15 @@ static inline void init_staticmem_bank(const struct memb= ank *bank) if ( mfn_x(bank_end) <=3D mfn_x(bank_start) ) return; =20 + /* Map temporarily before initialization */ + map_staticmem_pages_to_xen(mfn_to_maddr(bank_start), + mfn_to_maddr(bank_end)); + unprepare_staticmem_pages(mfn_to_page(bank_start), bank_pages, false); + + /* Unmap immediately after initialization */ + unmap_staticmem_pages_to_xen(mfn_to_maddr(bank_start), + mfn_to_maddr(bank_end)); } =20 void allocate_static_memory(struct domain *d, struct kernel_info *kinfo, --=20 2.34.1