public inbox for devel@edk2.groups.io
 help / color / mirror / Atom feed
From: "Jianyong Wu" <jianyong.wu@arm.com>
To: "devel@edk2.groups.io" <devel@edk2.groups.io>,
	Jianyong Wu <Jianyong.Wu@arm.com>,
	Sami Mujawar <Sami.Mujawar@arm.com>
Cc: "ard.biesheuvel@linaro.org" <ard.biesheuvel@linaro.org>,
	Justin He <Justin.He@arm.com>,
	Ard Biesheuvel <ardb+tianocore@kernel.org>,
	"quic_llindhol@quicinc.com" <quic_llindhol@quicinc.com>,
	"kraxel@redhat.com" <kraxel@redhat.com>
Subject: Re: [edk2-devel] [PATCH 1/2] CloudHv/arm: add PeiMemInfoLib
Date: Mon, 8 Aug 2022 07:03:02 +0000	[thread overview]
Message-ID: <DB9PR08MB7511CE0CE395406DA0E7885EF4639@DB9PR08MB7511.eurprd08.prod.outlook.com> (raw)
In-Reply-To: <17063BDF40129601.5552@groups.io>

+cc: Ard Biesheuvel, Leif Lindholm, Gerd Hoffmann

> -----Original Message-----
> From: devel@edk2.groups.io <devel@edk2.groups.io> On Behalf Of Jianyong
> Wu via groups.io
> Sent: Friday, July 29, 2022 3:22 PM
> To: devel@edk2.groups.io; Sami Mujawar <Sami.Mujawar@arm.com>
> Cc: ard.biesheuvel@linaro.org; Justin He <Justin.He@arm.com>; Jianyong
> Wu <Jianyong.Wu@arm.com>
> Subject: [edk2-devel] [PATCH 1/2] CloudHv/arm: add PeiMemInfoLib
>
> Memory layout in CLoud Hypervisor for arm is changed and is different with
> Qemu, thus we should build its own PeiMemInfoLib.
> The main change in the memory layout is that normal ram may not
> contiguous under 4G. The top 64M under 4G is reserved for 32bit device.
>
> What this patch does:
> 1. get all of the memory node from DT;
> 2. Init page table for each memory node; 3. Add all of the memory nodes to
> Hob;
>
> Signed-off-by: Jianyong Wu <jianyong.wu@arm.com>
> ---
>  .../CloudHvVirtMemInfoLib.c                   | 251 ++++++++++++++++++
>  .../CloudHvVirtMemInfoPeiLib.inf              |  46 ++++
>  2 files changed, 297 insertions(+)
>  create mode 100755
> ArmVirtPkg/Library/CloudHvVirtMemInfoLib/CloudHvVirtMemInfoLib.c
>  create mode 100755
> ArmVirtPkg/Library/CloudHvVirtMemInfoLib/CloudHvVirtMemInfoPeiLib.inf
>
> diff --git
> a/ArmVirtPkg/Library/CloudHvVirtMemInfoLib/CloudHvVirtMemInfoLib.c
> b/ArmVirtPkg/Library/CloudHvVirtMemInfoLib/CloudHvVirtMemInfoLib.c
> new file mode 100755
> index 0000000000..7ae24641d3
> --- /dev/null
> +++
> b/ArmVirtPkg/Library/CloudHvVirtMemInfoLib/CloudHvVirtMemInfoLib.c
> @@ -0,0 +1,251 @@
> +/** @file
> +
> +  Copyright (c) 2022, Arm Limited. All rights reserved.
> +
> +  SPDX-License-Identifier: BSD-2-Clause-Patent
> +
> +**/
> +
> +#include <PiPei.h>
> +
> +#include <Base.h>
> +#include <libfdt.h>
> +#include <Library/ArmLib.h>
> +#include <Library/BaseMemoryLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/MemoryAllocationLib.h> #include <Library/PcdLib.h>
> +
> +#include<Library/PrePiLib.h>
> +
> +// The first memnory node is the one whose base address is the lowest.
> +UINT64 FirMemNodeBase = 0, FirMemNodeSize = 0; // // Cloud Hypervisor
> +may have more than one memory nodes. Even there is no limit for that,
> +// I think 10 is enough in general.
> +//
> +#define CLOUDHV_MAX_MEM_NODE_NUM 10
> +
> +// Record memory node info (base address and size) struct
> +CloudHvMemNodeInfo {
> +  UINT64 Base;
> +  UINT64 Size;
> +};
> +
> +struct CloudHvMemNodeInfo
> CloudHvMemNode[CLOUDHV_MAX_MEM_NODE_NUM];
> +
> +RETURN_STATUS
> +EFIAPI
> +CloudHvVirtMemInfoPeiLibConstructor (
> +  VOID
> +  )
> +{
> +  VOID           *DeviceTreeBase;
> +  EFI_RESOURCE_ATTRIBUTE_TYPE  ResourceAttributes;
> +  INT32          Node, Prev;
> +  UINT64         CurBase, MemBase;
> +  UINT64         CurSize;
> +  CONST CHAR8    *Type;
> +  INT32          Len;
> +  CONST UINT64   *RegProp;
> +  RETURN_STATUS  PcdStatus;
> +  UINT8          Index;
> +
> +  ZeroMem (CloudHvMemNode, sizeof(CloudHvMemNode[0]) *
> + CLOUDHV_MAX_MEM_NODE_NUM);
> +
> +  Index = 0;
> +  MemBase = FixedPcdGet64 (PcdSystemMemoryBase);  ResourceAttributes
> =
> + (
> +                        EFI_RESOURCE_ATTRIBUTE_PRESENT |
> +                        EFI_RESOURCE_ATTRIBUTE_INITIALIZED |
> +                        EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE |
> +                        EFI_RESOURCE_ATTRIBUTE_TESTED
> +                        );
> +  DeviceTreeBase = (VOID *)(UINTN)PcdGet64
> + (PcdDeviceTreeInitialBaseAddress);
> +  ASSERT (DeviceTreeBase != NULL);
> +
> +  //
> +  // Make sure we have a valid device tree blob  //  ASSERT
> + (fdt_check_header (DeviceTreeBase) == 0);
> +
> +  //
> +  // Look for the lowest memory node
> +  //
> +  for (Prev = 0; ; Prev = Node) {
> +    Node = fdt_next_node (DeviceTreeBase, Prev, NULL);
> +    if (Node < 0) {
> +      break;
> +    }
> +
> +    //
> +    // Check for memory node
> +    //
> +    Type = fdt_getprop (DeviceTreeBase, Node, "device_type", &Len);
> +    if (Type && (AsciiStrnCmp (Type, "memory", Len) == 0)) {
> +      //
> +      // Get the 'reg' property of this node. For now, we will assume
> +      // two 8 byte quantities for base and size, respectively.
> +      //
> +      RegProp = fdt_getprop (DeviceTreeBase, Node, "reg", &Len);
> +      if ((RegProp != 0) && (Len == (2 * sizeof (UINT64)))) {
> +        CurBase = fdt64_to_cpu (ReadUnaligned64 (RegProp));
> +        CurSize = fdt64_to_cpu (ReadUnaligned64 (RegProp + 1));
> +
> +        DEBUG ((
> +          DEBUG_INFO,
> +          "%a: System RAM @ 0x%lx - 0x%lx\n",
> +          __FUNCTION__,
> +          CurBase,
> +          CurBase + CurSize - 1
> +          ));
> +
> +        if (CurBase == MemBase) {
> +            FirMemNodeBase = CurBase;
> +            FirMemNodeSize = CurSize;
> +        }
> +
> +        CloudHvMemNode[Index].Base = CurBase;
> +        CloudHvMemNode[Index].Size = CurSize;
> +        Index++;
> +        // We should build Hob seperately for the memory node except the
> first one
> +        if (CurBase != MemBase) {
> +          BuildResourceDescriptorHob (
> +            EFI_RESOURCE_SYSTEM_MEMORY,
> +            ResourceAttributes,
> +            CurBase,
> +            CurSize
> +            );
> +        }
> +        if (Index >= CLOUDHV_MAX_MEM_NODE_NUM) {
> +          DEBUG ((
> +            DEBUG_WARN,
> +            "%a: memory node larger than %d will not be included into Memory
> System\n",
> +            __FUNCTION__,
> +            CLOUDHV_MAX_MEM_NODE_NUM
> +            ));
> +          break;
> +        }
> +      } else {
> +        DEBUG ((
> +          DEBUG_ERROR,
> +          "%a: Failed to parse FDT memory node\n",
> +          __FUNCTION__
> +          ));
> +      }
> +    }
> +  }
> +
> +  //
> +  // Make sure the start of DRAM matches our expectation  //  ASSERT
> + (FixedPcdGet64 (PcdSystemMemoryBase) == FirMemNodeBase);  PcdStatus
> =
> + PcdSet64S (PcdSystemMemorySize, FirMemNodeSize);
> ASSERT_RETURN_ERROR
> + (PcdStatus);  ASSERT (
> +    (((UINT64)PcdGet64 (PcdFdBaseAddress) +
> +      (UINT64)PcdGet32 (PcdFdSize)) <= FirMemNodeBase) ||
> +    ((UINT64)PcdGet64 (PcdFdBaseAddress) >= (FirMemNodeBase +
> FirMemNodeSize))
> +    );
> +
> +  return RETURN_SUCCESS;
> +}
> +
> +// Number of Virtual Memory Map Descriptors #define
> +MAX_VIRTUAL_MEMORY_MAP_DESCRIPTORS  (4 +
> CLOUDHV_MAX_MEM_NODE_NUM)
> +
> +//
> +// Core peripherals such as the UART, the GIC and the RTC are // all
> +mapped in the 'miscellaneous device I/O' region, which we just map //
> +in its entirety rather than device by device. Note that it does not //
> +cover any of the NOR flash banks or PCI resource windows.
> +//
> +#define MACH_VIRT_PERIPH_BASE  0x00400000 #define
> MACH_VIRT_PERIPH_SIZE
> +0x0FC00000
> +
> +//
> +// The top of the 64M memory region under 4GB reserved for device //
> +#define TOP_32BIT_DEVICE_BASE  0xFC000000 #define
> TOP_32BIT_DEVICE_SIZE
> +0x04000000
> +
> +/**
> +  Return the Virtual Memory Map of your platform
> +
> +  This Virtual Memory Map is used by MemoryInitPei Module to initialize
> + the MMU  on your platform.
> +
> +  @param[out]   VirtualMemoryMap    Array of
> ARM_MEMORY_REGION_DESCRIPTOR
> +                                    describing a Physical-to-Virtual Memory
> +                                    mapping. This array must be ended by a
> +                                    zero-filled entry. The allocated memory
> +                                    will not be freed.
> +
> +**/
> +VOID
> +ArmVirtGetMemoryMap (
> +  OUT ARM_MEMORY_REGION_DESCRIPTOR  **VirtualMemoryMap
> +  )
> +{
> +  ARM_MEMORY_REGION_DESCRIPTOR  *VirtualMemoryTable;
> +  UINT8 Index = 0, i = 0;
> +
> +  ASSERT (VirtualMemoryMap != NULL);
> +
> +  VirtualMemoryTable = AllocatePool (
> +                         sizeof (ARM_MEMORY_REGION_DESCRIPTOR) *
> +                         MAX_VIRTUAL_MEMORY_MAP_DESCRIPTORS
> +                         );
> +
> +  if (VirtualMemoryTable == NULL) {
> +    DEBUG ((DEBUG_ERROR, "%a: Error: Failed AllocatePool()\n",
> __FUNCTION__));
> +    return;
> +  }
> +    // System DRAM
> +  while (CloudHvMemNode[i].Size != 0) {
> +    VirtualMemoryTable[Index].PhysicalBase = CloudHvMemNode[i].Base;
> +    VirtualMemoryTable[Index].VirtualBase  = CloudHvMemNode[i].Base;
> +    VirtualMemoryTable[Index].Length       = CloudHvMemNode[i].Size;
> +    VirtualMemoryTable[Index].Attributes   =
> ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK;
> +
> +    DEBUG ((
> +      DEBUG_INFO,
> +      "%a: Dumping System DRAM Memory Node%d Map:\n"
> +      "\tPhysicalBase: 0x%lX\n"
> +      "\tVirtualBase: 0x%lX\n"
> +      "\tLength: 0x%lX\n",
> +      __FUNCTION__,
> +      i,
> +      VirtualMemoryTable[Index].PhysicalBase,
> +      VirtualMemoryTable[Index].VirtualBase,
> +      VirtualMemoryTable[Index].Length
> +      ));
> +    Index++;
> +    i++;
> +  }
> +  // Memory mapped peripherals (UART, RTC, GIC, virtio-mmio, etc)
> + VirtualMemoryTable[Index].PhysicalBase = MACH_VIRT_PERIPH_BASE;
> + VirtualMemoryTable[Index].VirtualBase  = MACH_VIRT_PERIPH_BASE;
> +  VirtualMemoryTable[Index].Length       = MACH_VIRT_PERIPH_SIZE;
> +  VirtualMemoryTable[Index].Attributes   =
> ARM_MEMORY_REGION_ATTRIBUTE_DEVICE;
> +  Index++;
> +
> +  // Map the FV region as normal executable memory
> + VirtualMemoryTable[Index].PhysicalBase = PcdGet64 (PcdFvBaseAddress);
> + VirtualMemoryTable[Index].VirtualBase  =
> VirtualMemoryTable[Index].PhysicalBase;
> +  VirtualMemoryTable[Index].Length       = FixedPcdGet32 (PcdFvSize);
> +  VirtualMemoryTable[Index].Attributes   =
> ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK;
> +  Index++;
> +
> +  // Memory mapped for 32bit device (like TPM)
> + VirtualMemoryTable[Index].PhysicalBase = TOP_32BIT_DEVICE_BASE;
> + VirtualMemoryTable[Index].VirtualBase  = TOP_32BIT_DEVICE_BASE;
> +  VirtualMemoryTable[Index].Length       = TOP_32BIT_DEVICE_SIZE;
> +  VirtualMemoryTable[Index].Attributes   =
> ARM_MEMORY_REGION_ATTRIBUTE_DEVICE;
> +  Index++;
> +
> +  // End of Table
> +  ZeroMem (&VirtualMemoryTable[Index], sizeof
> + (ARM_MEMORY_REGION_DESCRIPTOR));
> +
> +  *VirtualMemoryMap = VirtualMemoryTable; }
> diff --git
> a/ArmVirtPkg/Library/CloudHvVirtMemInfoLib/CloudHvVirtMemInfoPeiLib.in
> f
> b/ArmVirtPkg/Library/CloudHvVirtMemInfoLib/CloudHvVirtMemInfoPeiLib.i
> nf
> new file mode 100755
> index 0000000000..5dd96faadd
> --- /dev/null
> +++
> b/ArmVirtPkg/Library/CloudHvVirtMemInfoLib/CloudHvVirtMemInfoPeiLib.
> +++ inf
> @@ -0,0 +1,46 @@
> +#/* @file
> +#
> +#  Copyright (c) 2011-2015, ARM Limited. All rights reserved.
> +#  Copyright (c) 2014-2017, Linaro Limited. All rights reserved.
> +#
> +#  SPDX-License-Identifier: BSD-2-Clause-Patent # #*/
> +
> +[Defines]
> +  INF_VERSION                    = 0x0001001A
> +  BASE_NAME                      = QemuVirtMemInfoPeiLib
> +  FILE_GUID                      = 0c4d10cf-d949-49b4-bd13-47a4ae22efce
> +  MODULE_TYPE                    = BASE
> +  VERSION_STRING                 = 1.0
> +  LIBRARY_CLASS                  = ArmVirtMemInfoLib|PEIM
> +  CONSTRUCTOR                    = CloudHvVirtMemInfoPeiLibConstructor
> +
> +[Sources]
> +  CloudHvVirtMemInfoLib.c
> +
> +[Packages]
> +  ArmPkg/ArmPkg.dec
> +  ArmVirtPkg/ArmVirtPkg.dec
> +  EmbeddedPkg/EmbeddedPkg.dec
> +  MdeModulePkg/MdeModulePkg.dec
> +  MdePkg/MdePkg.dec
> +
> +[LibraryClasses]
> +  ArmLib
> +  BaseMemoryLib
> +  DebugLib
> +  FdtLib
> +  PcdLib
> +  MemoryAllocationLib
> +
> +[Pcd]
> +  gArmTokenSpaceGuid.PcdFdBaseAddress
> +  gArmTokenSpaceGuid.PcdFvBaseAddress
> +  gArmTokenSpaceGuid.PcdSystemMemoryBase
> +  gArmTokenSpaceGuid.PcdSystemMemorySize
> +
> +[FixedPcd]
> +  gArmTokenSpaceGuid.PcdFdSize
> +  gArmTokenSpaceGuid.PcdFvSize
> +  gArmVirtTokenSpaceGuid.PcdDeviceTreeInitialBaseAddress
> --
> 2.17.1
>
>
>
> 
>

