3 Copyright (c) 2007, Intel Corporation
4 All rights reserved. This program and the accompanying materials
5 are licensed and made available under the terms and conditions of the BSD License
6 which accompanies this distribution. The full text of the license may be found at
7 http://opensource.org/licenses/bsd-license.php
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
24 GetFileNameFromFullPath (
31 Get file name from full path
35 FullPath - full file path
47 TempFileName
= StrGetNewTokenLine (FullPath
, L
"\\");
49 while (TempFileName
!= NULL
) {
50 FileName
= TempFileName
;
51 TempFileName
= StrGetNextTokenLine (L
"\\");
52 PatchForStrTokenBefore (TempFileName
, L
'\\');
59 GetDirNameFromFullPath (
66 Get dir name from full path
70 FullPath - full file path
80 FileName
= GetFileNameFromFullPath (FullPath
);
81 if (FileName
!= FullPath
) {
99 Construct full path accroding to dir and file path
115 DirPathSize
= StrLen(DirPath
);
116 *(DirPath
+ DirPathSize
) = L
'\\';
117 StrnCatS (DirPath
, DirPathSize
+ Size
+ 1, FilePath
, Size
);
119 *(DirPath
+ DirPathSize
+ Size
+ 1) = 0;
124 CHAR16
*mSymbolTypeStr
[] = {
133 IN EFI_DEBUGGER_SYMBOL_TYPE Type
139 Comvert Symbol Type to string
151 if (Type
< 0 || Type
>= EfiDebuggerSymbolTypeMax
) {
155 return mSymbolTypeStr
[Type
];
159 DebuggerDisplaySymbolAccrodingToAddress (
161 IN EFI_DEBUGGER_PRIVATE_DATA
*DebuggerPrivate
167 Find the symbol accroding to address and display symbol
171 Address - SymbolAddress
172 DebuggerPrivate - EBC Debugger private data structure
176 EFI_DEBUG_CONTINUE - formal return value
180 EFI_DEBUGGER_SYMBOL_OBJECT
*Object
;
181 EFI_DEBUGGER_SYMBOL_ENTRY
*Entry
;
182 UINTN CandidateAddress
;
185 // Find the nearest symbol address
187 CandidateAddress
= EbdFindSymbolAddress (Address
, EdbMatchSymbolTypeNearestAddress
, &Object
, &Entry
);
188 if (CandidateAddress
== 0) {
189 EDBPrint (L
"Symbole at Address not found!\n");
190 return EFI_DEBUG_CONTINUE
;
191 } else if (Address
!= CandidateAddress
) {
192 EDBPrint (L
"Symbole at Address not found, print nearest one!\n");
198 EDBPrint (L
"Symbol File Name: %s\n", Object
->Name
);
199 if (sizeof(UINTN
) == sizeof(UINT64
)) {
200 EDBPrint (L
" Address Type Symbol\n");
201 EDBPrint (L
" ================== ==== ========\n");
202 // EDBPrint (L" 0xFFFFFFFF00000000 ( F) TestMain\n");
204 L
" 0x%016lx %s %a\n",
205 (UINT64
)Entry
->RVA
+ Object
->BaseAddress
,
206 EdbSymbolTypeToStr (Entry
->Type
),
210 EDBPrint (L
" Address Type Symbol\n");
211 EDBPrint (L
" ========== ==== ========\n");
212 // EDBPrint (L" 0xFFFF0000 ( F) TestMain\n");
215 Entry
->RVA
+ Object
->BaseAddress
,
216 EdbSymbolTypeToStr (Entry
->Type
),
224 return EFI_DEBUG_CONTINUE
;
228 DebuggerDisplaySymbolAccrodingToName (
229 IN CHAR16
*SymbolFileName
,
230 IN CHAR16
*SymbolName
,
231 IN EFI_DEBUGGER_PRIVATE_DATA
*DebuggerPrivate
237 Find the symbol accroding to name and display symbol
241 SymbolFileName - The Symbol File Name, NULL means for all
242 SymbolName - The Symbol Name, NULL means for all
243 DebuggerPrivate - EBC Debugger private data structure
247 EFI_DEBUG_CONTINUE - formal return value
253 EFI_DEBUGGER_SYMBOL_OBJECT
*Object
;
254 EFI_DEBUGGER_SYMBOL_ENTRY
*Entry
;
256 if (DebuggerPrivate
->DebuggerSymbolContext
.ObjectCount
== 0) {
257 EDBPrint (L
"No Symbol File!\n");
258 return EFI_DEBUG_CONTINUE
;
262 // Go throuth each symbol file
264 Object
= DebuggerPrivate
->DebuggerSymbolContext
.Object
;
265 for (Index
= 0; Index
< DebuggerPrivate
->DebuggerSymbolContext
.ObjectCount
; Index
++, Object
++) {
266 if ((SymbolFileName
!= NULL
) &&
267 (StriCmp (SymbolFileName
, Object
->Name
) != 0)) {
272 // Break each symbol file
275 if (SetPageBreak ()) {
280 EDBPrint (L
"Symbol File Name: %s\n", Object
->Name
);
281 if (Object
->EntryCount
== 0) {
282 EDBPrint (L
"No Symbol!\n");
285 Entry
= Object
->Entry
;
286 if (sizeof(UINTN
) == sizeof(UINT64
)) {
287 EDBPrint (L
" Address Type Symbol\n");
288 EDBPrint (L
" ================== ==== ========\n");
289 // EDBPrint (L" 0xFFFFFFFF00000000 ( F) TestMain (EbcTest.obj)\n");
291 EDBPrint (L
" Address Type Symbol\n");
292 EDBPrint (L
" ========== ==== ========\n");
293 // EDBPrint (L" 0xFFFF0000 ( F) TestMain (EbcTest.obj)\n");
297 // Go through each symbol name
299 for (SubIndex
= 0; SubIndex
< Object
->EntryCount
; SubIndex
++, Entry
++) {
300 if ((SymbolName
!= NULL
) &&
301 (StrCmpUnicodeAndAscii (SymbolName
, Entry
->Name
) != 0)) {
308 if (((SubIndex
% EFI_DEBUGGER_LINE_NUMBER_IN_PAGE
) == 0) &&
310 if (SetPageBreak ()) {
315 if (sizeof(UINTN
) == sizeof(UINT64
)) {
317 L
" 0x%016lx %s %a (%a)\n",
318 (UINT64
)Entry
->RVA
+ Object
->BaseAddress
,
319 EdbSymbolTypeToStr (Entry
->Type
),
325 L
" 0x%08x %s %a (%a)\n",
326 Entry
->RVA
+ Object
->BaseAddress
,
327 EdbSymbolTypeToStr (Entry
->Type
),
338 return EFI_DEBUG_CONTINUE
;
343 IN CHAR16
*CommandArg
,
344 IN EFI_DEBUGGER_PRIVATE_DATA
*DebuggerPrivate
,
345 IN EFI_EXCEPTION_TYPE ExceptionType
,
346 IN OUT EFI_SYSTEM_CONTEXT SystemContext
352 DebuggerCommand - ListSymbol
356 CommandArg - The argument for this command
357 DebuggerPrivate - EBC Debugger private data structure
358 InterruptType - Interrupt type.
359 SystemContext - EBC system context.
363 EFI_DEBUG_CONTINUE - formal return value
367 CHAR16
*SymbolFileName
;
372 SymbolFileName
= NULL
;
374 CommandStr
= CommandArg
;
377 // display symbol according to address
379 if (CommandStr
!= NULL
) {
380 if ((StriCmp (CommandStr
, L
"F") != 0) &&
381 (StriCmp (CommandStr
, L
"S") != 0)) {
382 Address
= Xtoi (CommandStr
);
383 return DebuggerDisplaySymbolAccrodingToAddress (Address
, DebuggerPrivate
);
388 // Get SymbolFileName
390 if (CommandStr
!= NULL
) {
391 if (StriCmp (CommandStr
, L
"F") == 0) {
392 CommandStr
= StrGetNextTokenLine (L
" ");
393 if (CommandStr
== NULL
) {
394 EDBPrint (L
"Symbol File Name missing!\n");
395 return EFI_DEBUG_CONTINUE
;
397 SymbolFileName
= CommandStr
;
398 CommandStr
= StrGetNextTokenLine (L
" ");
405 if (CommandStr
!= NULL
) {
406 if (StriCmp (CommandStr
, L
"S") == 0) {
407 CommandStr
= StrGetNextTokenLine (L
" ");
408 if (CommandStr
== NULL
) {
409 EDBPrint (L
"Symbol Name missing!\n");
410 return EFI_DEBUG_CONTINUE
;
412 SymbolName
= CommandStr
;
413 CommandStr
= StrGetNextTokenLine (L
" ");
417 if (CommandStr
!= NULL
) {
418 EDBPrint (L
"Argument error!\n");
419 return EFI_DEBUG_CONTINUE
;
423 // display symbol according to name
425 return DebuggerDisplaySymbolAccrodingToName (SymbolFileName
, SymbolName
, DebuggerPrivate
);
430 IN CHAR16
*CommandArg
,
431 IN EFI_DEBUGGER_PRIVATE_DATA
*DebuggerPrivate
,
432 IN EFI_EXCEPTION_TYPE ExceptionType
,
433 IN OUT EFI_SYSTEM_CONTEXT SystemContext
439 DebuggerCommand - LoadSymbol
443 CommandArg - The argument for this command
444 DebuggerPrivate - EBC Debugger private data structure
445 InterruptType - Interrupt type.
446 SystemContext - EBC system context.
450 EFI_DEBUG_CONTINUE - formal return value
461 CHAR16 CodFile
[EFI_DEBUGGER_SYMBOL_NAME_MAX
];
466 // Check the argument
468 if (CommandArg
== NULL
) {
469 EDBPrint (L
"SymbolFile not found!\n");
470 return EFI_DEBUG_CONTINUE
;
473 CommandArg2
= StrGetNextTokenLine (L
" ");
474 if (CommandArg2
!= NULL
) {
475 if (StriCmp (CommandArg2
, L
"a") == 0) {
478 EDBPrint (L
"Argument error!\n");
479 return EFI_DEBUG_CONTINUE
;
483 if (StrLen (CommandArg
) <= 4) {
484 EDBPrint (L
"SymbolFile name error!\n");
485 return EFI_DEBUG_CONTINUE
;
487 if (StriCmp (CommandArg
+ (StrLen (CommandArg
) - 4), L
".map") != 0) {
488 EDBPrint (L
"SymbolFile name error!\n");
489 return EFI_DEBUG_CONTINUE
;
493 // Read MAP file to memory
495 Status
= ReadFileToBuffer (DebuggerPrivate
, CommandArg
, &BufferSize
, &Buffer
, TRUE
);
496 if (EFI_ERROR(Status
)) {
497 EDBPrint (L
"SymbolFile read error!\n");
498 return EFI_DEBUG_CONTINUE
;
501 FileName
= GetFileNameFromFullPath (CommandArg
);
505 Status
= EdbLoadSymbol (DebuggerPrivate
, FileName
, BufferSize
, Buffer
);
506 if (EFI_ERROR(Status
)) {
507 EDBPrint (L
"LoadSymbol error!\n");
508 gBS
->FreePool (Buffer
);
509 return EFI_DEBUG_CONTINUE
;
511 gBS
->FreePool (Buffer
);
514 // Patch Symbol for RVA
516 Status
= EdbPatchSymbolRVA (DebuggerPrivate
, FileName
, EdbEbcImageRvaSearchTypeLast
);
517 if (EFI_ERROR(Status
)) {
518 EDBPrint (L
"PatchSymbol RVA - %r! Using the RVA in symbol file.\n", Status
);
520 DEBUG ((DEBUG_ERROR
, "PatchSymbol RVA successfully!\n"));
524 return EFI_DEBUG_CONTINUE
;
528 // load each cod file
530 DirName
= GetDirNameFromFullPath (CommandArg
);
531 ZeroMem (CodFile
, sizeof(CodFile
));
532 if (StrCmp (DirName
, L
"") != 0) {
533 StrCpyS (CodFile
, sizeof(CodFile
), DirName
);
539 // Go throuth each file under this dir
542 CodFileName
= GetFileNameUnderDir (DebuggerPrivate
, DirName
, L
".cod", &Index
);
543 while (CodFileName
!= NULL
) {
544 ZeroMem (CodFile
, sizeof(CodFile
));
545 if (StrCmp (DirName
, L
"\\") != 0) {
546 StrCpyS (CodFile
, sizeof(CodFile
), DirName
);
550 // read cod file to memory
552 Status
= ReadFileToBuffer (DebuggerPrivate
, ConstructFullPath (CodFile
, CodFileName
, EFI_DEBUGGER_SYMBOL_NAME_MAX
- StrLen (CodFile
) - 2), &BufferSize
, &Buffer
, FALSE
);
553 if (EFI_ERROR(Status
)) {
554 EDBPrint (L
"CodeFile read error!\n");
555 CodFileName
= GetFileNameUnderDir (DebuggerPrivate
, DirName
, L
".cod", &Index
);
562 Status
= EdbLoadCode (DebuggerPrivate
, FileName
, CodFileName
, BufferSize
, Buffer
);
563 if (EFI_ERROR (Status
)) {
564 EDBPrint (L
"LoadCode error!\n");
565 gBS
->FreePool (Buffer
);
566 CodFileName
= GetFileNameUnderDir (DebuggerPrivate
, DirName
, L
".cod", &Index
);
573 Status
= EdbAddCodeBuffer (DebuggerPrivate
, FileName
, CodFileName
, BufferSize
, Buffer
);
574 if (EFI_ERROR (Status
)) {
575 EDBPrint (L
"AddCodeBuffer error!\n");
576 gBS
->FreePool (Buffer
);
577 CodFileName
= GetFileNameUnderDir (DebuggerPrivate
, DirName
, L
".cod", &Index
);
584 CodFileName
= GetFileNameUnderDir (DebuggerPrivate
, DirName
, L
".cod", &Index
);
590 return EFI_DEBUG_CONTINUE
;
594 DebuggerUnloadSymbol (
595 IN CHAR16
*CommandArg
,
596 IN EFI_DEBUGGER_PRIVATE_DATA
*DebuggerPrivate
,
597 IN EFI_EXCEPTION_TYPE ExceptionType
,
598 IN OUT EFI_SYSTEM_CONTEXT SystemContext
604 DebuggerCommand - UnloadSymbol
608 CommandArg - The argument for this command
609 DebuggerPrivate - EBC Debugger private data structure
610 InterruptType - Interrupt type.
611 SystemContext - EBC system context.
615 EFI_DEBUG_CONTINUE - formal return value
622 CHAR16 CodFile
[EFI_DEBUGGER_SYMBOL_NAME_MAX
];
628 // Check the argument
630 if (CommandArg
== NULL
) {
631 EDBPrint (L
"SymbolFile not found!\n");
632 return EFI_DEBUG_CONTINUE
;
635 FileName
= GetFileNameFromFullPath (CommandArg
);
640 DirName
= GetDirNameFromFullPath (CommandArg
);
641 ZeroMem (CodFile
, sizeof(CodFile
));
642 if (StrCmp (DirName
, L
"") != 0) {
643 StrCpyS (CodFile
, sizeof(CodFile
), DirName
);
649 // Go through each file under this dir
652 CodFileName
= GetFileNameUnderDir (DebuggerPrivate
, DirName
, L
".cod", &Index
);
653 while (CodFileName
!= NULL
) {
654 ZeroMem (CodFile
, sizeof(CodFile
));
655 if (StrCmp (DirName
, L
"\\") != 0) {
656 StrCpyS (CodFile
, sizeof(CodFile
), DirName
);
662 Status
= EdbUnloadCode (DebuggerPrivate
, FileName
, CodFileName
, &BufferPtr
);
663 if (EFI_ERROR (Status
)) {
664 EDBPrint (L
"UnloadCode error!\n");
665 CodFileName
= GetFileNameUnderDir (DebuggerPrivate
, DirName
, L
".cod", &Index
);
670 // Delete the code buffer
672 Status
= EdbDeleteCodeBuffer (DebuggerPrivate
, FileName
, CodFileName
, BufferPtr
);
673 if (EFI_ERROR (Status
)) {
674 EDBPrint (L
"DeleteCodeBuffer error!\n");
675 CodFileName
= GetFileNameUnderDir (DebuggerPrivate
, DirName
, L
".cod", &Index
);
682 CodFileName
= GetFileNameUnderDir (DebuggerPrivate
, DirName
, L
".cod", &Index
);
688 Status
= EdbUnloadSymbol (DebuggerPrivate
, FileName
);
689 if (EFI_ERROR(Status
)) {
690 EDBPrint (L
"UnloadSymbol error!\n");
696 return EFI_DEBUG_CONTINUE
;
700 DebuggerDisplaySymbol (
701 IN CHAR16
*CommandArg
,
702 IN EFI_DEBUGGER_PRIVATE_DATA
*DebuggerPrivate
,
703 IN EFI_EXCEPTION_TYPE ExceptionType
,
704 IN OUT EFI_SYSTEM_CONTEXT SystemContext
710 DebuggerCommand - DisplaySymbol
714 CommandArg - The argument for this command
715 DebuggerPrivate - EBC Debugger private data structure
716 InterruptType - Interrupt type.
717 SystemContext - EBC system context.
721 EFI_DEBUG_CONTINUE - formal return value
725 if (CommandArg
== NULL
) {
726 DebuggerPrivate
->DebuggerSymbolContext
.DisplaySymbol
= !DebuggerPrivate
->DebuggerSymbolContext
.DisplaySymbol
;
727 EdbShowDisasm (DebuggerPrivate
, SystemContext
);
728 } else if (StriCmp (CommandArg
, L
"on") == 0) {
729 DebuggerPrivate
->DebuggerSymbolContext
.DisplaySymbol
= TRUE
;
730 EdbShowDisasm (DebuggerPrivate
, SystemContext
);
731 } else if (StriCmp (CommandArg
, L
"off") == 0) {
732 DebuggerPrivate
->DebuggerSymbolContext
.DisplaySymbol
= FALSE
;
733 EdbShowDisasm (DebuggerPrivate
, SystemContext
);
735 EDBPrint (L
"DisplaySymbol - argument error\n");
738 return EFI_DEBUG_CONTINUE
;
743 IN CHAR16
*CommandArg
,
744 IN EFI_DEBUGGER_PRIVATE_DATA
*DebuggerPrivate
,
745 IN EFI_EXCEPTION_TYPE ExceptionType
,
746 IN OUT EFI_SYSTEM_CONTEXT SystemContext
752 DebuggerCommand - LoadCode
756 CommandArg - The argument for this command
757 DebuggerPrivate - EBC Debugger private data structure
758 InterruptType - Interrupt type.
759 SystemContext - EBC system context.
763 EFI_DEBUG_CONTINUE - formal return value
775 // Check the argument
777 if (CommandArg
== NULL
) {
778 EDBPrint (L
"CodeFile not found!\n");
779 return EFI_DEBUG_CONTINUE
;
781 CommandArg2
= StrGetNextTokenLine (L
" ");
782 if (CommandArg2
== NULL
) {
783 EDBPrint (L
"SymbolFile not found!\n");
784 return EFI_DEBUG_CONTINUE
;
787 if (StrLen (CommandArg
) <= 4) {
788 EDBPrint (L
"CodeFile name error!\n");
789 return EFI_DEBUG_CONTINUE
;
791 if (StriCmp (CommandArg
+ (StrLen (CommandArg
) - 4), L
".cod") != 0) {
792 EDBPrint (L
"CodeFile name error!\n");
793 return EFI_DEBUG_CONTINUE
;
795 if (StrLen (CommandArg2
) <= 4) {
796 EDBPrint (L
"SymbolFile name error!\n");
797 return EFI_DEBUG_CONTINUE
;
799 if (StriCmp (CommandArg2
+ (StrLen (CommandArg2
) - 4), L
".map") != 0) {
800 EDBPrint (L
"SymbolFile name error!\n");
801 return EFI_DEBUG_CONTINUE
;
805 // read cod file to memory
807 Status
= ReadFileToBuffer (DebuggerPrivate
, CommandArg
, &BufferSize
, &Buffer
, TRUE
);
808 if (EFI_ERROR(Status
)) {
809 EDBPrint (L
"CodeFile read error!\n");
810 return EFI_DEBUG_CONTINUE
;
813 FileName
= GetFileNameFromFullPath (CommandArg
);
814 MapFileName
= GetFileNameFromFullPath (CommandArg2
);
818 Status
= EdbLoadCode (DebuggerPrivate
, MapFileName
, FileName
, BufferSize
, Buffer
);
819 if (EFI_ERROR (Status
)) {
820 EDBPrint (L
"LoadCode error!\n");
821 gBS
->FreePool (Buffer
);
822 return EFI_DEBUG_CONTINUE
;
828 Status
= EdbAddCodeBuffer (DebuggerPrivate
, MapFileName
, FileName
, BufferSize
, Buffer
);
829 if (EFI_ERROR (Status
)) {
830 EDBPrint (L
"AddCodeBuffer error!\n");
831 gBS
->FreePool (Buffer
);
832 return EFI_DEBUG_CONTINUE
;
838 return EFI_DEBUG_CONTINUE
;
843 IN CHAR16
*CommandArg
,
844 IN EFI_DEBUGGER_PRIVATE_DATA
*DebuggerPrivate
,
845 IN EFI_EXCEPTION_TYPE ExceptionType
,
846 IN OUT EFI_SYSTEM_CONTEXT SystemContext
852 DebuggerCommand - UnloadCode
856 CommandArg - The argument for this command
857 DebuggerPrivate - EBC Debugger private data structure
858 InterruptType - Interrupt type.
859 SystemContext - EBC system context.
863 EFI_DEBUG_CONTINUE - formal return value
874 // Check the argument
876 if (CommandArg
== NULL
) {
877 EDBPrint (L
"CodeFile not found!\n");
878 return EFI_DEBUG_CONTINUE
;
880 CommandArg2
= StrGetNextTokenLine (L
" ");
881 if (CommandArg2
== NULL
) {
882 EDBPrint (L
"SymbolFile not found!\n");
883 return EFI_DEBUG_CONTINUE
;
886 FileName
= GetFileNameFromFullPath (CommandArg
);
887 MapFileName
= GetFileNameFromFullPath (CommandArg2
);
892 Status
= EdbUnloadCode (DebuggerPrivate
, MapFileName
, FileName
, &BufferPtr
);
893 if (EFI_ERROR (Status
)) {
894 EDBPrint (L
"UnloadCode error!\n");
895 return EFI_DEBUG_CONTINUE
;
899 // Delete Code buffer
901 Status
= EdbDeleteCodeBuffer (DebuggerPrivate
, MapFileName
, FileName
, BufferPtr
);
902 if (EFI_ERROR (Status
)) {
903 EDBPrint (L
"DeleteCodeBuffer error!\n");
909 return EFI_DEBUG_CONTINUE
;
913 DebuggerDisplayCode (
914 IN CHAR16
*CommandArg
,
915 IN EFI_DEBUGGER_PRIVATE_DATA
*DebuggerPrivate
,
916 IN EFI_EXCEPTION_TYPE ExceptionType
,
917 IN OUT EFI_SYSTEM_CONTEXT SystemContext
923 DebuggerCommand - DisplayCode
927 CommandArg - The argument for this command
928 DebuggerPrivate - EBC Debugger private data structure
929 InterruptType - Interrupt type.
930 SystemContext - EBC system context.
934 EFI_DEBUG_CONTINUE - formal return value
938 if (CommandArg
== NULL
) {
939 DebuggerPrivate
->DebuggerSymbolContext
.DisplayCodeOnly
= !DebuggerPrivate
->DebuggerSymbolContext
.DisplayCodeOnly
;
940 EdbShowDisasm (DebuggerPrivate
, SystemContext
);
941 } else if (StriCmp (CommandArg
, L
"on") == 0) {
942 DebuggerPrivate
->DebuggerSymbolContext
.DisplayCodeOnly
= TRUE
;
943 EdbShowDisasm (DebuggerPrivate
, SystemContext
);
944 } else if (StriCmp (CommandArg
, L
"off") == 0) {
945 DebuggerPrivate
->DebuggerSymbolContext
.DisplayCodeOnly
= FALSE
;
946 EdbShowDisasm (DebuggerPrivate
, SystemContext
);
948 EDBPrint (L
"DisplayCode - argument error\n");
951 return EFI_DEBUG_CONTINUE
;