]> git.proxmox.com Git - mirror_edk2.git/blame - PerformancePkg/Dp_App/Dp.c
Refine the code to follow coding style.
[mirror_edk2.git] / PerformancePkg / Dp_App / Dp.c
CommitLineData
c06ad33e 1/** @file\r
86da563d
ED
2 Shell application for Displaying Performance Metrics.\r
3\r
4 The Dp application reads performance data and presents it in several\r
5 different formats depending upon the needs of the user. Both\r
6 Trace and Measured Profiling information is processed and presented.\r
7\r
8 Dp uses the "PerformanceLib" to read the measurement records.\r
9 The "TimerLib" provides information about the timer, such as frequency,\r
10 beginning, and ending counter values.\r
11 Measurement records contain identifying information (Handle, Token, Module)\r
12 and start and end time values.\r
13 Dp uses this information to group records in different ways. It also uses\r
14 timer information to calculate elapsed time for each measurement.\r
15 \r
16 Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>\r
17 This program and the accompanying materials\r
18 are licensed and made available under the terms and conditions of the BSD License\r
19 which accompanies this distribution. The full text of the license may be found at\r
20 http://opensource.org/licenses/bsd-license.php\r
21 \r
22 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
23 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
c06ad33e 24**/\r
25\r
26#include <Library/UefiApplicationEntryPoint.h>\r
27#include <Library/ShellLib.h>\r
28#include <Library/BaseLib.h>\r
29#include <Library/MemoryAllocationLib.h>\r
30#include <Library/DebugLib.h>\r
31#include <Library/TimerLib.h>\r
32#include <Library/UefiLib.h>\r
33#include <Library/HiiLib.h>\r
34#include <Library/PcdLib.h>\r
35\r
36#include <Guid/Performance.h>\r
37\r
38#include <PerformanceTokens.h>\r
39#include "Dp.h"\r
40#include "Literals.h"\r
41#include "DpInternal.h"\r
42\r
43//\r
44/// Module-Global Variables\r
9dd74618 45///@{\r
c06ad33e 46EFI_HII_HANDLE gHiiHandle;\r
88359546 47SHELL_PARAM_ITEM *DpParamList = NULL;\r
c06ad33e 48CHAR16 *mPrintTokenBuffer = NULL;\r
a2daf8db
SZ
49CHAR16 mGaugeString[DP_GAUGE_STRING_LENGTH + 1];\r
50CHAR16 mUnicodeToken[DXE_PERFORMANCE_STRING_SIZE];\r
c06ad33e 51UINT64 mInterestThreshold;\r
52\r
53PERF_SUMMARY_DATA SummaryData = { 0 }; ///< Create the SummaryData structure and init. to ZERO.\r
54\r
55/// Timer Specific Information.\r
56TIMER_INFO TimerInfo;\r
57\r
58/// Items for which to gather cumulative statistics.\r
59PERF_CUM_DATA CumData[] = {\r
60 PERF_INIT_CUM_DATA (LOAD_IMAGE_TOK),\r
61 PERF_INIT_CUM_DATA (START_IMAGE_TOK),\r
62 PERF_INIT_CUM_DATA (DRIVERBINDING_START_TOK),\r
63 PERF_INIT_CUM_DATA (DRIVERBINDING_SUPPORT_TOK)\r
64};\r
65\r
66/// Number of items for which we are gathering cumulative statistics.\r
67UINT32 const NumCum = sizeof(CumData) / sizeof(PERF_CUM_DATA);\r
68\r
88359546
ED
69PARAM_ITEM_LIST ParamList[] = {\r
70 {STRING_TOKEN (STR_DP_OPTION_QH), TypeFlag}, // -? Help\r
71 {STRING_TOKEN (STR_DP_OPTION_LH), TypeFlag}, // -h Help\r
72 {STRING_TOKEN (STR_DP_OPTION_UH), TypeFlag}, // -H Help\r
73 {STRING_TOKEN (STR_DP_OPTION_LV), TypeFlag}, // -v Verbose Mode\r
74 {STRING_TOKEN (STR_DP_OPTION_UA), TypeFlag}, // -A All, Cooked\r
75 {STRING_TOKEN (STR_DP_OPTION_UR), TypeFlag}, // -R RAW All\r
76 {STRING_TOKEN (STR_DP_OPTION_LS), TypeFlag}, // -s Summary\r
c06ad33e 77#if PROFILING_IMPLEMENTED\r
88359546
ED
78 {STRING_TOKEN (STR_DP_OPTION_UP), TypeFlag}, // -P Dump Profile Data\r
79 {STRING_TOKEN (STR_DP_OPTION_UT), TypeFlag}, // -T Dump Trace Data\r
c06ad33e 80#endif\r
88359546
ED
81 {STRING_TOKEN (STR_DP_OPTION_LX), TypeFlag}, // -x eXclude Cumulative Items\r
82 {STRING_TOKEN (STR_DP_OPTION_LN), TypeValue}, // -n # Number of records to display for A and R\r
83 {STRING_TOKEN (STR_DP_OPTION_LT), TypeValue} // -t # Threshold of interest\r
c06ad33e 84 };\r
85\r
9dd74618 86///@}\r
c06ad33e 87\r
88359546
ED
88/**\r
89 Transfer the param list value and get the command line parse.\r
90\r
91**/\r
92VOID\r
93InitialShellParamList( void )\r
94{\r
95 UINT32 ListIndex;\r
96 UINT32 ListLength; \r
97\r
98 //\r
99 // Allocate one more for the end tag.\r
100 //\r
101 ListLength = sizeof (ParamList) / sizeof (ParamList[0]) + 1; \r
102 DpParamList = AllocatePool (sizeof (SHELL_PARAM_ITEM) * ListLength);\r
103 ASSERT (DpParamList != NULL);\r
104 \r
105 for (ListIndex = 0; ListIndex < ListLength - 1; ListIndex ++)\r
106 { \r
107 DpParamList[ListIndex].Name = HiiGetString (gHiiHandle, ParamList[ListIndex].Token, NULL); \r
108 DpParamList[ListIndex].Type = ParamList[ListIndex].Type;\r
109 }\r
110 DpParamList[ListIndex].Name = NULL;\r
111 DpParamList[ListIndex].Type = TypeMax;\r
112}\r
113\r
9dd74618
ED
114/**\r
115 Display Usage and Help information.\r
116**/\r
c06ad33e 117VOID\r
118ShowHelp( void )\r
119{\r
120 PrintToken (STRING_TOKEN (STR_DP_HELP_HEAD));\r
121#if PROFILING_IMPLEMENTED\r
122 PrintToken (STRING_TOKEN (STR_DP_HELP_FLAGS));\r
123#else\r
124 PrintToken (STRING_TOKEN (STR_DP_HELP_FLAGS_2));\r
125#endif // PROFILING_IMPLEMENTED\r
126 PrintToken (STRING_TOKEN (STR_DP_HELP_PAGINATE));\r
127 PrintToken (STRING_TOKEN (STR_DP_HELP_VERBOSE));\r
128 PrintToken (STRING_TOKEN (STR_DP_HELP_EXCLUDE));\r
129 PrintToken (STRING_TOKEN (STR_DP_HELP_STAT));\r
130 PrintToken (STRING_TOKEN (STR_DP_HELP_ALL));\r
131 PrintToken (STRING_TOKEN (STR_DP_HELP_RAW));\r
132#if PROFILING_IMPLEMENTED\r
133 PrintToken (STRING_TOKEN (STR_DP_HELP_TRACE));\r
134 PrintToken (STRING_TOKEN (STR_DP_HELP_PROFILE));\r
135#endif // PROFILING_IMPLEMENTED\r
136 PrintToken (STRING_TOKEN (STR_DP_HELP_THRESHOLD));\r
137 PrintToken (STRING_TOKEN (STR_DP_HELP_COUNT));\r
138 PrintToken (STRING_TOKEN (STR_DP_HELP_HELP));\r
139 Print(L"\n");\r
140}\r
141\r
9dd74618
ED
142/**\r
143 Display the trailing Verbose information.\r
144**/\r
c06ad33e 145VOID\r
146DumpStatistics( void )\r
147{\r
148 EFI_STRING StringPtr;\r
88359546
ED
149 EFI_STRING StringPtrUnknown;\r
150 StringPtr = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_SECTION_STATISTICS), NULL);\r
151 StringPtrUnknown = HiiGetString (gHiiHandle, STRING_TOKEN (STR_ALIT_UNKNOWN), NULL); \r
c06ad33e 152 PrintToken( STRING_TOKEN (STR_DP_SECTION_HEADER),\r
88359546 153 (StringPtr == NULL) ? StringPtrUnknown : StringPtr);\r
c06ad33e 154\r
155 PrintToken( STRING_TOKEN (STR_DP_STATS_NUMTRACE), SummaryData.NumTrace);\r
156 PrintToken( STRING_TOKEN (STR_DP_STATS_NUMINCOMPLETE), SummaryData.NumIncomplete);\r
157 PrintToken( STRING_TOKEN (STR_DP_STATS_NUMPHASES), SummaryData.NumSummary);\r
158 PrintToken( STRING_TOKEN (STR_DP_STATS_NUMHANDLES), SummaryData.NumHandles, SummaryData.NumTrace - SummaryData.NumHandles);\r
159 PrintToken( STRING_TOKEN (STR_DP_STATS_NUMPEIMS), SummaryData.NumPEIMs);\r
160 PrintToken( STRING_TOKEN (STR_DP_STATS_NUMGLOBALS), SummaryData.NumGlobal);\r
161#if PROFILING_IMPLEMENTED\r
162 PrintToken( STRING_TOKEN (STR_DP_STATS_NUMPROFILE), SummaryData.NumProfile);\r
163#endif // PROFILING_IMPLEMENTED\r
88359546
ED
164 FreePool (StringPtr);\r
165 FreePool (StringPtrUnknown);\r
c06ad33e 166}\r
167\r
9dd74618
ED
168/** \r
169 Dump performance data.\r
170 \r
171 @param[in] ImageHandle The image handle.\r
172 @param[in] SystemTable The system table.\r
173 \r
174 @retval EFI_SUCCESS Command completed successfully.\r
175 @retval EFI_INVALID_PARAMETER Command usage error.\r
176 @retval value Unknown error.\r
177 \r
c06ad33e 178**/\r
179EFI_STATUS\r
180EFIAPI\r
181InitializeDp (\r
182 IN EFI_HANDLE ImageHandle,\r
183 IN EFI_SYSTEM_TABLE *SystemTable\r
184 )\r
185{\r
186 UINT64 Freq;\r
187 UINT64 Ticker;\r
88359546
ED
188 UINT32 ListIndex;\r
189 \r
c06ad33e 190 LIST_ENTRY *ParamPackage;\r
191 CONST CHAR16 *CmdLineArg;\r
192 EFI_STRING StringPtr;\r
193 UINTN Number2Display;\r
194\r
195 EFI_STATUS Status;\r
9dd74618
ED
196 BOOLEAN SummaryMode;\r
197 BOOLEAN VerboseMode;\r
198 BOOLEAN AllMode;\r
199 BOOLEAN RawMode;\r
200 BOOLEAN TraceMode;\r
201 BOOLEAN ProfileMode;\r
202 BOOLEAN ExcludeMode;\r
203\r
88359546
ED
204 EFI_STRING StringDpOptionQh;\r
205 EFI_STRING StringDpOptionLh;\r
206 EFI_STRING StringDpOptionUh;\r
207 EFI_STRING StringDpOptionLv;\r
208 EFI_STRING StringDpOptionUs;\r
209 EFI_STRING StringDpOptionLs;\r
210 EFI_STRING StringDpOptionUa;\r
211 EFI_STRING StringDpOptionUr;\r
212 EFI_STRING StringDpOptionUt;\r
213 EFI_STRING StringDpOptionUp;\r
214 EFI_STRING StringDpOptionLx;\r
215 EFI_STRING StringDpOptionLn;\r
216 EFI_STRING StringDpOptionLt;\r
217 \r
9dd74618
ED
218 SummaryMode = FALSE;\r
219 VerboseMode = FALSE;\r
220 AllMode = FALSE;\r
221 RawMode = FALSE;\r
222 TraceMode = FALSE;\r
223 ProfileMode = FALSE;\r
224 ExcludeMode = FALSE;\r
88359546
ED
225\r
226 StringDpOptionQh = NULL;\r
227 StringDpOptionLh = NULL;\r
228 StringDpOptionUh = NULL;\r
229 StringDpOptionLv = NULL;\r
230 StringDpOptionUs = NULL;\r
231 StringDpOptionLs = NULL;\r
232 StringDpOptionUa = NULL;\r
233 StringDpOptionUr = NULL;\r
234 StringDpOptionUt = NULL;\r
235 StringDpOptionUp = NULL;\r
236 StringDpOptionLx = NULL;\r
237 StringDpOptionLn = NULL;\r
238 StringDpOptionLt = NULL;\r
239 StringPtr = NULL;\r
240\r
c06ad33e 241 // Get DP's entry time as soon as possible.\r
242 // This is used as the Shell-Phase end time.\r
243 //\r
244 Ticker = GetPerformanceCounter ();\r
245\r
246 // Register our string package with HII and return the handle to it.\r
247 //\r
248 gHiiHandle = HiiAddPackages (&gEfiCallerIdGuid, ImageHandle, DPStrings, NULL);\r
249 ASSERT (gHiiHandle != NULL);\r
250\r
88359546
ED
251 // Initial the command list\r
252 //\r
253 InitialShellParamList ();\r
254 \r
c06ad33e 255/****************************************************************************\r
256**** Process Command Line arguments ****\r
257****************************************************************************/\r
258 Status = ShellCommandLineParse (DpParamList, &ParamPackage, NULL, TRUE);\r
259\r
260 if (EFI_ERROR(Status)) {\r
261 PrintToken (STRING_TOKEN (STR_DP_INVALID_ARG));\r
262 ShowHelp();\r
263 }\r
264 else {\r
88359546
ED
265 StringDpOptionQh = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_QH), NULL);\r
266 StringDpOptionLh = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_LH), NULL);\r
267 StringDpOptionUh = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_UH), NULL);\r
268 \r
269 if (ShellCommandLineGetFlag (ParamPackage, StringDpOptionQh) ||\r
270 ShellCommandLineGetFlag (ParamPackage, StringDpOptionLh) ||\r
271 ShellCommandLineGetFlag (ParamPackage, StringDpOptionUh))\r
c06ad33e 272 {\r
273 ShowHelp();\r
274 }\r
275 else {\r
88359546
ED
276 StringDpOptionLv = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_LV), NULL);\r
277 StringDpOptionUs = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_US), NULL);\r
278 StringDpOptionLs = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_LS), NULL);\r
279 StringDpOptionUa = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_UA), NULL);\r
280 StringDpOptionUr = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_UR), NULL);\r
281 StringDpOptionUt = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_UT), NULL);\r
282 StringDpOptionUp = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_UP), NULL);\r
283 StringDpOptionLx = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_LX), NULL);\r
284 StringDpOptionLn = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_LN), NULL);\r
285 StringDpOptionLt = HiiGetString (gHiiHandle, STRING_TOKEN (STR_DP_OPTION_LT), NULL);\r
286 \r
c06ad33e 287 // Boolean Options\r
88359546
ED
288 // \r
289 VerboseMode = ShellCommandLineGetFlag (ParamPackage, StringDpOptionLv);\r
aec905b7
ED
290 SummaryMode = (BOOLEAN) (ShellCommandLineGetFlag (ParamPackage, StringDpOptionUs) ||\r
291 ShellCommandLineGetFlag (ParamPackage, StringDpOptionLs));\r
88359546
ED
292 AllMode = ShellCommandLineGetFlag (ParamPackage, StringDpOptionUa);\r
293 RawMode = ShellCommandLineGetFlag (ParamPackage, StringDpOptionUr);\r
c06ad33e 294#if PROFILING_IMPLEMENTED\r
88359546
ED
295 TraceMode = ShellCommandLineGetFlag (ParamPackage, StringDpOptionUt);\r
296 ProfileMode = ShellCommandLineGetFlag (ParamPackage, StringDpOptionUp);\r
c06ad33e 297#endif // PROFILING_IMPLEMENTED\r
88359546 298 ExcludeMode = ShellCommandLineGetFlag (ParamPackage, StringDpOptionLx);\r
c06ad33e 299\r
300 // Options with Values\r
88359546 301 CmdLineArg = ShellCommandLineGetValue (ParamPackage, StringDpOptionLn);\r
c06ad33e 302 if (CmdLineArg == NULL) {\r
303 Number2Display = DEFAULT_DISPLAYCOUNT;\r
304 }\r
305 else {\r
306 Number2Display = StrDecimalToUintn(CmdLineArg);\r
307 if (Number2Display == 0) {\r
308 Number2Display = MAXIMUM_DISPLAYCOUNT;\r
309 }\r
310 }\r
88359546 311 CmdLineArg = ShellCommandLineGetValue (ParamPackage, StringDpOptionLt);\r
c06ad33e 312 if (CmdLineArg == NULL) {\r
313 mInterestThreshold = DEFAULT_THRESHOLD; // 1ms := 1,000 us\r
314 }\r
315 else {\r
316 mInterestThreshold = StrDecimalToUint64(CmdLineArg);\r
317 }\r
318 // Handle Flag combinations and default behaviors\r
319 // If both TraceMode and ProfileMode are FALSE, set them both to TRUE\r
320 if ((! TraceMode) && (! ProfileMode)) {\r
321 TraceMode = TRUE;\r
322#if PROFILING_IMPLEMENTED\r
323 ProfileMode = TRUE;\r
324#endif // PROFILING_IMPLEMENTED\r
325 }\r
326\r
327/****************************************************************************\r
328**** Timer specific processing ****\r
329****************************************************************************/\r
330 // Get the Performance counter characteristics:\r
331 // Freq = Frequency in Hz\r
332 // StartCount = Value loaded into the counter when it starts counting\r
333 // EndCount = Value counter counts to before it needs to be reset\r
334 //\r
335 Freq = GetPerformanceCounterProperties (&TimerInfo.StartCount, &TimerInfo.EndCount);\r
336\r
337 // Convert the Frequency from Hz to KHz\r
338 TimerInfo.Frequency = (UINT32)DivU64x32 (Freq, 1000);\r
339\r
340 // Determine in which direction the performance counter counts.\r
341 TimerInfo.CountUp = (BOOLEAN) (TimerInfo.EndCount >= TimerInfo.StartCount);\r
342\r
343/****************************************************************************\r
344**** Print heading ****\r
345****************************************************************************/\r
346 // print DP's build version\r
347 PrintToken (STRING_TOKEN (STR_DP_BUILD_REVISION), DP_MAJOR_VERSION, DP_MINOR_VERSION);\r
348\r
349 // print performance timer characteristics\r
350 PrintToken (STRING_TOKEN (STR_DP_KHZ), TimerInfo.Frequency); // Print Timer frequency in KHz\r
351\r
352 if ((VerboseMode) &&\r
353 (! RawMode)\r
354 ) {\r
355 StringPtr = HiiGetString (gHiiHandle,\r
aec905b7 356 (EFI_STRING_ID) (TimerInfo.CountUp ? STRING_TOKEN (STR_DP_UP) : STRING_TOKEN (STR_DP_DOWN)),\r
c06ad33e 357 NULL);\r
358 ASSERT (StringPtr != NULL);\r
359 PrintToken (STRING_TOKEN (STR_DP_TIMER_PROPERTIES), // Print Timer count range and direction\r
360 StringPtr,\r
361 TimerInfo.StartCount,\r
362 TimerInfo.EndCount\r
363 );\r
364 PrintToken (STRING_TOKEN (STR_DP_VERBOSE_THRESHOLD), mInterestThreshold);\r
365 }\r
366\r
367/* **************************************************************************\r
368**** Print Sections based on command line options\r
369****\r
370**** Option modes have the following priority:\r
371**** v Verbose -- Valid in combination with any other options\r
372**** t Threshold -- Modifies All, Raw, and Cooked output\r
373**** Default is 0 for All and Raw mode\r
374**** Default is DEFAULT_THRESHOLD for "Cooked" mode\r
375**** n Number2Display Used by All and Raw mode. Otherwise ignored.\r
376**** A All -- R and S options are ignored\r
377**** R Raw -- S option is ignored\r
378**** s Summary -- Modifies "Cooked" output only\r
379**** Cooked (Default)\r
380****\r
381**** The All, Raw, and Cooked modes are modified by the Trace and Profile\r
382**** options.\r
383**** !T && !P := (0) Default, Both are displayed\r
384**** T && !P := (1) Only Trace records are displayed\r
385**** !T && P := (2) Only Profile records are displayed\r
386**** T && P := (3) Same as Default, both are displayed\r
387****************************************************************************/\r
388 GatherStatistics();\r
389 if (AllMode) {\r
390 if (TraceMode) {\r
391 DumpAllTrace( Number2Display, ExcludeMode);\r
392 }\r
393 if (ProfileMode) {\r
394 DumpAllProfile( Number2Display, ExcludeMode);\r
395 }\r
396 }\r
397 else if (RawMode) {\r
398 if (TraceMode) {\r
399 DumpRawTrace( Number2Display, ExcludeMode);\r
400 }\r
401 if (ProfileMode) {\r
402 DumpRawProfile( Number2Display, ExcludeMode);\r
403 }\r
404 }\r
405 else {\r
406 //------------- Begin Cooked Mode Processing\r
407 if (TraceMode) {\r
408 ProcessPhases ( Ticker );\r
409 if ( ! SummaryMode) {\r
410 Status = ProcessHandles ( ExcludeMode);\r
411 if ( ! EFI_ERROR( Status)) {\r
412 ProcessPeims ( );\r
413 ProcessGlobal ( );\r
414 ProcessCumulative ();\r
415 }\r
416 }\r
417 }\r
418 if (ProfileMode) {\r
419 DumpAllProfile( Number2Display, ExcludeMode);\r
420 }\r
421 } //------------- End of Cooked Mode Processing\r
422 if ( VerboseMode || SummaryMode) {\r
423 DumpStatistics();\r
424 }\r
425 }\r
426 }\r
88359546
ED
427\r
428 // Free the memory allocate from HiiGetString\r
429 //\r
430 ListIndex = 0;\r
431 while (DpParamList[ListIndex].Name != NULL) {\r
432 FreePool (DpParamList[ListIndex].Name);\r
433 ListIndex ++;\r
434 } \r
435 FreePool (DpParamList);\r
cdd95292
SZ
436\r
437 SafeFreePool (StringDpOptionQh);\r
438 SafeFreePool (StringDpOptionLh);\r
439 SafeFreePool (StringDpOptionUh);\r
440 SafeFreePool (StringDpOptionLv);\r
441 SafeFreePool (StringDpOptionUs);\r
442 SafeFreePool (StringDpOptionLs);\r
443 SafeFreePool (StringDpOptionUa);\r
444 SafeFreePool (StringDpOptionUr);\r
445 SafeFreePool (StringDpOptionUt);\r
446 SafeFreePool (StringDpOptionUp);\r
447 SafeFreePool (StringDpOptionLx);\r
448 SafeFreePool (StringDpOptionLn);\r
449 SafeFreePool (StringDpOptionLt);\r
450 SafeFreePool (StringPtr);\r
451 SafeFreePool (mPrintTokenBuffer);\r
452\r
c06ad33e 453 HiiRemovePackages (gHiiHandle);\r
454 return Status;\r
455}\r