mirror of https://github.com/acidanthera/audk.git
UefiCpuPkg/MpInitLib: Restore IDT context for APs.
REF: https://bugzilla.tianocore.org/show_bug.cgi?id=2683 This patch fixes an assertion because AP can't find the CpuMpData. When AP is waken up through Init-Sipi-Sipi, AP's IDT should be restored to pre-allocated buffer so AP can get the CpuMpData through the IDT base address. Current code already has logic to handle this when CpuMpData-> InitFlag is ApInitConfig but misses the logic when CpuMpData->InitFlag is ApInitReconfig. This patch fixes this gap. Reviewed-by: Ray Ni <ray.ni@intel.com> Regression-tested-by: Laszlo Ersek <lersek@redhat.com> Cc: Chandana Kumar <chandana.c.kumar@intel.com> Signed-off-by: Eric Dong <eric.dong@intel.com>
This commit is contained in:
parent
b2034179e8
commit
052aa07da4
|
@ -686,18 +686,31 @@ ApWakeupFunction (
|
||||||
WAKEUP_AP_SIGNAL,
|
WAKEUP_AP_SIGNAL,
|
||||||
0
|
0
|
||||||
);
|
);
|
||||||
if (CpuMpData->ApLoopMode == ApInHltLoop) {
|
|
||||||
|
if (CpuMpData->InitFlag == ApInitReconfig) {
|
||||||
//
|
//
|
||||||
// Restore AP's volatile registers saved
|
// ApInitReconfig happens when:
|
||||||
|
// 1. AP is re-enabled after it's disabled, in either PEI or DXE phase.
|
||||||
|
// 2. AP is initialized in DXE phase.
|
||||||
|
// In either case, use the volatile registers value derived from BSP.
|
||||||
|
// NOTE: IDTR.BASE stored in CpuMpData->CpuData[0].VolatileRegisters points to a
|
||||||
|
// different IDT shared by all APs.
|
||||||
//
|
//
|
||||||
RestoreVolatileRegisters (&CpuMpData->CpuData[ProcessorNumber].VolatileRegisters, TRUE);
|
RestoreVolatileRegisters (&CpuMpData->CpuData[0].VolatileRegisters, FALSE);
|
||||||
} else {
|
} else {
|
||||||
//
|
if (CpuMpData->ApLoopMode == ApInHltLoop) {
|
||||||
// The CPU driver might not flush TLB for APs on spot after updating
|
//
|
||||||
// page attributes. AP in mwait loop mode needs to take care of it when
|
// Restore AP's volatile registers saved before AP is halted
|
||||||
// woken up.
|
//
|
||||||
//
|
RestoreVolatileRegisters (&CpuMpData->CpuData[ProcessorNumber].VolatileRegisters, TRUE);
|
||||||
CpuFlushTlb ();
|
} else {
|
||||||
|
//
|
||||||
|
// The CPU driver might not flush TLB for APs on spot after updating
|
||||||
|
// page attributes. AP in mwait loop mode needs to take care of it when
|
||||||
|
// woken up.
|
||||||
|
//
|
||||||
|
CpuFlushTlb ();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (GetApState (&CpuMpData->CpuData[ProcessorNumber]) == CpuStateReady) {
|
if (GetApState (&CpuMpData->CpuData[ProcessorNumber]) == CpuStateReady) {
|
||||||
|
@ -1780,7 +1793,6 @@ MpInitLibInitialize (
|
||||||
InitializeSpinLock(&CpuMpData->CpuData[Index].ApLock);
|
InitializeSpinLock(&CpuMpData->CpuData[Index].ApLock);
|
||||||
CpuMpData->CpuData[Index].CpuHealthy = (CpuInfoInHob[Index].Health == 0)? TRUE:FALSE;
|
CpuMpData->CpuData[Index].CpuHealthy = (CpuInfoInHob[Index].Health == 0)? TRUE:FALSE;
|
||||||
CpuMpData->CpuData[Index].ApFunction = 0;
|
CpuMpData->CpuData[Index].ApFunction = 0;
|
||||||
CopyMem (&CpuMpData->CpuData[Index].VolatileRegisters, &VolatileRegisters, sizeof (CPU_VOLATILE_REGISTERS));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue