diff --git a/UefiCpuPkg/CpuDxe/CpuMp.c b/UefiCpuPkg/CpuDxe/CpuMp.c index 10065762a2..e03c7f1e49 100644 --- a/UefiCpuPkg/CpuDxe/CpuMp.c +++ b/UefiCpuPkg/CpuDxe/CpuMp.c @@ -52,6 +52,7 @@ GetMpSpinLock ( while (!AcquireSpinLockOrFail (&CpuData->CpuDataLock)) { CpuPause (); } + CpuData->LockSelf = GetApicId (); } /** @@ -1144,6 +1145,13 @@ ProcessorToIdleState ( WhoAmI (&mMpServicesTemplate, &ProcessorNumber); CpuData = &mMpSystemData.CpuDatas[ProcessorNumber]; + // + // Avoid forcibly reset AP caused the AP got lock not release. + // + if (CpuData->LockSelf == (INTN) GetApicId ()) { + ReleaseSpinLock (&CpuData->CpuDataLock); + } + // // Avoid forcibly reset AP caused the AP State is not updated. // @@ -1395,6 +1403,7 @@ FillInProcessorInformation ( CpuData->Procedure = NULL; CpuData->Parameter = NULL; InitializeSpinLock (&CpuData->CpuDataLock); + CpuData->LockSelf = -1; return EFI_SUCCESS; } diff --git a/UefiCpuPkg/CpuDxe/CpuMp.h b/UefiCpuPkg/CpuDxe/CpuMp.h index 4254419a93..5c892381ef 100644 --- a/UefiCpuPkg/CpuDxe/CpuMp.h +++ b/UefiCpuPkg/CpuDxe/CpuMp.h @@ -90,6 +90,7 @@ typedef enum { typedef struct { EFI_PROCESSOR_INFORMATION Info; SPIN_LOCK CpuDataLock; + INTN LockSelf; volatile CPU_STATE State; EFI_AP_PROCEDURE Procedure;