CPU MP Initialize Library common functions.\r
\r
Copyright (c) 2016 - 2018, Intel Corporation. All rights reserved.<BR>\r
- This program and the accompanying materials\r
- are licensed and made available under the terms and conditions of the BSD License\r
- which accompanies this distribution. The full text of the license may be found at\r
- http://opensource.org/licenses/bsd-license.php\r
-\r
- THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
- WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
+ SPDX-License-Identifier: BSD-2-Clause-Patent\r
\r
**/\r
\r
CPUID_VERSION_INFO_EDX VersionInfoEdx;\r
IA32_TSS_DESCRIPTOR *Tss;\r
\r
- AsmWriteCr0 (VolatileRegisters->Cr0);\r
AsmWriteCr3 (VolatileRegisters->Cr3);\r
AsmWriteCr4 (VolatileRegisters->Cr4);\r
+ AsmWriteCr0 (VolatileRegisters->Cr0);\r
\r
if (IsRestoreDr) {\r
AsmCpuid (CPUID_VERSION_INFO, NULL, NULL, NULL, &VersionInfoEdx.Uint32);\r
}\r
}\r
}\r
- SetApState (&CpuMpData->CpuData[ProcessorNumber], CpuStateIdle);\r
+ SetApState (&CpuMpData->CpuData[ProcessorNumber], CpuStateFinished);\r
}\r
}\r
\r
//\r
// If the AP finishes for StartupThisAP(), return EFI_SUCCESS.\r
//\r
- if (GetApState(CpuData) == CpuStateIdle) {\r
+ if (GetApState(CpuData) == CpuStateFinished) {\r
if (CpuData->Finished != NULL) {\r
*(CpuData->Finished) = TRUE;\r
}\r
+ SetApState (CpuData, CpuStateIdle);\r
return EFI_SUCCESS;\r
} else {\r
//\r
// Only BSP and corresponding AP access this unit of CPU Data. This means the AP will not modify the\r
// value of state after setting the it to CpuStateIdle, so BSP can safely make use of its value.\r
//\r
- if (GetApState(CpuData) == CpuStateIdle) {\r
+ if (GetApState(CpuData) == CpuStateFinished) {\r
CpuMpData->RunningCount --;\r
CpuMpData->CpuData[ProcessorNumber].Waiting = FALSE;\r
+ SetApState(CpuData, CpuStateIdle);\r
\r
//\r
// If in Single Thread mode, then search for the next waiting AP for execution.\r
ApLoopMode = GetApLoopMode (&MonitorFilterSize);\r
\r
//\r
- // Save BSP's Control registers for APs\r
+ // Save BSP's Control registers for APs.\r
//\r
SaveVolatileRegisters (&VolatileRegisters);\r
\r
//\r
CopyMem ((VOID *)ApIdtBase, (VOID *)VolatileRegisters.Idtr.Base, VolatileRegisters.Idtr.Limit + 1);\r
VolatileRegisters.Idtr.Base = ApIdtBase;\r
+ //\r
+ // Don't pass BSP's TR to APs to avoid AP init failure.\r
+ //\r
+ VolatileRegisters.Tr = 0;\r
CopyMem (&CpuMpData->CpuData[0].VolatileRegisters, &VolatileRegisters, sizeof (VolatileRegisters));\r
//\r
// Set BSP basic information\r
//\r
// Wait for old BSP finished AP task\r
//\r
- while (GetApState (&CpuMpData->CpuData[CallerNumber]) != CpuStateIdle) {\r
+ while (GetApState (&CpuMpData->CpuData[CallerNumber]) != CpuStateFinished) {\r
CpuPause ();\r
}\r
\r