mirror of https://github.com/acidanthera/audk.git
UefiCpuPkg MpInitLib: Save/restore original WakeupBuffer for DxeMpLib
Current code always allocates/frees < 1MB WakeupBuffer for DxeMpLib
until ExitBootService, but the allocation may be failed at late
phase of the boot.
This patch is to always save/restore original WakeupBuffer for
DxeMpLib, it is aligned with the solution for PeiMpLib at
9293d6e42e
, then AllocateResetVector()
and FreeResetVector() will be common and moved to MpLib.c.
Only difference is GetWakeupBuffer() that will be in PeiMpLib or
DxeMpLib respectively.
Cc: Liming Gao <liming.gao@intel.com>
Cc: Ruiyu Ni <ruiyu.ni@intel.com>
Cc: Eric Dong <eric.dong@intel.com>
Cc: Jeff Fan <jeff.fan@intel.com>
Contributed-under: TianoCore Contribution Agreement 1.0
Signed-off-by: Star Zeng <star.zeng@intel.com>
Reviewed-by: Liming Gao <liming.gao@intel.com>
This commit is contained in:
parent
4ad5f59715
commit
a6b3d753f9
|
@ -75,72 +75,41 @@ SaveCpuMpData (
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Allocate reset vector buffer.
|
Get available system memory below 1MB by specified size.
|
||||||
|
|
||||||
@param[in, out] CpuMpData The pointer to CPU MP Data structure.
|
@param[in] WakeupBufferSize Wakeup buffer size required
|
||||||
|
|
||||||
|
@retval other Return wakeup buffer address below 1MB.
|
||||||
|
@retval -1 Cannot find free memory below 1MB.
|
||||||
**/
|
**/
|
||||||
VOID
|
UINTN
|
||||||
AllocateResetVector (
|
GetWakeupBuffer (
|
||||||
IN OUT CPU_MP_DATA *CpuMpData
|
IN UINTN WakeupBufferSize
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
EFI_STATUS Status;
|
EFI_STATUS Status;
|
||||||
UINTN ApResetVectorSize;
|
|
||||||
EFI_PHYSICAL_ADDRESS StartAddress;
|
EFI_PHYSICAL_ADDRESS StartAddress;
|
||||||
|
|
||||||
if (CpuMpData->SaveRestoreFlag) {
|
|
||||||
BackupAndPrepareWakeupBuffer (CpuMpData);
|
|
||||||
} else {
|
|
||||||
ApResetVectorSize = CpuMpData->AddressMap.RendezvousFunnelSize +
|
|
||||||
sizeof (MP_CPU_EXCHANGE_INFO);
|
|
||||||
|
|
||||||
StartAddress = BASE_1MB;
|
StartAddress = BASE_1MB;
|
||||||
Status = gBS->AllocatePages (
|
Status = gBS->AllocatePages (
|
||||||
AllocateMaxAddress,
|
AllocateMaxAddress,
|
||||||
EfiACPIMemoryNVS,
|
EfiBootServicesData,
|
||||||
EFI_SIZE_TO_PAGES (ApResetVectorSize),
|
EFI_SIZE_TO_PAGES (WakeupBufferSize),
|
||||||
&StartAddress
|
&StartAddress
|
||||||
);
|
);
|
||||||
ASSERT_EFI_ERROR (Status);
|
ASSERT_EFI_ERROR (Status);
|
||||||
|
if (!EFI_ERROR (Status)) {
|
||||||
CpuMpData->WakeupBuffer = (UINTN) StartAddress;
|
|
||||||
CpuMpData->MpCpuExchangeInfo = (MP_CPU_EXCHANGE_INFO *) (UINTN)
|
|
||||||
(CpuMpData->WakeupBuffer + CpuMpData->AddressMap.RendezvousFunnelSize);
|
|
||||||
//
|
|
||||||
// copy AP reset code in it
|
|
||||||
//
|
|
||||||
CopyMem (
|
|
||||||
(VOID *) CpuMpData->WakeupBuffer,
|
|
||||||
(VOID *) CpuMpData->AddressMap.RendezvousFunnelAddress,
|
|
||||||
CpuMpData->AddressMap.RendezvousFunnelSize
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
Free AP reset vector buffer.
|
|
||||||
|
|
||||||
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
|
||||||
**/
|
|
||||||
VOID
|
|
||||||
FreeResetVector (
|
|
||||||
IN CPU_MP_DATA *CpuMpData
|
|
||||||
)
|
|
||||||
{
|
|
||||||
EFI_STATUS Status;
|
|
||||||
UINTN ApResetVectorSize;
|
|
||||||
|
|
||||||
if (CpuMpData->SaveRestoreFlag) {
|
|
||||||
RestoreWakeupBuffer (CpuMpData);
|
|
||||||
} else {
|
|
||||||
ApResetVectorSize = CpuMpData->AddressMap.RendezvousFunnelSize +
|
|
||||||
sizeof (MP_CPU_EXCHANGE_INFO);
|
|
||||||
Status = gBS->FreePages(
|
Status = gBS->FreePages(
|
||||||
(EFI_PHYSICAL_ADDRESS)CpuMpData->WakeupBuffer,
|
StartAddress,
|
||||||
EFI_SIZE_TO_PAGES (ApResetVectorSize)
|
EFI_SIZE_TO_PAGES (WakeupBufferSize)
|
||||||
);
|
);
|
||||||
ASSERT_EFI_ERROR (Status);
|
ASSERT_EFI_ERROR (Status);
|
||||||
|
DEBUG ((DEBUG_INFO, "WakeupBufferStart = %x, WakeupBufferSize = %x\n",
|
||||||
|
(UINTN) StartAddress, WakeupBufferSize));
|
||||||
|
} else {
|
||||||
|
StartAddress = (EFI_PHYSICAL_ADDRESS) -1;
|
||||||
}
|
}
|
||||||
|
return (UINTN) StartAddress;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -299,7 +268,6 @@ MpInitChangeApLoopCallback (
|
||||||
CPU_MP_DATA *CpuMpData;
|
CPU_MP_DATA *CpuMpData;
|
||||||
|
|
||||||
CpuMpData = GetCpuMpData ();
|
CpuMpData = GetCpuMpData ();
|
||||||
CpuMpData->SaveRestoreFlag = TRUE;
|
|
||||||
CpuMpData->PmCodeSegment = GetProtectedModeCS ();
|
CpuMpData->PmCodeSegment = GetProtectedModeCS ();
|
||||||
CpuMpData->ApLoopMode = PcdGet8 (PcdCpuApLoopMode);
|
CpuMpData->ApLoopMode = PcdGet8 (PcdCpuApLoopMode);
|
||||||
mNumberToFinish = CpuMpData->CpuCount - 1;
|
mNumberToFinish = CpuMpData->CpuCount - 1;
|
||||||
|
|
|
@ -795,6 +795,81 @@ TimedWaitForApFinish (
|
||||||
IN UINT32 TimeLimit
|
IN UINT32 TimeLimit
|
||||||
);
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
Get available system memory below 1MB by specified size.
|
||||||
|
|
||||||
|
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
||||||
|
**/
|
||||||
|
VOID
|
||||||
|
BackupAndPrepareWakeupBuffer(
|
||||||
|
IN CPU_MP_DATA *CpuMpData
|
||||||
|
)
|
||||||
|
{
|
||||||
|
CopyMem (
|
||||||
|
(VOID *) CpuMpData->BackupBuffer,
|
||||||
|
(VOID *) CpuMpData->WakeupBuffer,
|
||||||
|
CpuMpData->BackupBufferSize
|
||||||
|
);
|
||||||
|
CopyMem (
|
||||||
|
(VOID *) CpuMpData->WakeupBuffer,
|
||||||
|
(VOID *) CpuMpData->AddressMap.RendezvousFunnelAddress,
|
||||||
|
CpuMpData->AddressMap.RendezvousFunnelSize
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
Restore wakeup buffer data.
|
||||||
|
|
||||||
|
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
||||||
|
**/
|
||||||
|
VOID
|
||||||
|
RestoreWakeupBuffer(
|
||||||
|
IN CPU_MP_DATA *CpuMpData
|
||||||
|
)
|
||||||
|
{
|
||||||
|
CopyMem (
|
||||||
|
(VOID *) CpuMpData->WakeupBuffer,
|
||||||
|
(VOID *) CpuMpData->BackupBuffer,
|
||||||
|
CpuMpData->BackupBufferSize
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
Allocate reset vector buffer.
|
||||||
|
|
||||||
|
@param[in, out] CpuMpData The pointer to CPU MP Data structure.
|
||||||
|
**/
|
||||||
|
VOID
|
||||||
|
AllocateResetVector (
|
||||||
|
IN OUT CPU_MP_DATA *CpuMpData
|
||||||
|
)
|
||||||
|
{
|
||||||
|
UINTN ApResetVectorSize;
|
||||||
|
|
||||||
|
if (CpuMpData->WakeupBuffer == (UINTN) -1) {
|
||||||
|
ApResetVectorSize = CpuMpData->AddressMap.RendezvousFunnelSize +
|
||||||
|
sizeof (MP_CPU_EXCHANGE_INFO);
|
||||||
|
|
||||||
|
CpuMpData->WakeupBuffer = GetWakeupBuffer (ApResetVectorSize);
|
||||||
|
CpuMpData->MpCpuExchangeInfo = (MP_CPU_EXCHANGE_INFO *) (UINTN)
|
||||||
|
(CpuMpData->WakeupBuffer + CpuMpData->AddressMap.RendezvousFunnelSize);
|
||||||
|
}
|
||||||
|
BackupAndPrepareWakeupBuffer (CpuMpData);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
Free AP reset vector buffer.
|
||||||
|
|
||||||
|
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
||||||
|
**/
|
||||||
|
VOID
|
||||||
|
FreeResetVector (
|
||||||
|
IN CPU_MP_DATA *CpuMpData
|
||||||
|
)
|
||||||
|
{
|
||||||
|
RestoreWakeupBuffer (CpuMpData);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
This function will be called by BSP to wakeup AP.
|
This function will be called by BSP to wakeup AP.
|
||||||
|
|
||||||
|
@ -1353,7 +1428,6 @@ MpInitLibInitialize (
|
||||||
CpuMpData->CpuApStackSize = ApStackSize;
|
CpuMpData->CpuApStackSize = ApStackSize;
|
||||||
CpuMpData->BackupBuffer = BackupBufferAddr;
|
CpuMpData->BackupBuffer = BackupBufferAddr;
|
||||||
CpuMpData->BackupBufferSize = ApResetVectorSize;
|
CpuMpData->BackupBufferSize = ApResetVectorSize;
|
||||||
CpuMpData->SaveRestoreFlag = FALSE;
|
|
||||||
CpuMpData->WakeupBuffer = (UINTN) -1;
|
CpuMpData->WakeupBuffer = (UINTN) -1;
|
||||||
CpuMpData->CpuCount = 1;
|
CpuMpData->CpuCount = 1;
|
||||||
CpuMpData->BspNumber = 0;
|
CpuMpData->BspNumber = 0;
|
||||||
|
@ -2120,41 +2194,3 @@ GetCpuMpDataFromGuidedHob (
|
||||||
return CpuMpData;
|
return CpuMpData;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
Get available system memory below 1MB by specified size.
|
|
||||||
|
|
||||||
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
|
||||||
**/
|
|
||||||
VOID
|
|
||||||
BackupAndPrepareWakeupBuffer(
|
|
||||||
IN CPU_MP_DATA *CpuMpData
|
|
||||||
)
|
|
||||||
{
|
|
||||||
CopyMem (
|
|
||||||
(VOID *) CpuMpData->BackupBuffer,
|
|
||||||
(VOID *) CpuMpData->WakeupBuffer,
|
|
||||||
CpuMpData->BackupBufferSize
|
|
||||||
);
|
|
||||||
CopyMem (
|
|
||||||
(VOID *) CpuMpData->WakeupBuffer,
|
|
||||||
(VOID *) CpuMpData->AddressMap.RendezvousFunnelAddress,
|
|
||||||
CpuMpData->AddressMap.RendezvousFunnelSize
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
Restore wakeup buffer data.
|
|
||||||
|
|
||||||
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
|
||||||
**/
|
|
||||||
VOID
|
|
||||||
RestoreWakeupBuffer(
|
|
||||||
IN CPU_MP_DATA *CpuMpData
|
|
||||||
)
|
|
||||||
{
|
|
||||||
CopyMem (
|
|
||||||
(VOID *) CpuMpData->WakeupBuffer,
|
|
||||||
(VOID *) CpuMpData->BackupBuffer,
|
|
||||||
CpuMpData->BackupBufferSize
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
|
@ -201,7 +201,6 @@ struct _CPU_MP_DATA {
|
||||||
UINTN WakeupBuffer;
|
UINTN WakeupBuffer;
|
||||||
UINTN BackupBuffer;
|
UINTN BackupBuffer;
|
||||||
UINTN BackupBufferSize;
|
UINTN BackupBufferSize;
|
||||||
BOOLEAN SaveRestoreFlag;
|
|
||||||
|
|
||||||
volatile UINT32 StartCount;
|
volatile UINT32 StartCount;
|
||||||
volatile UINT32 FinishedCount;
|
volatile UINT32 FinishedCount;
|
||||||
|
@ -310,24 +309,18 @@ SaveCpuMpData (
|
||||||
IN CPU_MP_DATA *CpuMpData
|
IN CPU_MP_DATA *CpuMpData
|
||||||
);
|
);
|
||||||
|
|
||||||
/**
|
|
||||||
Allocate reset vector buffer.
|
|
||||||
|
|
||||||
@param[in, out] CpuMpData The pointer to CPU MP Data structure.
|
|
||||||
**/
|
|
||||||
VOID
|
|
||||||
AllocateResetVector (
|
|
||||||
IN OUT CPU_MP_DATA *CpuMpData
|
|
||||||
);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Free AP reset vector buffer.
|
Get available system memory below 1MB by specified size.
|
||||||
|
|
||||||
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
@param[in] WakeupBufferSize Wakeup buffer size required
|
||||||
|
|
||||||
|
@retval other Return wakeup buffer address below 1MB.
|
||||||
|
@retval -1 Cannot find free memory below 1MB.
|
||||||
**/
|
**/
|
||||||
VOID
|
UINTN
|
||||||
FreeResetVector (
|
GetWakeupBuffer (
|
||||||
IN CPU_MP_DATA *CpuMpData
|
IN UINTN WakeupBufferSize
|
||||||
);
|
);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -542,26 +535,6 @@ IsMwaitSupport (
|
||||||
VOID
|
VOID
|
||||||
);
|
);
|
||||||
|
|
||||||
/**
|
|
||||||
Get available system memory below 1MB by specified size.
|
|
||||||
|
|
||||||
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
|
||||||
**/
|
|
||||||
VOID
|
|
||||||
BackupAndPrepareWakeupBuffer(
|
|
||||||
IN CPU_MP_DATA *CpuMpData
|
|
||||||
);
|
|
||||||
|
|
||||||
/**
|
|
||||||
Restore wakeup buffer data.
|
|
||||||
|
|
||||||
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
|
||||||
**/
|
|
||||||
VOID
|
|
||||||
RestoreWakeupBuffer(
|
|
||||||
IN CPU_MP_DATA *CpuMpData
|
|
||||||
);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Enable Debug Agent to support source debugging on AP function.
|
Enable Debug Agent to support source debugging on AP function.
|
||||||
|
|
||||||
|
|
|
@ -187,42 +187,6 @@ GetWakeupBuffer (
|
||||||
return (UINTN) -1;
|
return (UINTN) -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
Allocate reset vector buffer.
|
|
||||||
|
|
||||||
@param[in, out] CpuMpData The pointer to CPU MP Data structure.
|
|
||||||
**/
|
|
||||||
VOID
|
|
||||||
AllocateResetVector (
|
|
||||||
IN OUT CPU_MP_DATA *CpuMpData
|
|
||||||
)
|
|
||||||
{
|
|
||||||
UINTN ApResetVectorSize;
|
|
||||||
|
|
||||||
if (CpuMpData->WakeupBuffer == (UINTN) -1) {
|
|
||||||
ApResetVectorSize = CpuMpData->AddressMap.RendezvousFunnelSize +
|
|
||||||
sizeof (MP_CPU_EXCHANGE_INFO);
|
|
||||||
|
|
||||||
CpuMpData->WakeupBuffer = GetWakeupBuffer (ApResetVectorSize);
|
|
||||||
CpuMpData->MpCpuExchangeInfo = (MP_CPU_EXCHANGE_INFO *) (UINTN)
|
|
||||||
(CpuMpData->WakeupBuffer + CpuMpData->AddressMap.RendezvousFunnelSize);
|
|
||||||
}
|
|
||||||
BackupAndPrepareWakeupBuffer (CpuMpData);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
Free AP reset vector buffer.
|
|
||||||
|
|
||||||
@param[in] CpuMpData The pointer to CPU MP Data structure.
|
|
||||||
**/
|
|
||||||
VOID
|
|
||||||
FreeResetVector (
|
|
||||||
IN CPU_MP_DATA *CpuMpData
|
|
||||||
)
|
|
||||||
{
|
|
||||||
RestoreWakeupBuffer (CpuMpData);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Checks APs status and updates APs status if needed.
|
Checks APs status and updates APs status if needed.
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue