]> git.proxmox.com Git - mirror_edk2.git/blame - BeagleBoardPkg/Library/EblCmdLib/EblCmdLib.c
ARM Packages: Removed trailing spaces
[mirror_edk2.git] / BeagleBoardPkg / Library / EblCmdLib / EblCmdLib.c
CommitLineData
2ef2b01e
A
1/** @file\r
2 Add custom commands for BeagleBoard development.\r
3\r
1ebd6c11 4 Copyright (c) 2008 - 2010, Apple Inc. All rights reserved.<BR>\r
3402aac7 5\r
1ebd6c11 6 This program and the accompanying materials\r
2ef2b01e
A
7 are licensed and made available under the terms and conditions of the BSD License\r
8 which accompanies this distribution. The full text of the license may be found at\r
9 http://opensource.org/licenses/bsd-license.php\r
10\r
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
13\r
14**/\r
15\r
16#include <PiDxe.h>\r
17#include <Library/ArmLib.h>\r
18#include <Library/CacheMaintenanceLib.h>\r
19#include <Library/EblCmdLib.h>\r
20#include <Library/BaseLib.h>\r
21#include <Library/DebugLib.h>\r
22#include <Library/UefiBootServicesTableLib.h>\r
23#include <Library/UefiRuntimeServicesTableLib.h>\r
24#include <Library/MemoryAllocationLib.h>\r
25#include <Library/UefiLib.h>\r
26#include <Library/PcdLib.h>\r
27#include <Library/EfiFileLib.h>\r
f9f937d2 28#include <Library/ArmDisassemblerLib.h>\r
b2a73e21 29#include <Library/PeCoffGetEntryPointLib.h>\r
d02b28d7 30#include <Library/PerformanceLib.h>\r
31#include <Library/TimerLib.h>\r
2ef2b01e 32\r
b2a73e21 33#include <Guid/DebugImageInfoTable.h>\r
d02b28d7 34\r
b2a73e21 35#include <Protocol/DebugSupport.h>\r
36#include <Protocol/LoadedImage.h>\r
6f72e28d 37\r
38/**\r
b2a73e21 39 Simple arm disassembler via a library\r
6f72e28d 40\r
b2a73e21 41 Argv[0] - symboltable\r
3402aac7 42 Argv[1] - Optional quoted format string\r
b2a73e21 43 Argv[2] - Optional flag\r
44\r
45 @param Argc Number of command arguments in Argv\r
3402aac7 46 @param Argv Array of strings that represent the parsed command line.\r
11c20f4e 47 Argv[0] is the command name\r
b2a73e21 48\r
49 @return EFI_SUCCESS\r
50\r
51**/\r
52EFI_STATUS\r
53EblSymbolTable (\r
54 IN UINTN Argc,\r
55 IN CHAR8 **Argv\r
56 )\r
57{\r
58 EFI_STATUS Status;\r
59 EFI_DEBUG_IMAGE_INFO_TABLE_HEADER *DebugImageTableHeader = NULL;\r
60 EFI_DEBUG_IMAGE_INFO *DebugTable;\r
61 UINTN Entry;\r
62 CHAR8 *Format;\r
63 CHAR8 *Pdb;\r
64 UINT32 PeCoffSizeOfHeaders;\r
65 UINT32 ImageBase;\r
66 BOOLEAN Elf;\r
3402aac7 67\r
b2a73e21 68 // Need to add lots of error checking on the passed in string\r
f3e69908 69 // Default string is for RealView debugger or gdb depending on toolchain used.\r
70 if (Argc > 1) {\r
71 Format = Argv[1];\r
72 } else {\r
73#if __GNUC__\r
74 // Assume gdb\r
75 Format = "add-symbol-file %a 0x%x";\r
76#else\r
3402aac7 77 // Default to RVCT\r
f3e69908 78 Format = "load /a /ni /np %a &0x%x";\r
79#endif\r
80 }\r
b2a73e21 81 Elf = (Argc > 2) ? FALSE : TRUE;\r
3402aac7 82\r
b2a73e21 83 Status = EfiGetSystemConfigurationTable (&gEfiDebugImageInfoTableGuid, (VOID **)&DebugImageTableHeader);\r
84 if (EFI_ERROR (Status)) {\r
85 return Status;\r
86 }\r
3402aac7 87\r
b2a73e21 88 DebugTable = DebugImageTableHeader->EfiDebugImageInfoTable;\r
89 if (DebugTable == NULL) {\r
90 return EFI_SUCCESS;\r
91 }\r
92\r
93 for (Entry = 0; Entry < DebugImageTableHeader->TableSize; Entry++, DebugTable++) {\r
94 if (DebugTable->NormalImage != NULL) {\r
95 if ((DebugTable->NormalImage->ImageInfoType == EFI_DEBUG_IMAGE_INFO_TYPE_NORMAL) && (DebugTable->NormalImage->LoadedImageProtocolInstance != NULL)) {\r
96 ImageBase = (UINT32)DebugTable->NormalImage->LoadedImageProtocolInstance->ImageBase;\r
97 PeCoffSizeOfHeaders = PeCoffGetSizeOfHeaders ((VOID *)(UINTN)ImageBase);\r
98 Pdb = PeCoffLoaderGetPdbPointer (DebugTable->NormalImage->LoadedImageProtocolInstance->ImageBase);\r
b8758b6e 99 if (Pdb != NULL) {\r
100 if (Elf) {\r
101 // ELF and Mach-O images don't include the header so the linked address does not include header\r
102 ImageBase += PeCoffSizeOfHeaders;\r
3402aac7 103 }\r
b8758b6e 104 AsciiPrint (Format, Pdb, ImageBase);\r
105 AsciiPrint ("\n");\r
106 } else {\r
107 }\r
b2a73e21 108 }\r
3402aac7 109 }\r
b2a73e21 110 }\r
111\r
112 return EFI_SUCCESS;\r
113}\r
114\r
115\r
116/**\r
117 Simple arm disassembler via a library\r
118\r
119 Argv[0] - disasm\r
120 Argv[1] - Address to start disassembling from\r
121 ARgv[2] - Number of instructions to disassembly (optional)\r
6f72e28d 122\r
123 @param Argc Number of command arguments in Argv\r
3402aac7 124 @param Argv Array of strings that represent the parsed command line.\r
11c20f4e 125 Argv[0] is the command name\r
6f72e28d 126\r
127 @return EFI_SUCCESS\r
128\r
129**/\r
130EFI_STATUS\r
f9f937d2 131EblDisassembler (\r
6f72e28d 132 IN UINTN Argc,\r
133 IN CHAR8 **Argv\r
134 )\r
135{\r
77844905 136 UINT8 *Ptr, *CurrentAddress;\r
f9f937d2 137 UINT32 Address;\r
138 UINT32 Count;\r
139 CHAR8 Buffer[80];\r
f3198cba 140 UINT32 ItBlock;\r
3402aac7 141\r
f9f937d2 142 if (Argc < 2) {\r
143 return EFI_INVALID_PARAMETER;\r
144 }\r
3402aac7 145\r
f9f937d2 146 Address = AsciiStrHexToUintn (Argv[1]);\r
77844905 147 Count = (Argc > 2) ? (UINT32)AsciiStrHexToUintn (Argv[2]) : 20;\r
f9f937d2 148\r
3402aac7 149 Ptr = (UINT8 *)(UINTN)Address;\r
f3198cba 150 ItBlock = 0;\r
77844905 151 do {\r
152 CurrentAddress = Ptr;\r
f3198cba 153 DisassembleInstruction (&Ptr, TRUE, TRUE, &ItBlock, Buffer, sizeof (Buffer));\r
77844905 154 AsciiPrint ("0x%08x: %a\n", CurrentAddress, Buffer);\r
155 } while (Count-- > 0);\r
3402aac7 156\r
f9f937d2 157\r
6f72e28d 158 return EFI_SUCCESS;\r
159}\r
160\r
161\r
d02b28d7 162CHAR8 *\r
163ImageHandleToPdbFileName (\r
164 IN EFI_HANDLE Handle\r
165 )\r
166{\r
167 EFI_STATUS Status;\r
168 EFI_LOADED_IMAGE_PROTOCOL *LoadedImage;\r
d39eb83c 169 CHAR8 *Pdb;\r
170 CHAR8 *StripLeading;\r
d02b28d7 171\r
172 Status = gBS->HandleProtocol (Handle, &gEfiLoadedImageProtocolGuid, (VOID **)&LoadedImage);\r
173 if (EFI_ERROR (Status)) {\r
174 return "";\r
175 }\r
176\r
d39eb83c 177 Pdb = PeCoffLoaderGetPdbPointer (LoadedImage->ImageBase);\r
178 StripLeading = AsciiStrStr (Pdb, "\\ARM\\");\r
179 if (StripLeading == NULL) {\r
180 StripLeading = AsciiStrStr (Pdb, "/ARM/");\r
181 if (StripLeading == NULL) {\r
182 return Pdb;\r
183 }\r
184 }\r
185 // Hopefully we hacked off the unneeded part\r
186 return (StripLeading + 5);\r
d02b28d7 187}\r
188\r
d39eb83c 189\r
d02b28d7 190CHAR8 *mTokenList[] = {\r
191 "SEC",\r
192 "PEI",\r
193 "DXE",\r
194 "BDS",\r
195 NULL\r
196};\r
197\r
198/**\r
199 Simple arm disassembler via a library\r
200\r
201 Argv[0] - disasm\r
202 Argv[1] - Address to start disassembling from\r
203 ARgv[2] - Number of instructions to disassembly (optional)\r
204\r
205 @param Argc Number of command arguments in Argv\r
3402aac7 206 @param Argv Array of strings that represent the parsed command line.\r
11c20f4e 207 Argv[0] is the command name\r
d02b28d7 208\r
209 @return EFI_SUCCESS\r
210\r
211**/\r
212EFI_STATUS\r
213EblPerformance (\r
214 IN UINTN Argc,\r
215 IN CHAR8 **Argv\r
216 )\r
217{\r
218 UINTN Key;\r
219 CONST VOID *Handle;\r
220 CONST CHAR8 *Token, *Module;\r
221 UINT64 Start, Stop, TimeStamp;\r
222 UINT64 Delta, TicksPerSecond, Milliseconds, Microseconds;\r
223 UINTN Index;\r
224\r
225 TicksPerSecond = GetPerformanceCounterProperties (NULL, NULL);\r
226\r
227 Key = 0;\r
228 do {\r
229 Key = GetPerformanceMeasurement (Key, (CONST VOID **)&Handle, &Token, &Module, &Start, &Stop);\r
230 if (Key != 0) {\r
231 if (AsciiStriCmp ("StartImage:", Token) == 0) {\r
232 if (Stop == 0) {\r
233 // The entry for EBL is still running so the stop time will be zero. Skip it\r
234 AsciiPrint (" running %a\n", ImageHandleToPdbFileName ((EFI_HANDLE)Handle));\r
235 } else {\r
236 Delta = Stop - Start;\r
237 Microseconds = DivU64x64Remainder (MultU64x32 (Delta, 1000000), TicksPerSecond, NULL);\r
238 AsciiPrint ("%10ld us %a\n", Microseconds, ImageHandleToPdbFileName ((EFI_HANDLE)Handle));\r
239 }\r
240 }\r
241 }\r
242 } while (Key != 0);\r
243\r
244 AsciiPrint ("\n");\r
245\r
246 TimeStamp = 0;\r
247 Key = 0;\r
248 do {\r
249 Key = GetPerformanceMeasurement (Key, (CONST VOID **)&Handle, &Token, &Module, &Start, &Stop);\r
250 if (Key != 0) {\r
251 for (Index = 0; mTokenList[Index] != NULL; Index++) {\r
252 if (AsciiStriCmp (mTokenList[Index], Token) == 0) {\r
253 Delta = Stop - Start;\r
254 TimeStamp += Delta;\r
255 Milliseconds = DivU64x64Remainder (MultU64x32 (Delta, 1000), TicksPerSecond, NULL);\r
256 AsciiPrint ("%6a %6ld ms\n", Token, Milliseconds);\r
257 break;\r
258 }\r
3402aac7 259 }\r
d02b28d7 260 }\r
261 } while (Key != 0);\r
262\r
263 AsciiPrint ("Total Time = %ld ms\n\n", DivU64x64Remainder (MultU64x32 (TimeStamp, 1000), TicksPerSecond, NULL));\r
264\r
265 return EFI_SUCCESS;\r
266}\r
267\r
268\r
2ef2b01e
A
269GLOBAL_REMOVE_IF_UNREFERENCED const EBL_COMMAND_TABLE mLibCmdTemplate[] =\r
270{\r
6f72e28d 271 {\r
f9f937d2 272 "disasm address [count]",\r
273 " disassemble count instructions",\r
6f72e28d 274 NULL,\r
f9f937d2 275 EblDisassembler\r
b2a73e21 276 },\r
d02b28d7 277 {\r
278 "performance",\r
279 " Display boot performance info",\r
280 NULL,\r
281 EblPerformance\r
282 },\r
b2a73e21 283 {\r
b8758b6e 284 "symboltable [\"format string\"] [PECOFF]",\r
b2a73e21 285 " show symbol table commands for debugger",\r
286 NULL,\r
287 EblSymbolTable\r
6f72e28d 288 }\r
2ef2b01e
A
289};\r
290\r
291\r
292VOID\r
293EblInitializeExternalCmd (\r
294 VOID\r
295 )\r
296{\r
297 EblAddCommands (mLibCmdTemplate, sizeof (mLibCmdTemplate)/sizeof (EBL_COMMAND_TABLE));\r
298 return;\r
299}\r