From 8cc26df4a60ec3a3b7f9d58ccefc12a1a5b6e199 Mon Sep 17 00:00:00 2001 From: Jeff Fan Date: Fri, 22 Nov 2013 06:30:01 +0000 Subject: [PATCH] 1. DebugAgentLib will install reserved vector table to persist vectors. 2. Update PeCoffExtraActionLib to detect if debug agent initialized or not by checking each IDT entry instead of whole IDT table. Signed-off-by: Jeff Fan Reviewed-by: Ruiyu Ni git-svn-id: https://svn.code.sf.net/p/edk2/code/trunk/edk2@14886 6f19259b-4bc3-4df7-8a09-765794883524 --- .../DebugAgent/DebugAgentCommon/DebugAgent.c | 108 ++++++++++++++++++ .../DebugAgent/DebugAgentCommon/DebugAgent.h | 12 +- .../DebugAgentCommon/Ia32/AsmFuncs.S | 27 ++++- .../DebugAgentCommon/Ia32/AsmFuncs.asm | 27 ++++- .../DebugAgentCommon/X64/AsmFuncs.S | 27 ++++- .../DebugAgentCommon/X64/AsmFuncs.asm | 27 ++++- .../DxeDebugAgent/DxeDebugAgentLib.c | 45 +++++++- .../Library/DebugAgent/DxeDebugAgentLib.inf | 6 +- .../SecPeiDebugAgent/SecPeiDebugAgentLib.c | 43 ++++++- .../DebugAgent/SecPeiDebugAgentLib.inf | 1 + .../SmmDebugAgent/SmmDebugAgentLib.c | 15 ++- .../SmmDebugAgent/SmmDebugAgentLib.h | 3 +- .../Library/DebugAgent/SmmDebugAgentLib.inf | 2 + .../Ia32/IntHandlerFuncs.c | 9 +- .../PeCoffExtraActionLib.c | 17 +-- .../PeCoffExtraActionLib.h | 7 +- .../X64/IntHandlerFuncs.c | 11 +- 17 files changed, 350 insertions(+), 37 deletions(-) diff --git a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/DebugAgent.c b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/DebugAgent.c index 01711ff085..239cf63f6b 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/DebugAgent.c +++ b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/DebugAgent.c @@ -24,6 +24,114 @@ CHAR8 mErrorMsgConnectOK[] = "HOST connection is successful!\r\n"; CHAR8 mErrorMsgConnectFail[] = "HOST connection is failed!\r\n"; CHAR8 mWarningMsgIngoreBreakpoint[] = "Ignore break point in SMM for SMI issued during DXE debugging!\r\n"; +// +// Vector Handoff Info list used by Debug Agent for persist +// +EFI_VECTOR_HANDOFF_INFO mVectorHandoffInfoDebugAgent[] = { + { + DEBUG_EXCEPT_DIVIDE_ERROR, // Vector 0 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_DEBUG, // Vector 1 + EFI_VECTOR_HANDOFF_DO_NOT_HOOK, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_NMI, // Vector 2 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_BREAKPOINT, // Vector 3 + EFI_VECTOR_HANDOFF_DO_NOT_HOOK, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_OVERFLOW, // Vector 4 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_BOUND, // Vector 5 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_INVALID_OPCODE, // Vector 6 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_DOUBLE_FAULT, // Vector 8 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_INVALID_TSS, // Vector 10 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_SEG_NOT_PRESENT, // Vector 11 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_STACK_FAULT, // Vector 12 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_GP_FAULT, // Vector 13 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_PAGE_FAULT, // Vector 14 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_FP_ERROR, // Vector 16 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_ALIGNMENT_CHECK, // Vector 17 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_MACHINE_CHECK, // Vector 18 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_EXCEPT_SIMD, // Vector 19 + EFI_VECTOR_HANDOFF_HOOK_BEFORE, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_TIMER_VECTOR, // Vector 32 + EFI_VECTOR_HANDOFF_DO_NOT_HOOK, + EFI_DEBUG_AGENT_GUID + }, + { + DEBUG_MAILBOX_VECTOR, // Vector 33 + EFI_VECTOR_HANDOFF_DO_NOT_HOOK, + EFI_DEBUG_AGENT_GUID + }, + { + 0, + EFI_VECTOR_HANDOFF_LAST_ENTRY, + { 0 } + } +}; + +UINTN mVectorHandoffInfoCount = sizeof (mVectorHandoffInfoDebugAgent) / sizeof (EFI_VECTOR_HANDOFF_INFO); + /** Calculate CRC16 for target data. diff --git a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/DebugAgent.h b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/DebugAgent.h index 748d562a59..deed55eafb 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/DebugAgent.h +++ b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/DebugAgent.h @@ -16,9 +16,9 @@ #define _DEBUG_AGENT_H_ #include - #include - +#include +#include #include #include #include @@ -41,6 +41,7 @@ #include "DebugMp.h" #include "DebugTimer.h" #include "ArchDebugSupport.h" +#include "DebugException.h" // // These macros may be already defined in DebugAgentLib.h @@ -50,8 +51,8 @@ #define DEBUG_AGENT_INIT_DXE_UNLOAD 11 #define DEBUG_AGENT_INIT_THUNK_PEI_IA32TOX64 12 -#define DEBUG_INT1_VECTOR 1 -#define DEBUG_INT3_VECTOR 3 +#define DEBUG_INT1_VECTOR DEBUG_EXCEPT_DEBUG +#define DEBUG_INT3_VECTOR DEBUG_EXCEPT_BREAKPOINT #define DEBUG_TIMER_VECTOR 32 #define DEBUG_MAILBOX_VECTOR 33 @@ -67,8 +68,9 @@ extern UINTN Exception0Handle; extern UINTN TimerInterruptHandle; extern UINT16 ExceptionStubHeaderSize; - extern BOOLEAN mSkipBreakpoint; +extern EFI_VECTOR_HANDOFF_INFO mVectorHandoffInfoDebugAgent[]; +extern UINTN mVectorHandoffInfoCount; // // CPU exception information issued by debug agent diff --git a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/Ia32/AsmFuncs.S b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/Ia32/AsmFuncs.S index e05317aaf8..284939126f 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/Ia32/AsmFuncs.S +++ b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/Ia32/AsmFuncs.S @@ -27,114 +27,137 @@ ASM_GLOBAL ASM_PFX(ExceptionStubHeaderSize) ASM_GLOBAL ASM_PFX(TimerInterruptHandle) ASM_GLOBAL ASM_PFX(CommonEntry) +.macro AGENT_HANDLER_SIGNATURE + .byte 0x41, 0x47, 0x54, 0x48 # AGENT_HANDLER_SIGNATURE SIGNATURE_32('A','G','T','H') +.endm + .data ASM_PFX(ExceptionStubHeaderSize): .word ASM_PFX(Exception1Handle) - ASM_PFX(Exception0Handle) .text -.byte 0x41, 0x47, 0x54, 0x48 # AGENT_HANDLER_SIGNATURE SIGNATURE_32('A','G','T','H') +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception0Handle): cli pushl %eax mov $0, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception1Handle): cli pushl %eax mov $1, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception2Handle): cli pushl %eax mov $2, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception3Handle): cli pushl %eax mov $3, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception4Handle): cli pushl %eax mov $4, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception5Handle): cli pushl %eax mov $5, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception6Handle): cli pushl %eax mov $6, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception7Handle): cli pushl %eax mov $7, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception8Handle): cli pushl %eax mov $8, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception9Handle): cli pushl %eax mov $9, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception10Handle): cli pushl %eax mov $10, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception11Handle): cli pushl %eax mov $11, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception12Handle): cli pushl %eax mov $12, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception13Handle): cli pushl %eax mov $13, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception14Handle): cli pushl %eax mov $14, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception15Handle): cli pushl %eax mov $15, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception16Handle): cli pushl %eax mov $16, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception17Handle): cli pushl %eax mov $17, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception18Handle): cli pushl %eax mov $18, %eax jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception19Handle): cli pushl %eax mov $19, %eax jmp ASM_PFX(CommonEntry) - +AGENT_HANDLER_SIGNATURE ASM_PFX(TimerInterruptHandle): cli pushl %eax diff --git a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/Ia32/AsmFuncs.asm b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/Ia32/AsmFuncs.asm index c80a33ba6c..9b219fc07d 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/Ia32/AsmFuncs.asm +++ b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/Ia32/AsmFuncs.asm @@ -32,6 +32,10 @@ InterruptProcess PROTO C public Exception0Handle, TimerInterruptHandle, ExceptionStubHeaderSize +AGENT_HANDLER_SIGNATURE MACRO + db 41h, 47h, 54h, 48h ; SIGNATURE_32('A','G','T','H') +ENDM + .data ExceptionStubHeaderSize DW Exception1Handle - Exception0Handle @@ -39,108 +43,127 @@ CommonEntryAddr DD CommonEntry .code -db 41h, 47h, 54h, 48h ; AGENT_HANDLER_SIGNATURE SIGNATURE_32('A','G','T','H') +AGENT_HANDLER_SIGNATURE Exception0Handle: cli push eax mov eax, 0 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception1Handle: cli push eax mov eax, 1 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception2Handle: cli push eax mov eax, 2 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception3Handle: cli push eax mov eax, 3 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception4Handle: cli push eax mov eax, 4 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception5Handle: cli push eax mov eax, 5 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception6Handle: cli push eax mov eax, 6 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception7Handle: cli push eax mov eax, 7 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception8Handle: cli push eax mov eax, 8 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception9Handle: cli push eax mov eax, 9 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception10Handle: cli push eax mov eax, 10 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception11Handle: cli push eax mov eax, 11 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception12Handle: cli push eax mov eax, 12 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception13Handle: cli push eax mov eax, 13 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception14Handle: cli push eax mov eax, 14 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception15Handle: cli push eax mov eax, 15 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception16Handle: cli push eax mov eax, 16 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception17Handle: cli push eax mov eax, 17 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception18Handle: cli push eax mov eax, 18 jmp dword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception19Handle: cli push eax mov eax, 19 jmp dword ptr [CommonEntryAddr] - +AGENT_HANDLER_SIGNATURE TimerInterruptHandle: cli push eax diff --git a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/X64/AsmFuncs.S b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/X64/AsmFuncs.S index e7c3ed7464..b742b67dba 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/X64/AsmFuncs.S +++ b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/X64/AsmFuncs.S @@ -28,6 +28,10 @@ ASM_GLOBAL ASM_PFX(ExceptionStubHeaderSize) ASM_GLOBAL ASM_PFX(TimerInterruptHandle) ASM_GLOBAL ASM_PFX(CommonEntry) +.macro AGENT_HANDLER_SIGNATURE + .byte 0x41, 0x47, 0x54, 0x48 # AGENT_HANDLER_SIGNATURE SIGNATURE_32('A','G','T','H') +.endm + .data ASM_PFX(ExceptionStubHeaderSize): .word ASM_PFX(Exception1Handle) - ASM_PFX(Exception0Handle) @@ -35,108 +39,127 @@ ASM_PFX(ExceptionStubHeaderSize): .word ASM_PFX(Exception1Handle) - ASM_PFX .text -.byte 0x41, 0x47, 0x54, 0x48 # AGENT_HANDLER_SIGNATURE SIGNATURE_32('A','G','T','H') +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception0Handle): cli pushq %rcx mov $0, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception1Handle): cli pushq %rcx mov $1, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception2Handle): cli pushq %rcx mov $2, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception3Handle): cli pushq %rcx mov $3, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception4Handle): cli pushq %rcx mov $4, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception5Handle): cli pushq %rcx mov $5, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception6Handle): cli pushq %rcx mov $6, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception7Handle): cli pushq %rcx mov $7, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception8Handle): cli pushq %rcx mov $8, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception9Handle): cli pushq %rcx mov $9, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception10Handle): cli pushq %rcx mov $10, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception11Handle): cli pushq %rcx mov $11, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception12Handle): cli pushq %rcx mov $12, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception13Handle): cli pushq %rcx mov $13, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception14Handle): cli pushq %rcx mov $14, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception15Handle): cli pushq %rcx mov $15, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception16Handle): cli pushq %rcx mov $16, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception17Handle): cli pushq %rcx mov $17, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception18Handle): cli pushq %rcx mov $18, %rcx jmp ASM_PFX(CommonEntry) +AGENT_HANDLER_SIGNATURE ASM_PFX(Exception19Handle): cli pushq %rcx mov $19, %rcx jmp ASM_PFX(CommonEntry) - +AGENT_HANDLER_SIGNATURE ASM_PFX(TimerInterruptHandle): cli pushq %rcx diff --git a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/X64/AsmFuncs.asm b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/X64/AsmFuncs.asm index 23abcc7621..cf8c5f0194 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/X64/AsmFuncs.asm +++ b/SourceLevelDebugPkg/Library/DebugAgent/DebugAgentCommon/X64/AsmFuncs.asm @@ -28,113 +28,136 @@ data SEGMENT public Exception0Handle, TimerInterruptHandle, ExceptionStubHeaderSize +AGENT_HANDLER_SIGNATURE MACRO + db 41h, 47h, 54h, 48h ; SIGNATURE_32('A','G','T','H') +ENDM + ExceptionStubHeaderSize dw Exception1Handle - Exception0Handle ; CommonEntryAddr dq CommonEntry ; .code -db 41h, 47h, 54h, 48h ; AGENT_HANDLER_SIGNATURE SIGNATURE_32('A','G','T','H') +AGENT_HANDLER_SIGNATURE Exception0Handle: cli push rcx mov rcx, 0 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception1Handle: cli push rcx mov rcx, 1 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception2Handle: cli push rcx mov rcx, 2 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception3Handle: cli push rcx mov rcx, 3 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception4Handle: cli push rcx mov rcx, 4 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception5Handle: cli push rcx mov rcx, 5 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception6Handle: cli push rcx mov rcx, 6 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception7Handle: cli push rcx mov rcx, 7 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception8Handle: cli push rcx mov rcx, 8 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception9Handle: cli push rcx mov rcx, 9 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception10Handle: cli push rcx mov rcx, 10 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception11Handle: cli push rcx mov rcx, 11 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception12Handle: cli push rcx mov rcx, 12 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception13Handle: cli push rcx mov rcx, 13 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception14Handle: cli push rcx mov rcx, 14 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception15Handle: cli push rcx mov rcx, 15 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception16Handle: cli push rcx mov rcx, 16 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception17Handle: cli push rcx mov rcx, 17 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception18Handle: cli push rcx mov rcx, 18 jmp qword ptr [CommonEntryAddr] +AGENT_HANDLER_SIGNATURE Exception19Handle: cli push rcx mov rcx, 19 jmp qword ptr [CommonEntryAddr] - +AGENT_HANDLER_SIGNATURE TimerInterruptHandle: cli push rcx diff --git a/SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgent/DxeDebugAgentLib.c b/SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgent/DxeDebugAgentLib.c index d560b52359..71130d8aaa 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgent/DxeDebugAgentLib.c +++ b/SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgent/DxeDebugAgentLib.c @@ -57,6 +57,32 @@ InternalConstructorWorker ( BOOLEAN DebugTimerInterruptState; DEBUG_AGENT_MAILBOX *Mailbox; DEBUG_AGENT_MAILBOX *NewMailbox; + EFI_HOB_GUID_TYPE *GuidHob; + EFI_VECTOR_HANDOFF_INFO *VectorHandoffInfo; + + // + // Check persisted vector handoff info + // + Status = EFI_SUCCESS; + GuidHob = GetFirstGuidHob (&gEfiVectorHandoffInfoPpiGuid); + if (GuidHob != NULL && !mDxeCoreFlag) { + // + // Check if configuration table is installed or not if GUIDed HOB existed, + // only when Debug Agent is not linked by DXE Core + // + Status = EfiGetSystemConfigurationTable (&gEfiVectorHandoffTableGuid, (VOID **) &VectorHandoffInfo); + } + if (GuidHob == NULL || Status != EFI_SUCCESS) { + // + // Install configuration table for persisted vector handoff info if GUIDed HOB cannot be found or + // configuration table does not exist + // + Status = gBS->InstallConfigurationTable (&gEfiVectorHandoffTableGuid, (VOID *) &mVectorHandoffInfoDebugAgent[0]); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "DebugAgent: Cannot install configuration table for persisted vector handoff info!\n")); + CpuDeadLoop (); + } + } // // Install EFI Serial IO protocol on debug port @@ -70,7 +96,10 @@ InternalConstructorWorker ( EFI_SIZE_TO_PAGES (sizeof(DEBUG_AGENT_MAILBOX) + PcdGet16(PcdDebugPortHandleBufferSize)), &Address ); - ASSERT_EFI_ERROR (Status); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "DebugAgent: Cannot install configuration table for mailbox!\n")); + CpuDeadLoop (); + } DebugTimerInterruptState = SaveAndSetDebugTimerInterrupt (FALSE); @@ -91,7 +120,10 @@ InternalConstructorWorker ( DebugTimerInterruptState = SaveAndSetDebugTimerInterrupt (DebugTimerInterruptState); Status = gBS->InstallConfigurationTable (&gEfiDebugAgentGuid, (VOID *) mMailboxPointer); - ASSERT_EFI_ERROR (Status); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "DebugAgent: Failed to install configuration for mailbox!\n")); + CpuDeadLoop (); + } } /** @@ -233,9 +265,16 @@ SetupDebugAgentEnviroment ( AsmReadIdtr ((IA32_DESCRIPTOR *) &Idtr); IdtEntryCount = (UINT16) ((Idtr.Limit + 1) / sizeof (IA32_IDT_GATE_DESCRIPTOR)); if (IdtEntryCount < 33) { + ZeroMem (&mIdtEntryTable, sizeof (IA32_IDT_GATE_DESCRIPTOR) * 33); + // + // Copy original IDT table into new one + // + CopyMem (&mIdtEntryTable, (VOID *) Idtr.Base, Idtr.Limit + 1); + // + // Load new IDT table + // Idtr.Limit = (UINT16) (sizeof (IA32_IDT_GATE_DESCRIPTOR) * 33 - 1); Idtr.Base = (UINTN) &mIdtEntryTable; - ZeroMem (&mIdtEntryTable, Idtr.Limit + 1); AsmWriteIdtr ((IA32_DESCRIPTOR *) &Idtr); } diff --git a/SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf b/SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf index cc9b48191d..e5a510d4b3 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf +++ b/SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf @@ -82,7 +82,11 @@ [Guids] gEfiDebugAgentGuid ## PRODUCES ## Configuration Table gEfiDebugAgentGuid ## CONSUMES ## HOB - + gEfiVectorHandoffTableGuid ## SOMETIMES_PRODUCES ## Configuration Table + +[Ppis] + gEfiVectorHandoffInfoPpiGuid ## UNDEFINED + [Protocols] gEfiSerialIoProtocolGuid ## PRODUCES gEfiDevicePathProtocolGuid ## PRODUCES diff --git a/SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgent/SecPeiDebugAgentLib.c b/SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgent/SecPeiDebugAgentLib.c index d036880c1d..0388807697 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgent/SecPeiDebugAgentLib.c +++ b/SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgent/SecPeiDebugAgentLib.c @@ -16,6 +16,22 @@ BOOLEAN mSkipBreakpoint = FALSE; + +EFI_PEI_VECTOR_HANDOFF_INFO_PPI mVectorHandoffInfoPpi = { + &mVectorHandoffInfoDebugAgent[0] +}; + +// +// Ppis to be installed +// +EFI_PEI_PPI_DESCRIPTOR mVectorHandoffInfoPpiList[] = { + { + (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST), + &gEfiVectorHandoffInfoPpiGuid, + &mVectorHandoffInfoPpi + } +}; + EFI_PEI_NOTIFY_DESCRIPTOR mMemoryDiscoveredNotifyList[1] = { { (EFI_PEI_PPI_DESCRIPTOR_NOTIFY_CALLBACK | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST), @@ -408,7 +424,14 @@ InitializeDebugAgent ( // TriggerSoftInterrupt (MEMORY_READY_SIGNATURE); } - + // + // Install Vector Handoff Info PPI to persist vectors used by Debug Agent + // + Status = PeiServicesInstallPpi (&mVectorHandoffInfoPpiList[0]); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "DebugAgent: Failed to install Vector Handoff Info PPI!\n")); + CpuDeadLoop (); + } // // Fix up Debug Port handle address and mailbox address // @@ -437,7 +460,10 @@ InitializeDebugAgent ( EFI_SIZE_TO_PAGES (sizeof(DEBUG_AGENT_MAILBOX) + PcdGet16(PcdDebugPortHandleBufferSize)), &Address ); - ASSERT_EFI_ERROR (Status); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "DebugAgent: Failed to allocate pages!\n")); + CpuDeadLoop (); + } NewMailbox = (DEBUG_AGENT_MAILBOX *) (UINTN) Address; // // Copy Mailbox and Debug Port Handle buffer to new location in ACPI NVS memory, because original Mailbox @@ -477,6 +503,14 @@ InitializeDebugAgent ( break; } // + // Install Vector Handoff Info PPI to persist vectors used by Debug Agent + // + Status = PeiServicesInstallPpi (&mVectorHandoffInfoPpiList[0]); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "DebugAgent: Failed to install Vector Handoff Info PPI!\n")); + CpuDeadLoop (); + } + // // Set up IDT entries // InitializeDebugIdt (); @@ -505,7 +539,10 @@ InitializeDebugAgent ( // If memery has been ready, the callback funtion will be invoked immediately // Status = PeiServicesNotifyPpi (&mMemoryDiscoveredNotifyList[0]); - ASSERT_EFI_ERROR (Status); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "DebugAgent: Failed to register memory discovered callback function!\n")); + CpuDeadLoop (); + } // // Set HOB check flag if memory has not been ready yet // diff --git a/SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgentLib.inf b/SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgentLib.inf index b81fc16d17..5204abca52 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgentLib.inf +++ b/SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgentLib.inf @@ -77,6 +77,7 @@ [Ppis] gEfiPeiMemoryDiscoveredPpiGuid + gEfiVectorHandoffInfoPpiGuid ## PRODUCES [Guids] gEfiDebugAgentGuid ## PRODUCES ## HOB diff --git a/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgent/SmmDebugAgentLib.c b/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgent/SmmDebugAgentLib.c index 145fee0fa5..651737e5e7 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgent/SmmDebugAgentLib.c +++ b/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgent/SmmDebugAgentLib.c @@ -192,6 +192,19 @@ InitializeDebugAgent ( switch (InitFlag) { case DEBUG_AGENT_INIT_SMM: + // + // Install configuration table for persisted vector handoff info + // + Status = gSmst->SmmInstallConfigurationTable ( + gSmst, + &gEfiVectorHandoffTableGuid, + (VOID *) &mVectorHandoffInfoDebugAgent[0], + sizeof (EFI_VECTOR_HANDOFF_INFO) * mVectorHandoffInfoCount + ); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "DebugAgent: Cannot install configuration table for persisted vector handoff info!\n")); + CpuDeadLoop (); + } // // Check if Debug Agent initialized in DXE phase // @@ -210,7 +223,7 @@ InitializeDebugAgent ( break; } // - // Debug Agent was not initialized before, uset the local mailbox. + // Debug Agent was not initialized before, use the local mailbox. // ZeroMem (&mLocalMailbox, sizeof (DEBUG_AGENT_MAILBOX)); Mailbox = &mLocalMailbox; diff --git a/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgent/SmmDebugAgentLib.h b/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgent/SmmDebugAgentLib.h index ccb55f830d..f30a892e21 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgent/SmmDebugAgentLib.h +++ b/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgent/SmmDebugAgentLib.h @@ -1,7 +1,7 @@ /** @file Header file for Smm Debug Agent Library instance. - Copyright (c) 2010, Intel Corporation. All rights reserved.
+ Copyright (c) 2010 - 2013, Intel Corporation. All rights reserved.
This program and the accompanying materials are licensed and made available under the terms and conditions of the BSD License which accompanies this distribution. The full text of the license may be found at @@ -18,6 +18,7 @@ #include #include +#include #include "DebugAgent.h" diff --git a/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgentLib.inf b/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgentLib.inf index 9ed314d407..2878c3189f 100644 --- a/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgentLib.inf +++ b/SourceLevelDebugPkg/Library/DebugAgent/SmmDebugAgentLib.inf @@ -71,9 +71,11 @@ PrintLib PeCoffExtraActionLib PeCoffGetEntryPointLib + SmmServicesTableLib [Guids] gEfiDebugAgentGuid ## CONSUMES ## Configuration Table + gEfiVectorHandoffTableGuid ## SOMETIMES_PRODUCES ## Configuration Table [Pcd] gEfiMdePkgTokenSpaceGuid.PcdFSBClock ## CONSUMES diff --git a/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/Ia32/IntHandlerFuncs.c b/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/Ia32/IntHandlerFuncs.c index b2d4c37a9d..ccf3fb1842 100644 --- a/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/Ia32/IntHandlerFuncs.c +++ b/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/Ia32/IntHandlerFuncs.c @@ -18,6 +18,7 @@ Read IDT entry to check if IDT entries are setup by Debug Agent. @param[in] IdtDescriptor Pointer to IDT Descriptor. + @param[in] InterruptType Interrupt type. @retval TRUE IDT entries were setup by Debug Agent. @retval FALSE IDT entries were not setuo by Debug Agent. @@ -25,7 +26,8 @@ **/ BOOLEAN CheckDebugAgentHandler ( - IN IA32_DESCRIPTOR *IdtDescriptor + IN IA32_DESCRIPTOR *IdtDescriptor, + IN UINTN InterruptType ) { IA32_IDT_GATE_DESCRIPTOR *IdtEntry; @@ -36,8 +38,9 @@ CheckDebugAgentHandler ( return FALSE; } - InterruptHandler = IdtEntry[0].Bits.OffsetLow + (IdtEntry[0].Bits.OffsetHigh << 16); - if (InterruptHandler >= 4 && *(UINT32 *)(InterruptHandler - 4) == AGENT_HANDLER_SIGNATURE) { + InterruptHandler = IdtEntry[InterruptType].Bits.OffsetLow + + (IdtEntry[InterruptType].Bits.OffsetHigh << 16); + if (InterruptHandler >= sizeof (UINT32) && *(UINT32 *)(InterruptHandler - sizeof (UINT32)) == AGENT_HANDLER_SIGNATURE) { return TRUE; } else { return FALSE; diff --git a/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLib.c b/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLib.c index c28d7930a3..9bf76bfb22 100644 --- a/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLib.c +++ b/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLib.c @@ -80,18 +80,21 @@ PeCoffLoaderExtraActionCommon ( IdtEntryHooked = FALSE; LoadImageMethod = PcdGet8 (PcdDebugLoadImageMethod); AsmReadIdtr (&IdtDescriptor); - if (!CheckDebugAgentHandler (&IdtDescriptor)) { - if (LoadImageMethod == DEBUG_LOAD_IMAGE_METHOD_SOFT_INT3) { + if (LoadImageMethod == DEBUG_LOAD_IMAGE_METHOD_SOFT_INT3) { + if (!CheckDebugAgentHandler (&IdtDescriptor, SOFT_INT_VECTOR_NUM)) { // // Do not trigger INT3 if Debug Agent did not setup IDT entries. // return; } - // - // Save and update IDT entry for INT1 - // - SaveAndUpdateIdtEntry1 (&IdtDescriptor, &OriginalIdtEntry); - IdtEntryHooked = TRUE; + } else { + if (!CheckDebugAgentHandler (&IdtDescriptor, IO_HW_BREAKPOINT_VECTOR_NUM)) { + // + // Save and update IDT entry for INT1 + // + SaveAndUpdateIdtEntry1 (&IdtDescriptor, &OriginalIdtEntry); + IdtEntryHooked = TRUE; + } } // diff --git a/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLib.h b/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLib.h index 36aebf16d1..3f919287e8 100644 --- a/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLib.h +++ b/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLib.h @@ -28,12 +28,16 @@ #define DEBUG_LOAD_IMAGE_METHOD_IO_HW_BREAKPOINT 1 #define DEBUG_LOAD_IMAGE_METHOD_SOFT_INT3 2 +#define IO_HW_BREAKPOINT_VECTOR_NUM 1 +#define SOFT_INT_VECTOR_NUM 3 + extern UINTN AsmInterruptHandle; /** Read IDT entry to check if IDT entries are setup by Debug Agent. @param[in] IdtDescriptor Pointer to IDT Descriptor. + @param[in] InterruptType Interrupt type. @retval TRUE IDT entries were setup by Debug Agent. @retval FALSE IDT entries were not setuo by Debug Agent. @@ -41,7 +45,8 @@ extern UINTN AsmInterruptHandle; **/ BOOLEAN CheckDebugAgentHandler ( - IN IA32_DESCRIPTOR *IdtDescriptor + IN IA32_DESCRIPTOR *IdtDescriptor, + IN UINTN InterruptType ); /** diff --git a/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/X64/IntHandlerFuncs.c b/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/X64/IntHandlerFuncs.c index c9041de765..5431187d06 100644 --- a/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/X64/IntHandlerFuncs.c +++ b/SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/X64/IntHandlerFuncs.c @@ -18,6 +18,7 @@ Read IDT entry to check if IDT entries are setup by Debug Agent. @param[in] IdtDescriptor Pointer to IDT Descriptor. + @param[in] InterruptType Interrupt type. @retval TRUE IDT entries were setup by Debug Agent. @retval FALSE IDT entries were not setuo by Debug Agent. @@ -25,7 +26,8 @@ **/ BOOLEAN CheckDebugAgentHandler ( - IN IA32_DESCRIPTOR *IdtDescriptor + IN IA32_DESCRIPTOR *IdtDescriptor, + IN UINTN InterruptType ) { IA32_IDT_GATE_DESCRIPTOR *IdtEntry; @@ -36,9 +38,10 @@ CheckDebugAgentHandler ( return FALSE; } - InterruptHandler = IdtEntry[0].Bits.OffsetLow + (((UINTN)IdtEntry[0].Bits.OffsetHigh) << 16) + - (((UINTN)IdtEntry[0].Bits.OffsetUpper) << 32); - if (InterruptHandler >= 4 && *(UINT32 *)(InterruptHandler - 4) == AGENT_HANDLER_SIGNATURE) { + InterruptHandler = IdtEntry[InterruptType].Bits.OffsetLow + + (((UINTN)IdtEntry[InterruptType].Bits.OffsetHigh) << 16) + + (((UINTN)IdtEntry[InterruptType].Bits.OffsetUpper) << 32); + if (InterruptHandler >= sizeof (UINT32) && *(UINT32 *)(InterruptHandler - sizeof (UINT32)) == AGENT_HANDLER_SIGNATURE) { return TRUE; } else { return FALSE;