Skip to content

Commit bbee92c

Browse files
xuweiintelmergify[bot]
authored andcommitted
UefiCpuPkg/PiSmmCpuDxeSmm: Add sync barrier before BSP invokes SmmCoreEntry
This patch introduces a synchronization point between the BSP and APs to ensure all APs have entered their SMM wait-loop (while (TRUE) in APHandler ()) before the BSP calls into the SMI handler logic via gSmmCpuPrivate ->SmmCoreEntry(). Previously, the BSP would invoke ReleaseAllAPs() and immediately proceed to SmmCoreEntry() without confirming whether APs had reached the stable waiting state. If SmmStartupThisAp() was called inside the SMI handler shortly after ReleaseAllAPs(), it might lead to a race condition: APs are issued two consecutive wait signals (SmmCpuSyncWaitForBsp()). BSP sends two consecutive releases (ReleaseAllAPs() + SmmStartupThisAp()) If an AP has not yet responded to the first release, the second release may overwrite the semaphore state, and the AP might miss the notification, causing it to hang or behave unpredictably. To address this: A SmmCpuSyncWaitForAPs() is added in BSP after mmCpuPlatformHookBeforeMmiHandler() and before entering SmmCoreEntry(). A matching SmmCpuSyncReleaseBsp() is added in AP immediately after its own SmmCpuPlatformHookBeforeMmiHandler() This ensures that BSP does not enter SMI handler logic or dispatch any AP-related requests before all APs are confirmed to be idle and ready. Debug sync point markers (e.g., /// #6, #7) are updated accordingly. This change eliminates a subtle but critical race condition in multi-processor/multi-socket systems during SMM entry and improves overall synchronization safety. Signed-off-by: Wei6 Xu <[email protected]>
1 parent 92c714f commit bbee92c

File tree

1 file changed

+32
-12
lines changed

1 file changed

+32
-12
lines changed

UefiCpuPkg/PiSmmCpuDxeSmm/MpService.c

Lines changed: 32 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -561,6 +561,11 @@ BSPHandler (
561561
// Wait for all APs to complete their MTRR programming
562562
//
563563
SmmCpuSyncWaitForAPs (mSmmMpSyncData->SyncContext, ApCount, CpuIndex); /// #5: Wait APs
564+
565+
//
566+
// Notify all APs to continue
567+
//
568+
ReleaseAllAPs (); /// #6: Signal APs
564569
}
565570
}
566571

