From nobody Fri Oct 31 03:48:31 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 1753086770496837.02236606163; Mon, 21 Jul 2025 01:32:50 -0700 (PDT) Received: from list by lists.xenproject.org with outflank-mailman.1051163.1419471 (Exim 4.92) (envelope-from ) id 1udlwt-0007LO-Ck; Mon, 21 Jul 2025 08:32:39 +0000 Received: by outflank-mailman (output) from mailman id 1051163.1419471; Mon, 21 Jul 2025 08:32:39 +0000 Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.92) (envelope-from ) id 1udlwt-0007LC-9H; Mon, 21 Jul 2025 08:32:39 +0000 Received: by outflank-mailman (input) for mailman id 1051163; Mon, 21 Jul 2025 08:32:37 +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 1udlwr-0005OI-KD for xen-devel@lists.xenproject.org; Mon, 21 Jul 2025 08:32:37 +0000 Received: from foss.arm.com (foss.arm.com [217.140.110.172]) by se1-gles-flk1.inumbo.com (Halon) with ESMTP id 40d39d8e-660d-11f0-b894-0df219b8e170; Mon, 21 Jul 2025 10:32:35 +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 439FD153B; Mon, 21 Jul 2025 01:32:29 -0700 (PDT) Received: from PWQ0QT7DJ1.arm.com (unknown [10.57.71.32]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 9F8713F66E; Mon, 21 Jul 2025 01:32:33 -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: 40d39d8e-660d-11f0-b894-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 , Ayan Kumar Halder Subject: [PATCH v4 5/6] arm/mpu: Implement early_fdt_map support in MPU systems Date: Mon, 21 Jul 2025 09:31:46 +0100 Message-ID: <3326c844f49a94228c1d79fc1afec614691d4a2a.1753084737.git.hari.limaye@arm.com> X-Mailer: git-send-email 2.42.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-ZM-MESSAGEID: 1753086772661116600 Content-Type: text/plain; charset="utf-8" From: Luca Fancellu Implement the function early_fdt_map(), which is responsible for mapping the Device Tree Blob in the early stages of the boot process, for MPU systems. We make use of the map_pages_to_xen() and destroy_xen_mappings() APIs. In particular the latter function is necessary in the case that the initial mapping of the fdt_header is insufficient to cover the entire DTB, as we must destroy and then remap the region due to the APIs no providing support for extending the size of an existing region. Signed-off-by: Luca Fancellu Signed-off-by: Hari Limaye Reviewed-by: Ayan Kumar Halder Reviewed-by: Michal Orzel --- Changes from v1: - Add Ayan's R-b Changes from v2: - Rename mapped_fdt_paddr -> mapped_fdt_base - Remove full stops - Add sanity check for MAX_FDT_SIZE - Improve comment regarding early return when DTB already mapped Changes from v3: - Use ASSERT instead of conditional check that `mapped_fdt_base =3D=3D INVALID_PADDR` --- xen/arch/arm/mpu/setup.c | 73 ++++++++++++++++++++++++++++++++++++++-- 1 file changed, 71 insertions(+), 2 deletions(-) diff --git a/xen/arch/arm/mpu/setup.c b/xen/arch/arm/mpu/setup.c index b4da77003f..2ef703757f 100644 --- a/xen/arch/arm/mpu/setup.c +++ b/xen/arch/arm/mpu/setup.c @@ -1,17 +1,86 @@ /* SPDX-License-Identifier: GPL-2.0-only */ =20 +#include #include #include +#include #include +#include #include +#include #include =20 +static paddr_t __initdata mapped_fdt_base =3D INVALID_PADDR; +static paddr_t __initdata mapped_fdt_limit =3D INVALID_PADDR; + void __init setup_pagetables(void) {} =20 void * __init early_fdt_map(paddr_t fdt_paddr) { - BUG_ON("unimplemented"); - return NULL; + /* Map at least a page containing the DTB address, exclusive range */ + paddr_t base =3D round_pgdown(fdt_paddr); + paddr_t limit =3D round_pgup(fdt_paddr + sizeof(struct fdt_header)); + unsigned int flags =3D PAGE_HYPERVISOR_RO; + void *fdt_virt =3D (void *)fdt_paddr; /* virt =3D=3D paddr for MPU */ + int rc; + uint32_t size; + unsigned long nr_mfns; + + /* + * Check whether the physical FDT address is set and meets the minimum + * alignment requirement. Since we are relying on MIN_FDT_ALIGN to be = at + * least 8 bytes so that we always access the magic and size fields + * of the FDT header after mapping the first chunk, double check if + * that is indeed the case. + */ + BUILD_BUG_ON(MIN_FDT_ALIGN < 8); + if ( !fdt_paddr || fdt_paddr % MIN_FDT_ALIGN ) + return NULL; + + /* + * DTB at this address has already been mapped.`start_xen` calls this = twice, + * before and after `setup_page_tables`, which is a no-op on MPU. + */ + if ( mapped_fdt_base =3D=3D fdt_paddr ) + return fdt_virt; + + ASSERT(mapped_fdt_base =3D=3D INVALID_PADDR); + + nr_mfns =3D (limit - base) >> PAGE_SHIFT; + + rc =3D map_pages_to_xen(base, maddr_to_mfn(base), nr_mfns, flags); + if ( rc ) + panic("Unable to map the device-tree\n"); + + mapped_fdt_base =3D fdt_paddr; + mapped_fdt_limit =3D limit; + + if ( fdt_magic(fdt_virt) !=3D FDT_MAGIC ) + return NULL; + + size =3D fdt_totalsize(fdt_virt); + if ( size > MAX_FDT_SIZE ) + return NULL; + + limit =3D round_pgup(fdt_paddr + size); + + /* If the mapped range is not enough, map the rest of the DTB. */ + if ( limit > mapped_fdt_limit ) + { + rc =3D destroy_xen_mappings(base, mapped_fdt_limit); + if ( rc ) + panic("Unable to unmap the device-tree header\n"); + + nr_mfns =3D (limit - base) >> PAGE_SHIFT; + + rc =3D map_pages_to_xen(base, maddr_to_mfn(base), nr_mfns, flags); + if ( rc ) + panic("Unable to map the device-tree\n"); + + mapped_fdt_limit =3D limit; + } + + return fdt_virt; } =20 /* --=20 2.34.1