2 Trace reporting for the Dp utility.
4 Copyright (c) 2009 - 2017, Intel Corporation. All rights reserved.<BR>
5 (C) Copyright 2015-2016 Hewlett Packard Enterprise Development LP<BR>
6 This program and the accompanying materials
7 are licensed and made available under the terms and conditions of the BSD License
8 which accompanies this distribution. The full text of the license may be found at
9 http://opensource.org/licenses/bsd-license.php
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
15 #include <Library/BaseLib.h>
16 #include <Library/BaseMemoryLib.h>
17 #include <Library/MemoryAllocationLib.h>
18 #include <Library/DebugLib.h>
19 #include <Library/UefiBootServicesTableLib.h>
20 #include <Library/PeCoffGetEntryPointLib.h>
21 #include <Library/PerformanceLib.h>
22 #include <Library/PrintLib.h>
23 #include <Library/HiiLib.h>
24 #include <Library/PcdLib.h>
26 #include <Guid/Performance.h>
30 #include "DpInternal.h"
33 Collect verbose statistics about the logged performance measurements.
35 General Summary information for all Trace measurements is gathered and
36 stored within the SummaryData structure. This information is both
37 used internally by subsequent reporting functions, and displayed
38 at the end of verbose reports.
40 @pre The SummaryData and CumData structures must be initialized
41 prior to calling this function.
43 @post The SummaryData and CumData structures contain statistics for the
44 current performance logs.
46 @param[in, out] CustomCumulativeData A pointer to the cumtom cumulative data.
51 IN OUT PERF_CUM_DATA
*CustomCumulativeData OPTIONAL
54 MEASUREMENT_RECORD Measurement
;
60 while ((LogEntryKey
= GetPerformanceMeasurementEx (
65 &Measurement
.StartTimeStamp
,
66 &Measurement
.EndTimeStamp
,
67 &Measurement
.Identifier
)) != 0)
69 ++SummaryData
.NumTrace
; // Count the number of TRACE Measurement records
70 if (Measurement
.EndTimeStamp
== 0) {
71 ++SummaryData
.NumIncomplete
; // Count the incomplete records
75 if (Measurement
.Handle
!= NULL
) {
76 ++SummaryData
.NumHandles
; // Count the number of measurements with non-NULL handles
79 if (IsPhase( &Measurement
)) {
80 ++SummaryData
.NumSummary
; // Count the number of major phases
82 else { // !IsPhase(...
83 if(Measurement
.Handle
== NULL
) {
84 ++SummaryData
.NumGlobal
;
88 if (AsciiStrnCmp (Measurement
.Token
, ALit_PEIM
, PERF_TOKEN_LENGTH
) == 0) {
89 ++SummaryData
.NumPEIMs
; // Count PEIM measurements
92 Duration
= GetDuration (&Measurement
);
93 TIndex
= GetCumulativeItem (&Measurement
);
95 CumData
[TIndex
].Duration
+= Duration
;
96 CumData
[TIndex
].Count
++;
97 if ( Duration
< CumData
[TIndex
].MinDur
) {
98 CumData
[TIndex
].MinDur
= Duration
;
100 if ( Duration
> CumData
[TIndex
].MaxDur
) {
101 CumData
[TIndex
].MaxDur
= Duration
;
106 // Collect the data for custom cumulative data.
108 if ((CustomCumulativeData
!= NULL
) && (AsciiStrCmp (Measurement
.Token
, CustomCumulativeData
->Name
) == 0)) {
109 CustomCumulativeData
->Duration
+= Duration
;
110 CustomCumulativeData
->Count
++;
111 if (Duration
< CustomCumulativeData
->MinDur
) {
112 CustomCumulativeData
->MinDur
= Duration
;
114 if (Duration
> CustomCumulativeData
->MaxDur
) {
115 CustomCumulativeData
->MaxDur
= Duration
;
122 Gather and print ALL Trace Records.
124 Displays all "interesting" Trace measurements in order.<BR>
125 The number of records displayed is controlled by:
126 - records with a duration less than mInterestThreshold microseconds are not displayed.
127 - No more than Limit records are displayed. A Limit of zero will not limit the output.
128 - If the ExcludeFlag is TRUE, records matching entries in the CumData array are not
131 @pre The mInterestThreshold global variable is set to the shortest duration to be printed.
132 The mGaugeString and mUnicodeToken global arrays are used for temporary string storage.
133 They must not be in use by a calling function.
135 @param[in] Limit The number of records to print. Zero is ALL.
136 @param[in] ExcludeFlag TRUE to exclude individual Cumulative items from display.
138 @retval EFI_SUCCESS The operation was successful.
139 @retval EFI_ABORTED The user aborts the operation.
140 @return Others from a call to gBS->LocateHandleBuffer().
145 IN BOOLEAN ExcludeFlag
148 MEASUREMENT_RECORD Measurement
;
151 const CHAR16
*IncFlag
;
157 EFI_HANDLE
*HandleBuffer
;
160 EFI_STRING StringPtrUnknown
;
162 StringPtrUnknown
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_ALIT_UNKNOWN
), NULL
);
163 IncFlag
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_DP_SECTION_ALL
), NULL
);
164 PrintToken( STRING_TOKEN (STR_DP_SECTION_HEADER
),
165 (IncFlag
== NULL
) ? StringPtrUnknown
: IncFlag
);
166 FreePool (StringPtrUnknown
);
168 // Get Handle information
170 Status
= gBS
->LocateHandleBuffer (AllHandles
, NULL
, NULL
, &HandleCount
, &HandleBuffer
);
171 if (EFI_ERROR (Status
)) {
172 PrintToken (STRING_TOKEN (STR_DP_HANDLES_ERROR
), Status
);
175 // We have successfully populated the HandleBuffer
176 // Display ALL Measurement Records
177 // Up to Limit lines displayed
178 // Display only records with Elapsed times >= mInterestThreshold
179 // Display driver names in Module field for records with Handles.
182 PrintToken (STRING_TOKEN (STR_DP_ALL_HEADR2
) );
183 PrintToken (STRING_TOKEN (STR_DP_ALL_DASHES2
) );
185 PrintToken (STRING_TOKEN (STR_DP_ALL_HEADR
) );
186 PrintToken (STRING_TOKEN (STR_DP_DASHES
) );
192 while ( WITHIN_LIMIT(Count
, Limit
) &&
193 ((LogEntryKey
= GetPerformanceMeasurementEx (
198 &Measurement
.StartTimeStamp
,
199 &Measurement
.EndTimeStamp
,
200 &Measurement
.Identifier
)) != 0)
203 ++Index
; // Count every record. First record is 1.
205 SafeFreePool ((VOID
*) IncFlag
);
206 if (Measurement
.EndTimeStamp
!= 0) {
207 Duration
= GetDuration (&Measurement
);
208 ElapsedTime
= DurationInMicroSeconds ( Duration
);
209 IncFlag
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_DP_COMPLETE
), NULL
);
212 IncFlag
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_DP_INCOMPLETE
), NULL
); // Mark incomplete records
214 if (((Measurement
.EndTimeStamp
!= 0) && (ElapsedTime
< mInterestThreshold
)) ||
215 ((ExcludeFlag
) && (GetCumulativeItem(&Measurement
) >= 0))
216 ) { // Ignore "uninteresting" or excluded records
219 ++Count
; // Count the number of records printed
221 // If Handle is non-zero, see if we can determine a name for the driver
222 AsciiStrToUnicodeStrS (Measurement
.Module
, mGaugeString
, ARRAY_SIZE (mGaugeString
)); // Use Module by default
223 AsciiStrToUnicodeStrS (Measurement
.Token
, mUnicodeToken
, ARRAY_SIZE (mUnicodeToken
));
224 if (Measurement
.Handle
!= NULL
) {
225 // See if the Handle is in the HandleBuffer
226 for (TIndex
= 0; TIndex
< HandleCount
; TIndex
++) {
227 if (Measurement
.Handle
== HandleBuffer
[TIndex
]) {
228 GetNameFromHandle (HandleBuffer
[TIndex
]);
234 if (AsciiStrnCmp (Measurement
.Token
, ALit_PEIM
, PERF_TOKEN_LENGTH
) == 0) {
235 UnicodeSPrint (mGaugeString
, sizeof (mGaugeString
), L
"%g", Measurement
.Handle
);
238 // Ensure that the argument strings are not too long.
239 mGaugeString
[DP_GAUGE_STRING_LENGTH
] = 0;
240 mUnicodeToken
[13] = 0;
243 PrintToken( STRING_TOKEN (STR_DP_ALL_VARS2
),
244 Index
, // 1 based, Which measurement record is being printed
250 Measurement
.Identifier
253 PrintToken( STRING_TOKEN (STR_DP_ALL_VARS
),
254 Index
, // 1 based, Which measurement record is being printed
262 if (ShellGetExecutionBreakFlag ()) {
263 Status
= EFI_ABORTED
;
268 if (HandleBuffer
!= NULL
) {
269 FreePool (HandleBuffer
);
271 SafeFreePool ((VOID
*) IncFlag
);
276 Gather and print Raw Trace Records.
278 All Trace measurements with a duration greater than or equal to
279 mInterestThreshold are printed without interpretation.
281 The number of records displayed is controlled by:
282 - records with a duration less than mInterestThreshold microseconds are not displayed.
283 - No more than Limit records are displayed. A Limit of zero will not limit the output.
284 - If the ExcludeFlag is TRUE, records matching entries in the CumData array are not
287 @pre The mInterestThreshold global variable is set to the shortest duration to be printed.
289 @param[in] Limit The number of records to print. Zero is ALL.
290 @param[in] ExcludeFlag TRUE to exclude individual Cumulative items from display.
292 @retval EFI_SUCCESS The operation was successful.
293 @retval EFI_ABORTED The user aborts the operation.
298 IN BOOLEAN ExcludeFlag
301 MEASUREMENT_RECORD Measurement
;
308 EFI_STRING StringPtr
;
309 EFI_STRING StringPtrUnknown
;
312 Status
= EFI_SUCCESS
;
314 StringPtrUnknown
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_ALIT_UNKNOWN
), NULL
);
315 StringPtr
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_DP_SECTION_RAWTRACE
), NULL
);
316 PrintToken( STRING_TOKEN (STR_DP_SECTION_HEADER
),
317 (StringPtr
== NULL
) ? StringPtrUnknown
: StringPtr
);
318 FreePool (StringPtr
);
319 FreePool (StringPtrUnknown
);
322 PrintToken (STRING_TOKEN (STR_DP_RAW_HEADR2
) );
323 PrintToken (STRING_TOKEN (STR_DP_RAW_DASHES2
) );
325 PrintToken (STRING_TOKEN (STR_DP_RAW_HEADR
) );
326 PrintToken (STRING_TOKEN (STR_DP_RAW_DASHES
) );
332 while ( WITHIN_LIMIT(Count
, Limit
) &&
333 ((LogEntryKey
= GetPerformanceMeasurementEx (
338 &Measurement
.StartTimeStamp
,
339 &Measurement
.EndTimeStamp
,
340 &Measurement
.Identifier
)) != 0)
343 ++Index
; // Count every record. First record is 1.
345 if (Measurement
.EndTimeStamp
!= 0) {
346 Duration
= GetDuration (&Measurement
);
347 ElapsedTime
= DurationInMicroSeconds ( Duration
);
349 if ((ElapsedTime
< mInterestThreshold
) ||
350 ((ExcludeFlag
) && (GetCumulativeItem(&Measurement
) >= 0))
351 ) { // Ignore "uninteresting" or Excluded records
354 ++Count
; // Count the number of records printed
357 PrintToken (STRING_TOKEN (STR_DP_RAW_VARS2
),
358 Index
, // 1 based, Which measurement record is being printed
360 Measurement
.StartTimeStamp
,
361 Measurement
.EndTimeStamp
,
364 Measurement
.Identifier
367 PrintToken (STRING_TOKEN (STR_DP_RAW_VARS
),
368 Index
, // 1 based, Which measurement record is being printed
370 Measurement
.StartTimeStamp
,
371 Measurement
.EndTimeStamp
,
376 if (ShellGetExecutionBreakFlag ()) {
377 Status
= EFI_ABORTED
;
385 Gather and print Major Phase metrics.
393 MEASUREMENT_RECORD Measurement
;
394 UINT64 BdsTimeoutValue
;
402 EFI_STRING StringPtr
;
404 EFI_STRING StringPtrUnknown
;
412 // Get Execution Phase Statistics
414 StringPtrUnknown
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_ALIT_UNKNOWN
), NULL
);
415 StringPtr
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_DP_SECTION_PHASES
), NULL
);
416 PrintToken( STRING_TOKEN (STR_DP_SECTION_HEADER
),
417 (StringPtr
== NULL
) ? StringPtrUnknown
: StringPtr
);
418 FreePool (StringPtr
);
419 FreePool (StringPtrUnknown
);
422 while ((LogEntryKey
= GetPerformanceMeasurementEx (
427 &Measurement
.StartTimeStamp
,
428 &Measurement
.EndTimeStamp
,
429 &Measurement
.Identifier
)) != 0)
431 if (Measurement
.EndTimeStamp
== 0) { // Skip "incomplete" records
434 Duration
= GetDuration (&Measurement
);
435 if ( Measurement
.Handle
!= NULL
436 && (AsciiStrnCmp (Measurement
.Token
, ALit_BdsTO
, PERF_TOKEN_LENGTH
) == 0)
439 BdsTimeoutValue
= Duration
;
440 } else if (AsciiStrnCmp (Measurement
.Token
, ALit_SEC
, PERF_TOKEN_LENGTH
) == 0) {
442 } else if (AsciiStrnCmp (Measurement
.Token
, ALit_PEI
, PERF_TOKEN_LENGTH
) == 0) {
444 } else if (AsciiStrnCmp (Measurement
.Token
, ALit_DXE
, PERF_TOKEN_LENGTH
) == 0) {
446 } else if (AsciiStrnCmp (Measurement
.Token
, ALit_BDS
, PERF_TOKEN_LENGTH
) == 0) {
453 // print SEC phase duration time
456 ElapsedTime
= DurationInMicroSeconds ( SecTime
); // Calculate elapsed time in microseconds
457 Total
+= DivU64x32 (ElapsedTime
, 1000); // Accumulate time in milliseconds
458 PrintToken (STRING_TOKEN (STR_DP_SEC_PHASE
), ElapsedTime
);
461 // print PEI phase duration time
464 ElapsedTime
= DivU64x32 (
466 (UINT32
)TimerInfo
.Frequency
468 Total
+= ElapsedTime
;
469 PrintToken (STRING_TOKEN (STR_DP_PHASE_DURATION
), ALit_PEI
, ElapsedTime
);
472 // print DXE phase duration time
475 ElapsedTime
= DivU64x32 (
477 (UINT32
)TimerInfo
.Frequency
479 Total
+= ElapsedTime
;
480 PrintToken (STRING_TOKEN (STR_DP_PHASE_DURATION
), ALit_DXE
, ElapsedTime
);
483 // print BDS phase duration time
486 ElapsedTime
= DivU64x32 (
488 (UINT32
)TimerInfo
.Frequency
490 Total
+= ElapsedTime
;
491 PrintToken (STRING_TOKEN (STR_DP_PHASE_DURATION
), ALit_BDS
, ElapsedTime
);
494 if (BdsTimeoutValue
> 0) {
495 ElapsedTime
= DivU64x32 (
497 (UINT32
)TimerInfo
.Frequency
499 PrintToken (STRING_TOKEN (STR_DP_PHASE_BDSTO
), ALit_BdsTO
, ElapsedTime
);
502 PrintToken (STRING_TOKEN (STR_DP_TOTAL_DURATION
), Total
);
506 Gather and print Handle data.
508 @param[in] ExcludeFlag TRUE to exclude individual Cumulative items from display.
510 @retval EFI_SUCCESS The operation was successful.
511 @retval EFI_ABORTED The user aborts the operation.
512 @return Others from a call to gBS->LocateHandleBuffer().
516 IN BOOLEAN ExcludeFlag
519 MEASUREMENT_RECORD Measurement
;
522 EFI_HANDLE
*HandleBuffer
;
523 EFI_STRING StringPtr
;
529 EFI_STRING StringPtrUnknown
;
531 StringPtrUnknown
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_ALIT_UNKNOWN
), NULL
);
532 StringPtr
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_DP_SECTION_DRIVERS
), NULL
);
533 PrintToken( STRING_TOKEN (STR_DP_SECTION_HEADER
),
534 (StringPtr
== NULL
) ? StringPtrUnknown
: StringPtr
);
535 FreePool (StringPtr
);
536 FreePool (StringPtrUnknown
);
538 Status
= gBS
->LocateHandleBuffer (AllHandles
, NULL
, NULL
, &HandleCount
, &HandleBuffer
);
539 if (EFI_ERROR (Status
)) {
540 PrintToken (STRING_TOKEN (STR_DP_HANDLES_ERROR
), Status
);
544 Print (L
"There are %,d Handles defined.\n", (Size
/ sizeof(HandleBuffer
[0])));
548 PrintToken (STRING_TOKEN (STR_DP_HANDLE_SECTION2
) );
550 PrintToken (STRING_TOKEN (STR_DP_HANDLE_SECTION
) );
552 PrintToken (STRING_TOKEN (STR_DP_DASHES
) );
556 while ((LogEntryKey
= GetPerformanceMeasurementEx (
561 &Measurement
.StartTimeStamp
,
562 &Measurement
.EndTimeStamp
,
563 &Measurement
.Identifier
)) != 0)
566 Duration
= GetDuration (&Measurement
);
567 ElapsedTime
= DurationInMicroSeconds ( Duration
);
568 if ((ElapsedTime
< mInterestThreshold
) ||
569 (Measurement
.EndTimeStamp
== 0) ||
570 (Measurement
.Handle
== NULL
) ||
571 ((ExcludeFlag
) && (GetCumulativeItem(&Measurement
) >= 0))
572 ) { // Ignore "uninteresting" or excluded records
575 mGaugeString
[0] = 0; // Empty driver name by default
576 AsciiStrToUnicodeStrS (Measurement
.Token
, mUnicodeToken
, ARRAY_SIZE (mUnicodeToken
));
577 // See if the Handle is in the HandleBuffer
578 for (Index
= 0; Index
< HandleCount
; Index
++) {
579 if (Measurement
.Handle
== HandleBuffer
[Index
]) {
580 GetNameFromHandle (HandleBuffer
[Index
]); // Name is put into mGaugeString
584 // Ensure that the argument strings are not too long.
585 mGaugeString
[DP_GAUGE_STRING_LENGTH
] = 0;
586 mUnicodeToken
[11] = 0;
587 if (mGaugeString
[0] != 0) {
588 // Display the record if it has a valid handle.
591 STRING_TOKEN (STR_DP_HANDLE_VARS2
),
592 Count
, // 1 based, Which measurement record is being printed
593 Index
+ 1, // 1 based, Which handle is being printed
597 Measurement
.Identifier
601 STRING_TOKEN (STR_DP_HANDLE_VARS
),
602 Count
, // 1 based, Which measurement record is being printed
603 Index
+ 1, // 1 based, Which handle is being printed
610 if (ShellGetExecutionBreakFlag ()) {
611 Status
= EFI_ABORTED
;
616 if (HandleBuffer
!= NULL
) {
617 FreePool (HandleBuffer
);
623 Gather and print PEIM data.
625 Only prints complete PEIM records
627 @retval EFI_SUCCESS The operation was successful.
628 @retval EFI_ABORTED The user aborts the operation.
635 MEASUREMENT_RECORD Measurement
;
638 EFI_STRING StringPtr
;
641 EFI_STRING StringPtrUnknown
;
644 Status
= EFI_SUCCESS
;
646 StringPtrUnknown
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_ALIT_UNKNOWN
), NULL
);
647 StringPtr
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_DP_SECTION_PEIMS
), NULL
);
648 PrintToken( STRING_TOKEN (STR_DP_SECTION_HEADER
),
649 (StringPtr
== NULL
) ? StringPtrUnknown
: StringPtr
);
650 FreePool (StringPtr
);
651 FreePool (StringPtrUnknown
);
654 PrintToken (STRING_TOKEN (STR_DP_PEIM_SECTION2
));
656 PrintToken (STRING_TOKEN (STR_DP_PEIM_SECTION
));
658 PrintToken (STRING_TOKEN (STR_DP_DASHES
));
661 while ((LogEntryKey
= GetPerformanceMeasurementEx (
666 &Measurement
.StartTimeStamp
,
667 &Measurement
.EndTimeStamp
,
668 &Measurement
.Identifier
)) != 0)
671 if ((Measurement
.EndTimeStamp
== 0) ||
672 (AsciiStrnCmp (Measurement
.Token
, ALit_PEIM
, PERF_TOKEN_LENGTH
) != 0)
677 Duration
= GetDuration (&Measurement
);
678 ElapsedTime
= DurationInMicroSeconds ( Duration
); // Calculate elapsed time in microseconds
679 if (ElapsedTime
>= mInterestThreshold
) {
680 // PEIM FILE Handle is the start address of its FFS file that contains its file guid.
682 PrintToken (STRING_TOKEN (STR_DP_PEIM_VARS2
),
683 TIndex
, // 1 based, Which measurement record is being printed
684 Measurement
.Handle
, // base address
685 Measurement
.Handle
, // file guid
687 Measurement
.Identifier
690 PrintToken (STRING_TOKEN (STR_DP_PEIM_VARS
),
691 TIndex
, // 1 based, Which measurement record is being printed
692 Measurement
.Handle
, // base address
693 Measurement
.Handle
, // file guid
698 if (ShellGetExecutionBreakFlag ()) {
699 Status
= EFI_ABORTED
;
707 Gather and print global data.
709 Strips out incomplete or "Execution Phase" records
710 Only prints records where Handle is NULL
711 Increment TIndex for every record, even skipped ones, so that we have an
712 indication of every measurement record taken.
714 @retval EFI_SUCCESS The operation was successful.
715 @retval EFI_ABORTED The user aborts the operation.
722 MEASUREMENT_RECORD Measurement
;
725 EFI_STRING StringPtr
;
727 UINTN Index
; // Index, or number, of the measurement record being processed
728 EFI_STRING StringPtrUnknown
;
731 Status
= EFI_SUCCESS
;
733 StringPtrUnknown
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_ALIT_UNKNOWN
), NULL
);
734 StringPtr
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_DP_SECTION_GENERAL
), NULL
);
735 PrintToken( STRING_TOKEN (STR_DP_SECTION_HEADER
),
736 (StringPtr
== NULL
) ? StringPtrUnknown
: StringPtr
);
737 FreePool (StringPtr
);
738 FreePool (StringPtrUnknown
);
741 PrintToken (STRING_TOKEN (STR_DP_GLOBAL_SECTION2
));
743 PrintToken (STRING_TOKEN (STR_DP_GLOBAL_SECTION
));
745 PrintToken (STRING_TOKEN (STR_DP_DASHES
));
750 while ((LogEntryKey
= GetPerformanceMeasurementEx (
755 &Measurement
.StartTimeStamp
,
756 &Measurement
.EndTimeStamp
,
757 &Measurement
.Identifier
)) != 0)
759 AsciiStrToUnicodeStrS (Measurement
.Module
, mGaugeString
, ARRAY_SIZE (mGaugeString
));
760 AsciiStrToUnicodeStrS (Measurement
.Token
, mUnicodeToken
, ARRAY_SIZE (mUnicodeToken
));
761 mGaugeString
[25] = 0;
762 mUnicodeToken
[31] = 0;
763 if ( ! ( IsPhase( &Measurement
) ||
764 (Measurement
.Handle
!= NULL
) ||
765 (Measurement
.EndTimeStamp
== 0)
768 Duration
= GetDuration (&Measurement
);
769 ElapsedTime
= DurationInMicroSeconds ( Duration
);
770 if (ElapsedTime
>= mInterestThreshold
) {
773 STRING_TOKEN (STR_DP_GLOBAL_VARS2
),
778 Measurement
.Identifier
782 STRING_TOKEN (STR_DP_GLOBAL_VARS
),
791 if (ShellGetExecutionBreakFlag ()) {
792 Status
= EFI_ABORTED
;
801 Gather and print cumulative data.
803 Traverse the measurement records and:<BR>
804 For each record with a Token listed in the CumData array:<BR>
805 - Update the instance count and the total, minimum, and maximum durations.
806 Finally, print the gathered cumulative statistics.
808 @param[in] CustomCumulativeData A pointer to the cumtom cumulative data.
813 IN PERF_CUM_DATA
*CustomCumulativeData OPTIONAL
816 UINT64 AvgDur
; // the computed average duration
820 EFI_STRING StringPtr
;
822 EFI_STRING StringPtrUnknown
;
824 StringPtrUnknown
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_ALIT_UNKNOWN
), NULL
);
825 StringPtr
= HiiGetString (gHiiHandle
, STRING_TOKEN (STR_DP_SECTION_CUMULATIVE
), NULL
);
826 PrintToken( STRING_TOKEN (STR_DP_SECTION_HEADER
),
827 (StringPtr
== NULL
) ? StringPtrUnknown
: StringPtr
);
828 FreePool (StringPtr
);
829 FreePool (StringPtrUnknown
);
831 PrintToken (STRING_TOKEN (STR_DP_CUMULATIVE_SECT_1
));
832 PrintToken (STRING_TOKEN (STR_DP_CUMULATIVE_SECT_2
));
833 PrintToken (STRING_TOKEN (STR_DP_DASHES
));
835 for ( TIndex
= 0; TIndex
< NumCum
; ++TIndex
) {
836 if (CumData
[TIndex
].Count
!= 0) {
837 AvgDur
= DivU64x32 (CumData
[TIndex
].Duration
, CumData
[TIndex
].Count
);
838 AvgDur
= DurationInMicroSeconds(AvgDur
);
839 Dur
= DurationInMicroSeconds(CumData
[TIndex
].Duration
);
840 MaxDur
= DurationInMicroSeconds(CumData
[TIndex
].MaxDur
);
841 MinDur
= DurationInMicroSeconds(CumData
[TIndex
].MinDur
);
843 PrintToken (STRING_TOKEN (STR_DP_CUMULATIVE_STATS
),
844 CumData
[TIndex
].Name
,
845 CumData
[TIndex
].Count
,
855 // Print the custom cumulative data.
857 if (CustomCumulativeData
!= NULL
) {
858 if (CustomCumulativeData
->Count
!= 0) {
859 AvgDur
= DivU64x32 (CustomCumulativeData
->Duration
, CustomCumulativeData
->Count
);
860 AvgDur
= DurationInMicroSeconds (AvgDur
);
861 Dur
= DurationInMicroSeconds (CustomCumulativeData
->Duration
);
862 MaxDur
= DurationInMicroSeconds (CustomCumulativeData
->MaxDur
);
863 MinDur
= DurationInMicroSeconds (CustomCumulativeData
->MinDur
);
870 PrintToken (STRING_TOKEN (STR_DP_CUMULATIVE_STATS
),
871 CustomCumulativeData
->Name
,
872 CustomCumulativeData
->Count
,