@@ -569,6 +574,11 @@ BSPHandler (
569574
//
570575
SmmCpuPlatformHookBeforeMmiHandler ();
571576

577+
//
578+
// Wait for all APs of arrival at this point
579+
//
580+
SmmCpuSyncWaitForAPs (mSmmMpSyncData->SyncContext, ApCount, CpuIndex); /// #7: Wait APs
581+
572582
//
573583
// The BUSY lock is initialized to Acquired state
574584
//
@@ -630,18 +640,18 @@ BSPHandler (
630640
// Notify all APs to exit
631641
//
632642
*mSmmMpSyncData->InsideSmm = FALSE;
633-
ReleaseAllAPs (); /// #6: Signal APs
643+
ReleaseAllAPs (); /// #8: Signal APs
634644

635645
if (SmmCpuFeaturesNeedConfigureMtrrs ()) {
636646
//
637647
// Wait for all APs the readiness to program MTRRs
638648
//
639-
SmmCpuSyncWaitForAPs (mSmmMpSyncData->SyncContext, ApCount, CpuIndex); /// #7: Wait APs
649+
SmmCpuSyncWaitForAPs (mSmmMpSyncData->SyncContext, ApCount, CpuIndex); /// #9: Wait APs
640650

641651
//
642652
// Signal APs to restore MTRRs
643653
//
644-
ReleaseAllAPs (); /// #8: Signal APs
654+
ReleaseAllAPs (); /// #10: Signal APs
645655

646656
//
647657
// Restore OS MTRRs
@@ -654,12 +664,12 @@ BSPHandler (
654664
//
655665
// Wait for all APs to complete their pending tasks including MTRR programming if needed.
656666
//
657-
SmmCpuSyncWaitForAPs (mSmmMpSyncData->SyncContext, ApCount, CpuIndex); /// #9: Wait APs
667+
SmmCpuSyncWaitForAPs (mSmmMpSyncData->SyncContext, ApCount, CpuIndex); /// #11: Wait APs
658668

659669
//
660670
// Signal APs to Reset states/semaphore for this processor
661671
//
662-
ReleaseAllAPs (); /// #10: Signal APs
672+
ReleaseAllAPs (); /// #12: Signal APs
663673
}
664674

665675
if (mSmmDebugAgentSupport) {
@@ -684,7 +694,7 @@ BSPHandler (
684694
// Gather APs to exit SMM synchronously. Note the Present flag is cleared by now but
685695
// WaitForAllAps does not depend on the Present flag.
686696
//
687-
SmmCpuSyncWaitForAPs (mSmmMpSyncData->SyncContext, ApCount, CpuIndex); /// #11: Wait APs
697+
SmmCpuSyncWaitForAPs (mSmmMpSyncData->SyncContext, ApCount, CpuIndex); /// #13: Wait APs
688698

689699
//
690700
// At this point, all APs should have exited from APHandler().
@@ -845,18 +855,28 @@ APHandler (
845855
// Signal BSP the completion of this AP
846856
//
847857
SmmCpuSyncReleaseBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #5: Signal BSP
858+
859+
//
860+
// Wait for BSP's signal to continue
861+
//
862+
SmmCpuSyncWaitForBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #6: Wait BSP
848863
}
849864

850865
//
851866
// Perform SMM CPU Platform Hook before executing MMI Handler
852867
//
853868
SmmCpuPlatformHookBeforeMmiHandler ();
854869

870+
//
871+
// Notify BSP of arrival at this point
872+
//
873+
SmmCpuSyncReleaseBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #7: Signal BSP
874+
855875
while (TRUE) {
856876
//
857877
// Wait for something to happen
858878
//
859-
SmmCpuSyncWaitForBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #6: Wait BSP
879+
SmmCpuSyncWaitForBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #8: Wait BSP
860880

861881
//
862882
// Check if BSP wants to exit SMM
@@ -896,12 +916,12 @@ APHandler (
896916
//
897917
// Notify BSP the readiness of this AP to program MTRRs
898918
//
899-
SmmCpuSyncReleaseBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #7: Signal BSP
919+
SmmCpuSyncReleaseBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #9: Signal BSP
900920

901921
//
902922
// Wait for the signal from BSP to program MTRRs
903923
//
904-
SmmCpuSyncWaitForBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #8: Wait BSP
924+
SmmCpuSyncWaitForBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #10: Wait BSP
905925

906926
//
907927
// Restore OS MTRRs
@@ -914,12 +934,12 @@ APHandler (
914934
//
915935
// Notify BSP the readiness of this AP to Reset states/semaphore for this processor
916936
//
917-
SmmCpuSyncReleaseBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #9: Signal BSP
937+
SmmCpuSyncReleaseBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #11: Signal BSP
918938

919939
//
920940
// Wait for the signal from BSP to Reset states/semaphore for this processor
921941
//
922-
SmmCpuSyncWaitForBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #10: Wait BSP
942+
SmmCpuSyncWaitForBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #12: Wait BSP
923943
}
924944

925945
//
@@ -930,7 +950,7 @@ APHandler (
930950
//
931951
// Notify BSP the readiness of this AP to exit SMM
932952
//
933-
SmmCpuSyncReleaseBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #11: Signal BSP
953+
SmmCpuSyncReleaseBsp (mSmmMpSyncData->SyncContext, CpuIndex, BspIndex); /// #13: Signal BSP
934954
}
935955

936956
/**

0 commit comments

Comments
 (0)