123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287 |
- /** @file
- Copyright (c) 2020 - 2023, Ampere Computing LLC. All rights reserved.<BR>
- SPDX-License-Identifier: BSD-2-Clause-Patent
- **/
- #include "AcpiPlatform.h"
- EFI_ACPI_6_3_GIC_ITS_STRUCTURE GicItsTemplate = {
- EFI_ACPI_6_3_GIC_ITS,
- sizeof (EFI_ACPI_6_3_GIC_ITS_STRUCTURE),
- EFI_ACPI_RESERVED_WORD,
- 0, /* GicItsId */
- 0, /* PhysicalBaseAddress */
- 0, /* Reserved2 */
- };
- EFI_ACPI_6_3_GICR_STRUCTURE GicRTemplate = {
- EFI_ACPI_6_3_GICR,
- sizeof (EFI_ACPI_6_3_GICR_STRUCTURE),
- EFI_ACPI_RESERVED_WORD,
- AC01_GICR_MASTER_BASE_ADDRESS, /* DiscoveryRangeBaseAddress */
- 0x1000000, /* DiscoveryRangeLength */
- };
- EFI_ACPI_6_3_GIC_DISTRIBUTOR_STRUCTURE GicDTemplate = {
- EFI_ACPI_6_3_GICD,
- sizeof (EFI_ACPI_6_3_GIC_DISTRIBUTOR_STRUCTURE),
- EFI_ACPI_RESERVED_WORD,
- 0, /* GicDistHwId */
- AC01_GICD_MASTER_BASE_ADDRESS, /* GicDistBase */
- 0, /* GicDistVector */
- 0x3, /* GicVersion */
- {EFI_ACPI_RESERVED_BYTE, EFI_ACPI_RESERVED_BYTE, EFI_ACPI_RESERVED_BYTE}
- };
- EFI_ACPI_6_3_GIC_STRUCTURE GiccTemplate = {
- EFI_ACPI_6_3_GIC,
- sizeof (EFI_ACPI_6_3_GIC_STRUCTURE),
- EFI_ACPI_RESERVED_WORD,
- 0, /* GicId */
- 0, /* AcpiCpuUid */
- 0, /* Flags */
- 0,
- 23, /* PmuIrq */
- 0,
- 0,
- 0,
- 0,
- 25, /* GsivId */
- 0, /* GicRBase */
- 0, /* Mpidr */
- 0, /* ProcessorPowerEfficiencyClass */
- 0, /* Reserved2 */
- 21, /* SPE irq */
- };
- EFI_ACPI_6_3_MULTIPLE_APIC_DESCRIPTION_TABLE_HEADER MADTTableHeaderTemplate = {
- __ACPI_HEADER (
- EFI_ACPI_6_3_MULTIPLE_APIC_DESCRIPTION_TABLE_SIGNATURE,
- 0, /* need fill in */
- EFI_ACPI_6_3_MULTIPLE_APIC_DESCRIPTION_TABLE_REVISION
- ),
- };
- EFI_ACPI_6_3_MULTIPLE_APIC_DESCRIPTION_TABLE_HEADER *MadtTablePointer;
- UINT32
- AcpiInstallMadtProcessorNode (
- VOID *EntryPointer,
- UINT32 CpuId
- )
- {
- EFI_ACPI_6_3_GIC_STRUCTURE *MadtProcessorEntryPointer = EntryPointer;
- UINT32 SocketId;
- UINT32 ClusterId;
- UINTN Size;
- Size = sizeof (GiccTemplate);
- CopyMem (MadtProcessorEntryPointer, &GiccTemplate, Size);
- SocketId = SOCKET_ID (CpuId);
- ClusterId = CLUSTER_ID (CpuId);
- //
- // GICv2 compatibility mode is not supported.
- // Hence, set GIC's CPU Interface Number to 0.
- //
- MadtProcessorEntryPointer->CPUInterfaceNumber = 0;
- MadtProcessorEntryPointer->AcpiProcessorUid =
- (SocketId << PLATFORM_SOCKET_UID_BIT_OFFSET) +
- (ClusterId << 8) + (CpuId % PLATFORM_CPU_NUM_CORES_PER_CPM);
- MadtProcessorEntryPointer->Flags = 1;
- MadtProcessorEntryPointer->MPIDR =
- (((ClusterId << 8) + (CpuId % PLATFORM_CPU_NUM_CORES_PER_CPM)) << 8);
- MadtProcessorEntryPointer->MPIDR += (((UINT64)SocketId) << 32);
- return Size;
- }
- UINT32
- AcpiInstallMadtGicD (
- VOID *EntryPointer
- )
- {
- EFI_ACPI_6_3_GIC_DISTRIBUTOR_STRUCTURE *GicDEntryPointer = EntryPointer;
- UINTN Size;
- Size = sizeof (GicDTemplate);
- CopyMem (GicDEntryPointer, &GicDTemplate, Size);
- return Size;
- }
- UINT32
- AcpiInstallMadtGicR (
- VOID *EntryPointer,
- UINT32 SocketId
- )
- {
- EFI_ACPI_6_3_GICR_STRUCTURE *GicREntryPointer = EntryPointer;
- UINTN Size;
- /*
- * If the Slave socket is not present, discard the Slave socket
- * GIC redistributor region
- */
- if (SocketId == 1 && !IsSlaveSocketActive ()) {
- return 0;
- }
- Size = sizeof (GicRTemplate);
- CopyMem (GicREntryPointer, &GicRTemplate, Size);
- if (SocketId == 1) {
- GicREntryPointer->DiscoveryRangeBaseAddress = AC01_GICR_SLAVE_BASE_ADDRESS;
- }
- return Size;
- }
- UINT32
- AcpiInstallMadtGicIts (
- VOID *EntryPointer,
- UINT32 Index
- )
- {
- EFI_ACPI_6_3_GIC_ITS_STRUCTURE *GicItsEntryPointer = EntryPointer;
- UINTN Size, Offset;
- UINT64 GicBase = AC01_GICD_MASTER_BASE_ADDRESS;
- UINT32 ItsId = Index;
- if (Index > SOCKET0_LAST_RC) { /* Socket 1, Index: 8-15 */
- GicBase = AC01_GICD_SLAVE_BASE_ADDRESS;
- Index -= (SOCKET0_LAST_RC + 1); /* Socket 1, Index:8 -> RCA0 */
- }
- Size = sizeof (GicItsTemplate);
- CopyMem (GicItsEntryPointer, &GicItsTemplate, Size);
- Offset = 0x40000 + Index * 0x20000;
- GicItsEntryPointer->GicItsId = ItsId;
- GicItsEntryPointer->PhysicalBaseAddress = Offset + GicBase;
- return Size;
- }
- /*
- * Install MADT table.
- */
- EFI_STATUS
- AcpiInstallMadtTable (
- VOID
- )
- {
- EFI_ACPI_6_3_GIC_STRUCTURE *GiccEntryPointer = NULL;
- EFI_ACPI_TABLE_PROTOCOL *AcpiTableProtocol;
- UINTN MadtTableKey = 0;
- INTN Index;
- EFI_STATUS Status;
- UINTN Size;
- UINTN Length;
- UINT32 *CoreOrder;
- UINT32 SktMaxCoreNum;
- Status = gBS->LocateProtocol (
- &gEfiAcpiTableProtocolGuid,
- NULL,
- (VOID **)&AcpiTableProtocol
- );
- if (EFI_ERROR (Status)) {
- return Status;
- }
- Size = sizeof (MADTTableHeaderTemplate) +
- sizeof (GiccTemplate) * GetNumberOfActiveCores () +
- sizeof (GicDTemplate) +
- sizeof (GicRTemplate) * GetNumberOfActiveSockets () +
- sizeof (GicItsTemplate) * (SOCKET0_LAST_RC - SOCKET0_FIRST_RC + 1);
- if (IsSlaveSocketActive ()) {
- Size += (sizeof (GicItsTemplate) * (SOCKET1_LAST_RC - SOCKET1_FIRST_RC + 1));
- } else if (!IsSlaveSocketAvailable ()) {
- Size += sizeof (GicItsTemplate) * 2; /* RCA0/1 */
- }
- MadtTablePointer =
- (EFI_ACPI_6_3_MULTIPLE_APIC_DESCRIPTION_TABLE_HEADER *)AllocateZeroPool (Size);
- if (MadtTablePointer == NULL) {
- return EFI_OUT_OF_RESOURCES;
- }
- GiccEntryPointer =
- (EFI_ACPI_6_3_GIC_STRUCTURE *)((UINT64)MadtTablePointer +
- sizeof (MADTTableHeaderTemplate));
- /* Install Gic interface for each processor */
- Length = 0;
- CoreOrder = CpuGetCoreOrder ();
- ASSERT (CoreOrder != NULL);
- SktMaxCoreNum = PLATFORM_CPU_MAX_CPM * PLATFORM_CPU_NUM_CORES_PER_CPM;
- for (Index = 0; Index < SktMaxCoreNum; Index++) {
- if (IsCpuEnabled (CoreOrder[Index])) {
- Length += AcpiInstallMadtProcessorNode ((VOID *)((UINT64)GiccEntryPointer + Length), CoreOrder[Index]);
- }
- }
- for (Index = 0; Index < SktMaxCoreNum; Index++) {
- if (IsCpuEnabled (CoreOrder[Index] + SktMaxCoreNum)) {
- Length += AcpiInstallMadtProcessorNode ((VOID *)((UINT64)GiccEntryPointer + Length), CoreOrder[Index] + SktMaxCoreNum);
- }
- }
- /* Install Gic Distributor */
- Length += AcpiInstallMadtGicD ((VOID *)((UINT64)GiccEntryPointer + Length));
- /* Install Gic Redistributor */
- for (Index = 0; Index < PLATFORM_CPU_MAX_SOCKET; Index++) {
- Length += AcpiInstallMadtGicR ((VOID *)((UINT64)GiccEntryPointer + Length), Index);
- }
- /* Install Gic ITS */
- if (!IsSlaveSocketAvailable ()) {
- for (Index = 0; Index <= 1; Index++) { /* RCA0/1 */
- Length += AcpiInstallMadtGicIts ((VOID *)((UINT64)GiccEntryPointer + Length), Index);
- }
- }
- for (Index = SOCKET0_FIRST_RC; Index <= SOCKET0_LAST_RC; Index++) {
- Length += AcpiInstallMadtGicIts ((VOID *)((UINT64)GiccEntryPointer + Length), Index);
- }
- if (IsSlaveSocketActive ()) {
- for (Index = SOCKET1_FIRST_RC; Index <= SOCKET1_LAST_RC; Index++) {
- Length += AcpiInstallMadtGicIts ((VOID *)((UINT64)GiccEntryPointer + Length), Index);
- }
- }
- CopyMem (
- MadtTablePointer,
- &MADTTableHeaderTemplate,
- sizeof (MADTTableHeaderTemplate)
- );
- Length += sizeof (MADTTableHeaderTemplate);
- MadtTablePointer->Header.Length = Length;
- ASSERT (Size == Length);
- CopyMem (
- MadtTablePointer->Header.OemId,
- PcdGetPtr (PcdAcpiDefaultOemId),
- sizeof (MadtTablePointer->Header.OemId)
- );
- AcpiUpdateChecksum ((UINT8 *)MadtTablePointer, MadtTablePointer->Header.Length);
- Status = AcpiTableProtocol->InstallAcpiTable (
- AcpiTableProtocol,
- (VOID *)MadtTablePointer,
- MadtTablePointer->Header.Length,
- &MadtTableKey
- );
- FreePool ((VOID *)MadtTablePointer);
- if (EFI_ERROR (Status)) {
- return Status;
- }
- return EFI_SUCCESS;
- }
|