/** This function will be called from AP reset code if BSP uses WakeUpAP. @param ExchangeInfo Pointer to the MP exchange info buffer @param NumApsExecuting Number of current executing AP **/ VOID EFIAPI ApCFunction ( IN MP_CPU_EXCHANGE_INFO *ExchangeInfo, IN UINTN NumApsExecuting ) { PEI_CPU_MP_DATA *PeiCpuMpData; UINTN ProcessorNumber; EFI_AP_PROCEDURE Procedure; UINTN BistData; volatile UINT32 *ApStartupSignalBuffer; PeiCpuMpData = ExchangeInfo->PeiCpuMpData; while (TRUE) { if (PeiCpuMpData->InitFlag) { ProcessorNumber = NumApsExecuting; // // Sync BSP's Control registers to APs // RestoreVolatileRegisters (&PeiCpuMpData->CpuData[0].VolatileRegisters, FALSE); // // This is first time AP wakeup, get BIST information from AP stack // BistData = *(UINTN *) (PeiCpuMpData->Buffer + ProcessorNumber * PeiCpuMpData->CpuApStackSize - sizeof (UINTN)); PeiCpuMpData->CpuData[ProcessorNumber].Health.Uint32 = (UINT32) BistData; PeiCpuMpData->CpuData[ProcessorNumber].ApicId = GetInitialApicId (); if (PeiCpuMpData->CpuData[ProcessorNumber].ApicId >= 0xFF) { // // Set x2APIC mode if there are any logical processor reporting // an APIC ID of 255 or greater. // AcquireSpinLock(&PeiCpuMpData->MpLock); PeiCpuMpData->X2ApicEnable = TRUE; ReleaseSpinLock(&PeiCpuMpData->MpLock); } // // Sync BSP's Mtrr table to all wakeup APs and load microcode on APs. // MtrrSetAllMtrrs (&PeiCpuMpData->MtrrTable); MicrocodeDetect (); PeiCpuMpData->CpuData[ProcessorNumber].State = CpuStateIdle; } else { // // Execute AP function if AP is not disabled // GetProcessorNumber (PeiCpuMpData, &ProcessorNumber); if (PeiCpuMpData->ApLoopMode == ApInHltLoop) { // // Restore AP's volatile registers saved // RestoreVolatileRegisters (&PeiCpuMpData->CpuData[ProcessorNumber].VolatileRegisters, TRUE); } if ((PeiCpuMpData->CpuData[ProcessorNumber].State != CpuStateDisabled) && (PeiCpuMpData->ApFunction != 0)) { PeiCpuMpData->CpuData[ProcessorNumber].State = CpuStateBusy; Procedure = (EFI_AP_PROCEDURE)(UINTN)PeiCpuMpData->ApFunction; // // Invoke AP function here // Procedure ((VOID *)(UINTN)PeiCpuMpData->ApFunctionArgument); // // Re-get the processor number due to BSP/AP maybe exchange in AP function // GetProcessorNumber (PeiCpuMpData, &ProcessorNumber); PeiCpuMpData->CpuData[ProcessorNumber].State = CpuStateIdle; } } // // AP finished executing C code // InterlockedIncrement ((UINT32 *)&PeiCpuMpData->FinishedCount); // // Place AP is specified loop mode // if (PeiCpuMpData->ApLoopMode == ApInHltLoop) { // // Save AP volatile registers // SaveVolatileRegisters (&PeiCpuMpData->CpuData[ProcessorNumber].VolatileRegisters); // // Place AP in Hlt-loop // while (TRUE) { DisableInterrupts (); CpuSleep (); CpuPause (); } } ApStartupSignalBuffer = PeiCpuMpData->CpuData[ProcessorNumber].StartupApSignal; // // Clear AP start-up signal // *ApStartupSignalBuffer = 0; while (TRUE) { DisableInterrupts (); if (PeiCpuMpData->ApLoopMode == ApInMwaitLoop) { // // Place AP in Mwait-loop // AsmMonitor ((UINTN)ApStartupSignalBuffer, 0, 0); if (*ApStartupSignalBuffer != WAKEUP_AP_SIGNAL) { // // If AP start-up signal is not set, place AP into // the maximum C-state // AsmMwait (PeiCpuMpData->ApTargetCState << 4, 0); } } else if (PeiCpuMpData->ApLoopMode == ApInRunLoop) { // // Place AP in Run-loop // CpuPause (); } else { ASSERT (FALSE); } // // If AP start-up signal is written, AP is waken up // otherwise place AP in loop again // if (*ApStartupSignalBuffer == WAKEUP_AP_SIGNAL) { break; } } } }
/** Common exception handler. @param InterruptType Exception type @param SystemContext EFI_SYSTEM_CONTEXT **/ VOID EFIAPI CommonExceptionHandler ( IN EFI_EXCEPTION_TYPE InterruptType, IN EFI_SYSTEM_CONTEXT SystemContext ) { #if defined (MDE_CPU_IA32) DEBUG (( EFI_D_ERROR, "!!!! IA32 Exception Type - %08x !!!!\n", InterruptType )); if ((mErrorCodeFlag & (1 << InterruptType)) != 0) { DEBUG (( EFI_D_ERROR, "ExceptionData - %08x\n", SystemContext.SystemContextIa32->ExceptionData )); } DEBUG (( EFI_D_ERROR, "CS - %04x, EIP - %08x, EFL - %08x, SS - %04x\n", SystemContext.SystemContextIa32->Cs, SystemContext.SystemContextIa32->Eip, SystemContext.SystemContextIa32->Eflags, SystemContext.SystemContextIa32->Ss )); DEBUG (( EFI_D_ERROR, "DS - %04x, ES - %04x, FS - %04x, GS - %04x\n", SystemContext.SystemContextIa32->Ds, SystemContext.SystemContextIa32->Es, SystemContext.SystemContextIa32->Fs, SystemContext.SystemContextIa32->Gs )); DEBUG (( EFI_D_ERROR, "EAX - %08x, EBX - %08x, ECX - %08x, EDX - %08x\n", SystemContext.SystemContextIa32->Eax, SystemContext.SystemContextIa32->Ebx, SystemContext.SystemContextIa32->Ecx, SystemContext.SystemContextIa32->Edx )); DEBUG (( EFI_D_ERROR, "ESP - %08x, EBP - %08x, ESI - %08x, EDI - %08x\n", SystemContext.SystemContextIa32->Esp, SystemContext.SystemContextIa32->Ebp, SystemContext.SystemContextIa32->Esi, SystemContext.SystemContextIa32->Edi )); DEBUG (( EFI_D_ERROR, "GDT - %08x LIM - %04x, IDT - %08x LIM - %04x\n", SystemContext.SystemContextIa32->Gdtr[0], SystemContext.SystemContextIa32->Gdtr[1], SystemContext.SystemContextIa32->Idtr[0], SystemContext.SystemContextIa32->Idtr[1] )); DEBUG (( EFI_D_ERROR, "LDT - %08x, TR - %08x\n", SystemContext.SystemContextIa32->Ldtr, SystemContext.SystemContextIa32->Tr )); DEBUG (( EFI_D_ERROR, "CR0 - %08x, CR2 - %08x, CR3 - %08x, CR4 - %08x\n", SystemContext.SystemContextIa32->Cr0, SystemContext.SystemContextIa32->Cr2, SystemContext.SystemContextIa32->Cr3, SystemContext.SystemContextIa32->Cr4 )); DEBUG (( EFI_D_ERROR, "DR0 - %08x, DR1 - %08x, DR2 - %08x, DR3 - %08x\n", SystemContext.SystemContextIa32->Dr0, SystemContext.SystemContextIa32->Dr1, SystemContext.SystemContextIa32->Dr2, SystemContext.SystemContextIa32->Dr3 )); DEBUG (( EFI_D_ERROR, "DR6 - %08x, DR7 - %08x\n", SystemContext.SystemContextIa32->Dr6, SystemContext.SystemContextIa32->Dr7 )); #elif defined (MDE_CPU_X64) DEBUG (( EFI_D_ERROR, "!!!! X64 Exception Type - %016lx !!!!\n", (UINT64)InterruptType )); if ((mErrorCodeFlag & (1 << InterruptType)) != 0) { DEBUG (( EFI_D_ERROR, "ExceptionData - %016lx\n", SystemContext.SystemContextX64->ExceptionData )); } DEBUG (( EFI_D_ERROR, "RIP - %016lx, RFL - %016lx\n", SystemContext.SystemContextX64->Rip, SystemContext.SystemContextX64->Rflags )); DEBUG (( EFI_D_ERROR, "RAX - %016lx, RCX - %016lx, RDX - %016lx\n", SystemContext.SystemContextX64->Rax, SystemContext.SystemContextX64->Rcx, SystemContext.SystemContextX64->Rdx )); DEBUG (( EFI_D_ERROR, "RBX - %016lx, RSP - %016lx, RBP - %016lx\n", SystemContext.SystemContextX64->Rbx, SystemContext.SystemContextX64->Rsp, SystemContext.SystemContextX64->Rbp )); DEBUG (( EFI_D_ERROR, "RSI - %016lx, RDI - %016lx\n", SystemContext.SystemContextX64->Rsi, SystemContext.SystemContextX64->Rdi )); DEBUG (( EFI_D_ERROR, "R8 - %016lx, R9 - %016lx, R10 - %016lx\n", SystemContext.SystemContextX64->R8, SystemContext.SystemContextX64->R9, SystemContext.SystemContextX64->R10 )); DEBUG (( EFI_D_ERROR, "R11 - %016lx, R12 - %016lx, R13 - %016lx\n", SystemContext.SystemContextX64->R11, SystemContext.SystemContextX64->R12, SystemContext.SystemContextX64->R13 )); DEBUG (( EFI_D_ERROR, "R14 - %016lx, R15 - %016lx\n", SystemContext.SystemContextX64->R14, SystemContext.SystemContextX64->R15 )); DEBUG (( EFI_D_ERROR, "CS - %04lx, DS - %04lx, ES - %04lx, FS - %04lx, GS - %04lx, SS - %04lx\n", SystemContext.SystemContextX64->Cs, SystemContext.SystemContextX64->Ds, SystemContext.SystemContextX64->Es, SystemContext.SystemContextX64->Fs, SystemContext.SystemContextX64->Gs, SystemContext.SystemContextX64->Ss )); DEBUG (( EFI_D_ERROR, "GDT - %016lx; %04lx, IDT - %016lx; %04lx\n", SystemContext.SystemContextX64->Gdtr[0], SystemContext.SystemContextX64->Gdtr[1], SystemContext.SystemContextX64->Idtr[0], SystemContext.SystemContextX64->Idtr[1] )); DEBUG (( EFI_D_ERROR, "LDT - %016lx, TR - %016lx\n", SystemContext.SystemContextX64->Ldtr, SystemContext.SystemContextX64->Tr )); DEBUG (( EFI_D_ERROR, "CR0 - %016lx, CR2 - %016lx, CR3 - %016lx\n", SystemContext.SystemContextX64->Cr0, SystemContext.SystemContextX64->Cr2, SystemContext.SystemContextX64->Cr3 )); DEBUG (( EFI_D_ERROR, "CR4 - %016lx, CR8 - %016lx\n", SystemContext.SystemContextX64->Cr4, SystemContext.SystemContextX64->Cr8 )); DEBUG (( EFI_D_ERROR, "DR0 - %016lx, DR1 - %016lx, DR2 - %016lx\n", SystemContext.SystemContextX64->Dr0, SystemContext.SystemContextX64->Dr1, SystemContext.SystemContextX64->Dr2 )); DEBUG (( EFI_D_ERROR, "DR3 - %016lx, DR6 - %016lx, DR7 - %016lx\n", SystemContext.SystemContextX64->Dr3, SystemContext.SystemContextX64->Dr6, SystemContext.SystemContextX64->Dr7 )); #else #error CPU type not supported for exception information dump! #endif // // Hang the system with CpuSleep so the processor will enter a lower power // state. // while (TRUE) { CpuSleep (); }; }