]> git.proxmox.com Git - mirror_edk2.git/blame_incremental - ArmPlatformPkg/PrePi/MainMPCore.c
UefiCpuPkg: Move AsmRelocateApLoopStart from Mpfuncs.nasm to AmdSev.nasm
[mirror_edk2.git] / ArmPlatformPkg / PrePi / MainMPCore.c
... / ...
CommitLineData
1/** @file\r
2\r
3 Copyright (c) 2011-2014, ARM Limited. All rights reserved.\r
4\r
5 SPDX-License-Identifier: BSD-2-Clause-Patent\r
6\r
7**/\r
8\r
9#include "PrePi.h"\r
10\r
11#include <Library/ArmGicLib.h>\r
12\r
13#include <Ppi/ArmMpCoreInfo.h>\r
14\r
15VOID\r
16PrimaryMain (\r
17 IN UINTN UefiMemoryBase,\r
18 IN UINTN StacksBase,\r
19 IN UINT64 StartTimeStamp\r
20 )\r
21{\r
22 // Enable the GIC Distributor\r
23 ArmGicEnableDistributor (PcdGet64 (PcdGicDistributorBase));\r
24\r
25 // In some cases, the secondary cores are waiting for an SGI from the next stage boot loader to resume their initialization\r
26 if (!FixedPcdGet32 (PcdSendSgiToBringUpSecondaryCores)) {\r
27 // Sending SGI to all the Secondary CPU interfaces\r
28 ArmGicSendSgiTo (PcdGet64 (PcdGicDistributorBase), ARM_GIC_ICDSGIR_FILTER_EVERYONEELSE, 0x0E, PcdGet32 (PcdGicSgiIntId));\r
29 }\r
30\r
31 PrePiMain (UefiMemoryBase, StacksBase, StartTimeStamp);\r
32\r
33 // We must never return\r
34 ASSERT (FALSE);\r
35}\r
36\r
37VOID\r
38SecondaryMain (\r
39 IN UINTN MpId\r
40 )\r
41{\r
42 EFI_STATUS Status;\r
43 ARM_MP_CORE_INFO_PPI *ArmMpCoreInfoPpi;\r
44 UINTN Index;\r
45 UINTN ArmCoreCount;\r
46 ARM_CORE_INFO *ArmCoreInfoTable;\r
47 UINT32 ClusterId;\r
48 UINT32 CoreId;\r
49\r
50 VOID (*SecondaryStart)(\r
51 VOID\r
52 );\r
53 UINTN SecondaryEntryAddr;\r
54 UINTN AcknowledgeInterrupt;\r
55 UINTN InterruptId;\r
56\r
57 ClusterId = GET_CLUSTER_ID (MpId);\r
58 CoreId = GET_CORE_ID (MpId);\r
59\r
60 // On MP Core Platform we must implement the ARM MP Core Info PPI (gArmMpCoreInfoPpiGuid)\r
61 Status = GetPlatformPpi (&gArmMpCoreInfoPpiGuid, (VOID **)&ArmMpCoreInfoPpi);\r
62 ASSERT_EFI_ERROR (Status);\r
63\r
64 ArmCoreCount = 0;\r
65 Status = ArmMpCoreInfoPpi->GetMpCoreInfo (&ArmCoreCount, &ArmCoreInfoTable);\r
66 ASSERT_EFI_ERROR (Status);\r
67\r
68 // Find the core in the ArmCoreTable\r
69 for (Index = 0; Index < ArmCoreCount; Index++) {\r
70 if ((GET_MPIDR_AFF1 (ArmCoreInfoTable[Index].Mpidr) == ClusterId) &&\r
71 (GET_MPIDR_AFF0 (ArmCoreInfoTable[Index].Mpidr) == CoreId))\r
72 {\r
73 break;\r
74 }\r
75 }\r
76\r
77 // The ARM Core Info Table must define every core\r
78 ASSERT (Index != ArmCoreCount);\r
79\r
80 // Clear Secondary cores MailBox\r
81 MmioWrite32 (ArmCoreInfoTable[Index].MailboxClearAddress, ArmCoreInfoTable[Index].MailboxClearValue);\r
82\r
83 do {\r
84 ArmCallWFI ();\r
85\r
86 // Read the Mailbox\r
87 SecondaryEntryAddr = MmioRead32 (ArmCoreInfoTable[Index].MailboxGetAddress);\r
88\r
89 // Acknowledge the interrupt and send End of Interrupt signal.\r
90 AcknowledgeInterrupt = ArmGicAcknowledgeInterrupt (PcdGet64 (PcdGicInterruptInterfaceBase), &InterruptId);\r
91 // Check if it is a valid interrupt ID\r
92 if (InterruptId < ArmGicGetMaxNumInterrupts (PcdGet64 (PcdGicDistributorBase))) {\r
93 // Got a valid SGI number hence signal End of Interrupt\r
94 ArmGicEndOfInterrupt (PcdGet64 (PcdGicInterruptInterfaceBase), AcknowledgeInterrupt);\r
95 }\r
96 } while (SecondaryEntryAddr == 0);\r
97\r
98 // Jump to secondary core entry point.\r
99 SecondaryStart = (VOID (*)()) SecondaryEntryAddr;\r
100 SecondaryStart ();\r
101\r
102 // The secondaries shouldn't reach here\r
103 ASSERT (FALSE);\r
104}\r