UefiCpuPkg/MpLib: fix potential overflow issue.

Current calculate timeout logic may have overflow if the input
timeout value too large. This patch fix this potential overflow
issue.

V2: Use local variable instead of call GetPerformanceCounterProperties
twice. Also correct some comments.

Cc: Michael Kinney <michael.d.kinney@intel.com>
Cc: Ruiyu Ni <ruiyu.ni@intel.com>
Contributed-under: TianoCore Contribution Agreement 1.1
Signed-off-by: Eric Dong <eric.dong@intel.com>
Reviewed-by: Michael Kinney <michael.d.kinney@intel.com>
This commit is contained in:
Eric Dong 2017-08-21 14:40:44 +08:00
parent 714c260301
commit 48cfb7c0f4
1 changed files with 32 additions and 9 deletions

View File

@ -1001,6 +1001,9 @@ CalculateTimeout (
OUT UINT64 *CurrentTime
)
{
UINT64 TimeoutInSeconds;
UINT64 TimestampCounterFreq;
//
// Read the current value of the performance counter
//
@ -1016,17 +1019,37 @@ CalculateTimeout (
//
// GetPerformanceCounterProperties () returns the timestamp counter's frequency
// in Hz. So multiply the return value with TimeoutInMicroseconds and then divide
// in Hz.
//
TimestampCounterFreq = GetPerformanceCounterProperties (NULL, NULL);
//
// Check the potential overflow before calculate the number of ticks for the timeout value.
//
if (DivU64x64Remainder (MAX_UINT64, TimeoutInMicroseconds, NULL) < TimestampCounterFreq) {
//
// Convert microseconds into seconds if direct multiplication overflows
//
TimeoutInSeconds = DivU64x32 (TimeoutInMicroseconds, 1000000);
//
// Assertion if the final tick count exceeds MAX_UINT64
//
ASSERT (DivU64x64Remainder (MAX_UINT64, TimeoutInSeconds, NULL) >= TimestampCounterFreq);
return MultU64x64 (TimestampCounterFreq, TimeoutInSeconds);
} else {
//
// No overflow case, multiply the return value with TimeoutInMicroseconds and then divide
// it by 1,000,000, to get the number of ticks for the timeout value.
//
return DivU64x32 (
MultU64x64 (
GetPerformanceCounterProperties (NULL, NULL),
TimestampCounterFreq,
TimeoutInMicroseconds
),
1000000
);
}
}
/**
Checks whether timeout expires.