IMPORTANT NOTICE: The contents of this email and any attachments are confidential and may also be privileged. If you are not the intended recipient, please notify the sender immediately and do not disclose the contents to any other person, use it for any purpose, or store or copy the information in any medium. Thank you.

  parent reply	other threads:[~2022-08-08  7:03 UTC|newest]

Thread overview: 11+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-07-29  7:21 [PATCH 0/2] CloudHv/arm: Add specific mem info lib Jianyong Wu
2022-07-29  7:21 ` [PATCH 1/2] CloudHv/arm: add PeiMemInfoLib Jianyong Wu
2022-08-08 11:27   ` Sami Mujawar
2022-08-09  8:31     ` Jianyong Wu
     [not found]     ` <1709A00AB94047B2.29555@groups.io>
2022-08-18  5:22       ` [edk2-devel] " Jianyong Wu
2022-08-18 11:40         ` Sami Mujawar
2022-08-19  7:41           ` Jianyong Wu
2022-07-29  7:21 ` [PATCH 2/2] CloudHv/arm: switch PeiMemLib to its own Jianyong Wu
2022-08-08 11:29   ` Sami Mujawar
     [not found] ` <17063BDF40129601.5552@groups.io>
2022-08-08  7:03   ` Jianyong Wu [this message]
     [not found] ` <17063BDFB8173BFA.24450@groups.io>
2022-08-08  7:04   ` [edk2-devel] " Jianyong Wu

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-list 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=DB9PR08MB7511CE0CE395406DA0E7885EF4639@DB9PR08MB7511.eurprd08.prod.outlook.com \
    --to=devel@edk2.groups.io \
    /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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox