зеркало из https://github.com/microsoft/mu_plus.git
Merged PR 2124207: Adding hardware error record support into core
Adding report status code handler that collects certain errors and store on the flash for MS WHEA process. Related work items: #16620999, #17798962, #17798979, #18167784
This commit is contained in:
Родитель
063c57a491
Коммит
326963f3ba
|
@ -0,0 +1,110 @@
|
|||
/** @file -- MsWheaEarlyStorageLib.h
|
||||
|
||||
This header defines APIs to utilize special memory for MsWheaReport during early stage.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#ifndef __MS_WHEA_EARLY_STORAGE_LIB__
|
||||
#define __MS_WHEA_EARLY_STORAGE_LIB__
|
||||
|
||||
#include <Uefi/UefiBaseType.h>
|
||||
|
||||
#define EARLY_STORAGE_DEFAULT_VALUE 0xFF
|
||||
|
||||
/**
|
||||
|
||||
This routine returns the maximum number of bytes that can be stored in the PEI event store.
|
||||
|
||||
@retval Count The maximum number of bytes that can be stored in the MS WHEA store.
|
||||
|
||||
**/
|
||||
UINT8
|
||||
EFIAPI
|
||||
MsWheaEarlyStorageGetMaxSize (
|
||||
VOID
|
||||
);
|
||||
|
||||
/**
|
||||
|
||||
This routine reads the specified data region from the MS WHEA store.
|
||||
|
||||
@param[in] Ptr The pointer to hold intended read data
|
||||
@param[in] Size The size of intended read data
|
||||
@param[in] Offset The offset of read data, starting from
|
||||
MS_WHEA_EARLY_STORAGE_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaEarlyStorageRead (
|
||||
VOID *Ptr,
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
);
|
||||
|
||||
/**
|
||||
|
||||
This routine writes the specified data region from the MS WHEA store.
|
||||
|
||||
@param[in] Ptr The pointer to hold intended written data
|
||||
@param[in] Size The size of intended written data
|
||||
@param[in] Offset The offset of written data, starting from
|
||||
MS_WHEA_EARLY_STORAGE_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaEarlyStorageWrite (
|
||||
VOID *Ptr,
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
);
|
||||
|
||||
/**
|
||||
|
||||
This routine clears the specified data region from the MS WHEA store to PcdMsWheaEarlyStorageDefaultValue.
|
||||
|
||||
@param[in] Size The size of intended clear data
|
||||
@param[in] Offset The offset of clear data, starting from
|
||||
MS_WHEA_EARLY_STORAGE_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaEarlyStorageClear (
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
);
|
||||
|
||||
#endif // __MS_WHEA_EARLY_STORAGE_LIB__
|
|
@ -0,0 +1,128 @@
|
|||
/** @file -- MsWheaErrorStatus.h
|
||||
|
||||
This header file defines MsWheaReport expected/applied header components.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#ifndef __MS_WHEA_ERROR_STATUS__
|
||||
#define __MS_WHEA_ERROR_STATUS__
|
||||
|
||||
#include <Guid/Cper.h>
|
||||
#include <Pi/PiStatusCode.h>
|
||||
|
||||
#define MS_WHEA_ERROR_SIGNATURE SIGNATURE_32('W', 'H', 'E', 'A')
|
||||
|
||||
/**
|
||||
|
||||
Accepted phase values
|
||||
|
||||
**/
|
||||
#define MS_WHEA_PHASE_PEI 0x00
|
||||
#define MS_WHEA_PHASE_DXE 0x01
|
||||
#define MS_WHEA_PHASE_DXE_RUNTIME 0x02
|
||||
|
||||
/**
|
||||
|
||||
Accepted revision values
|
||||
|
||||
**/
|
||||
#define MS_WHEA_REV_0 0x0000
|
||||
#define MS_WHEA_REV_1 0x0001
|
||||
#define MS_WHEA_REV_WILDCARD 0x7FFF
|
||||
|
||||
#define MS_WHEA_ERROR_EARLY_STORAGE_STORE_FULL \
|
||||
0xAFAFAFAF
|
||||
|
||||
/**
|
||||
|
||||
Microsoft WHEA accepted error status type, other types will be ignored
|
||||
|
||||
**/
|
||||
#define MS_WHEA_ERROR_STATUS_TYPE (EFI_ERROR_MAJOR | EFI_ERROR_CODE)
|
||||
|
||||
typedef UINT16 MS_WHEA_REV;
|
||||
typedef UINT16 MS_WHEA_ERROR_PHASE;
|
||||
|
||||
/**
|
||||
|
||||
Minimal information reported for reported status codes under fatal severity (Rev0 and above).
|
||||
|
||||
Note: All the upcoming Early Storage entry should start with the following parameters
|
||||
|
||||
Rev: Revision used for parser to identify supplied payload format.
|
||||
Phase: Phase of boot process reporting module, will be filled at the backend.
|
||||
ErrorStatusCode: Reported Status Code Value upon calling ReportStatusCode*
|
||||
|
||||
**/
|
||||
typedef struct MS_WHEA_EARLY_STORAGE_ENTRY_V0_T_DEF {
|
||||
MS_WHEA_REV Rev;
|
||||
MS_WHEA_ERROR_PHASE Phase;
|
||||
UINT32 ErrorStatusCode;
|
||||
} MS_WHEA_EARLY_STORAGE_ENTRY_V0, MS_WHEA_EARLY_STORAGE_ENTRY_COMMON;
|
||||
|
||||
/**
|
||||
|
||||
Minimal information reported for reported status codes under Rev 1 and fatal severity
|
||||
|
||||
Rev: Revision used for parser to identify supplied payload format.
|
||||
Phase: Phase of boot process reporting module, will be filled at the backend.
|
||||
ErrorStatusCode: Reported Status Code Value upon calling ReportStatusCode*
|
||||
CriticalInfo: Critical information to be filled by caller
|
||||
ReporterID: ReporterID to be filled by caller to reporter identification purpose
|
||||
|
||||
**/
|
||||
typedef struct MS_WHEA_EARLY_STORAGE_ENTRY_V1_T_DEF {
|
||||
MS_WHEA_REV Rev;
|
||||
MS_WHEA_ERROR_PHASE Phase;
|
||||
UINT32 ErrorStatusCode;
|
||||
UINT64 CriticalInfo;
|
||||
UINT64 ReporterID;
|
||||
} MS_WHEA_EARLY_STORAGE_ENTRY_V1;
|
||||
|
||||
/**
|
||||
|
||||
Microsoft WHEA error list entry header, to be included as error header when using
|
||||
ReportStatusCodeWithExtendedData.
|
||||
|
||||
Signature: 'WHEA', indocator of WHEA compliance
|
||||
Rev: Revision used for parser to identify supplied payload format.
|
||||
Phase: Phase of boot process reporting module, will be filled at the backend.
|
||||
ErrorStatusCode: Reported Status Code Value upon calling ReportStatusCode*
|
||||
CriticalInfo: Critical information to be filled by caller, Ignored for Rev: 0 and wildcard
|
||||
ReporterID: ReporterID to be filled by caller to reporter identification purpose, ignored for
|
||||
Rev: 0 and wildcard
|
||||
|
||||
**/
|
||||
typedef struct MS_WHEA_ERROR_HDR_T_DEF {
|
||||
UINT32 Signature;
|
||||
MS_WHEA_REV Rev;
|
||||
MS_WHEA_ERROR_PHASE Phase;
|
||||
UINT32 ErrorSeverity;
|
||||
UINT32 Reserved;
|
||||
UINT64 CriticalInfo;
|
||||
UINT64 ReporterID;
|
||||
} MS_WHEA_ERROR_HDR;
|
||||
|
||||
#endif // __MS_WHEA_ERROR_STATUS__
|
|
@ -0,0 +1,311 @@
|
|||
/** @file -- MsWheaEarlyStorageLib.c
|
||||
|
||||
This header defines APIs to utilize special memory for MsWheaReport during
|
||||
early stage.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/IoLib.h>
|
||||
#include <Library/PcdLib.h>
|
||||
#include <Library/MsWheaEarlyStorageLib.h>
|
||||
|
||||
#define PCAT_RTC_LO_ADDRESS_PORT 0x70
|
||||
#define PCAT_RTC_LO_DATA_PORT 0x71
|
||||
#define PCAT_RTC_HI_ADDRESS_PORT 0x72
|
||||
#define PCAT_RTC_HI_DATA_PORT 0x73
|
||||
|
||||
#define MS_WHEA_EARLY_STORAGE_OFFSET 0x40
|
||||
|
||||
/**
|
||||
|
||||
This routine has the highest previlege to read any byte(s) on the CMOS
|
||||
|
||||
@param[in] Ptr The pointer to hold read data
|
||||
@param[in] Size The size of intended read data
|
||||
@param[in] Offset The offset of read data, starting from the beginning of CMOS
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
__MsWheaCMOSRawRead (
|
||||
VOID *Ptr,
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
)
|
||||
{
|
||||
UINT8 mIndex;
|
||||
UINT8 i;
|
||||
UINT8 *mBuf;
|
||||
EFI_STATUS Status;
|
||||
|
||||
mBuf = Ptr;
|
||||
if ((mBuf == NULL) ||
|
||||
(Size == 0) ||
|
||||
((UINT8)(PcdGet32(PcdMsWheaReportPcatCapacity) - Size) < Offset)) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
for (i = 0; i < Size; i++) {
|
||||
mIndex = Offset + i;
|
||||
if ((mIndex >= 0) && (mIndex <= 127)) {
|
||||
IoWrite8(PCAT_RTC_LO_ADDRESS_PORT, mIndex);
|
||||
mBuf[i] = IoRead8(PCAT_RTC_LO_DATA_PORT);
|
||||
}
|
||||
else {
|
||||
IoWrite8(PCAT_RTC_HI_ADDRESS_PORT, mIndex);
|
||||
mBuf[i] = IoRead8(PCAT_RTC_HI_DATA_PORT);
|
||||
}
|
||||
}
|
||||
Status = EFI_SUCCESS;
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine has the highest previlege to write any byte(s) on the CMOS
|
||||
|
||||
@param[in] Ptr The pointer to hold intended written data
|
||||
@param[in] Size The size of intended written data
|
||||
@param[in] Offset The offset of written data, starting from the beginning of CMOS
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
__MsWheaCMOSRawWrite (
|
||||
VOID *Ptr,
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
)
|
||||
{
|
||||
UINT8 mIndex;
|
||||
UINT8 i;
|
||||
UINT8 *mBuf;
|
||||
EFI_STATUS Status;
|
||||
|
||||
mBuf = Ptr;
|
||||
if ((mBuf == NULL) ||
|
||||
(Size == 0) ||
|
||||
((UINT8)(PcdGet32(PcdMsWheaReportPcatCapacity) - Size) < Offset)) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
for (i = 0; i < Size; i++) {
|
||||
mIndex = Offset + i;
|
||||
if ((mIndex >= 0) && (mIndex <= 127)) {
|
||||
IoWrite8(PCAT_RTC_LO_ADDRESS_PORT, mIndex);
|
||||
IoWrite8(PCAT_RTC_LO_DATA_PORT, mBuf[i]);
|
||||
}
|
||||
else {
|
||||
IoWrite8(PCAT_RTC_HI_ADDRESS_PORT, mIndex);
|
||||
IoWrite8(PCAT_RTC_HI_DATA_PORT, mBuf[i]);
|
||||
}
|
||||
}
|
||||
Status = EFI_SUCCESS;
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine has the highest previlege to 'clear' any byte(s) on the CMOS
|
||||
|
||||
@param[in] Size The size of intended clear region
|
||||
@param[in] Offset The offset of clear data, starting from the beginning of CMOS
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
__MsWheaCMOSRawClear (
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
)
|
||||
{
|
||||
UINT8 mIndex;
|
||||
UINT8 i;
|
||||
EFI_STATUS Status;
|
||||
|
||||
if ((Size == 0) ||
|
||||
((UINT8)(PcdGet32(PcdMsWheaReportPcatCapacity) - Size) < Offset)) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
for (i = 0; i < Size; i++) {
|
||||
mIndex = Offset + i;
|
||||
if ((mIndex >= 0) && (mIndex <= 127)) {
|
||||
IoWrite8(PCAT_RTC_LO_ADDRESS_PORT, mIndex);
|
||||
IoWrite8(PCAT_RTC_LO_DATA_PORT, PcdGet8(PcdMsWheaEarlyStorageDefaultValue));
|
||||
}
|
||||
else {
|
||||
IoWrite8(PCAT_RTC_HI_ADDRESS_PORT, mIndex);
|
||||
IoWrite8(PCAT_RTC_HI_DATA_PORT, PcdGet8(PcdMsWheaEarlyStorageDefaultValue));
|
||||
}
|
||||
}
|
||||
Status = EFI_SUCCESS;
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine clears all bytes in Data region
|
||||
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
MsWheaCMOSStoreClearAll (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
__MsWheaCMOSRawClear(MsWheaEarlyStorageGetMaxSize(), MS_WHEA_EARLY_STORAGE_OFFSET);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine returns the maximum number of bytes that can be stored in the PEI event store.
|
||||
|
||||
@retval Count The maximum number of bytes that can be stored in the MS WHEA store.
|
||||
|
||||
**/
|
||||
UINT8
|
||||
EFIAPI
|
||||
MsWheaEarlyStorageGetMaxSize (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
return (UINT8)((PcdGet32(PcdMsWheaReportPcatCapacity) - (MS_WHEA_EARLY_STORAGE_OFFSET)) & 0xFF);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine reads the specified data region from the MS WHEA store.
|
||||
|
||||
@param[in] Ptr The pointer to hold intended read data
|
||||
@param[in] Size The size of intended read data
|
||||
@param[in] Offset The offset of read data, starting from
|
||||
MS_WHEA_EARLY_STORAGE_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaEarlyStorageRead (
|
||||
VOID *Ptr,
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
if (Offset >= MsWheaEarlyStorageGetMaxSize()) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = __MsWheaCMOSRawRead(Ptr, Size, MS_WHEA_EARLY_STORAGE_OFFSET + Offset);
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine writes the specified data region from the MS WHEA store.
|
||||
|
||||
@param[in] Ptr The pointer to hold intended written data
|
||||
@param[in] Size The size of intended written data
|
||||
@param[in] Offset The offset of written data, starting from
|
||||
MS_WHEA_EARLY_STORAGE_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaEarlyStorageWrite (
|
||||
VOID *Ptr,
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
if (Offset >= MsWheaEarlyStorageGetMaxSize()) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = __MsWheaCMOSRawWrite(Ptr, Size, MS_WHEA_EARLY_STORAGE_OFFSET + Offset);
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine clears the specified data region from the MS WHEA store to PcdMsWheaEarlyStorageDefaultValue.
|
||||
|
||||
@param[in] Size The size of intended clear data
|
||||
@param[in] Offset The offset of clear data, starting from
|
||||
MS_WHEA_EARLY_STORAGE_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaEarlyStorageClear (
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
if (Offset >= MsWheaEarlyStorageGetMaxSize()) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = __MsWheaCMOSRawClear(Size, MS_WHEA_EARLY_STORAGE_OFFSET + Offset);
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
|
@ -0,0 +1,64 @@
|
|||
## @file -- MsWheaEarlyStorageLib.inf
|
||||
#
|
||||
# This header defines APIs to utilize special memory for MsWheaReport during
|
||||
# early stage.
|
||||
#
|
||||
# Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
# All rights reserved.
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
# 1. Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions and the following disclaimer.
|
||||
# 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions and the following disclaimer in the documentation
|
||||
# and/or other materials provided with the distribution.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
# IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
# LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
# OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
# ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
##
|
||||
|
||||
[Defines]
|
||||
INF_VERSION = 0x00010005
|
||||
BASE_NAME = MsWheaEarlyStorageLib
|
||||
FILE_GUID = E3E9F981-545E-4AF1-ACFA-44578AB7D159
|
||||
MODULE_TYPE = BASE
|
||||
VERSION_STRING = 1.0
|
||||
LIBRARY_CLASS = MsWheaEarlyStorageLib
|
||||
|
||||
#
|
||||
# The following information is for reference only and not required by the
|
||||
# build tools.
|
||||
#
|
||||
# VALID_ARCHITECTURES = IA32 X64 IPF EBC
|
||||
#
|
||||
|
||||
[Sources]
|
||||
MsWheaEarlyStorageLib.c
|
||||
|
||||
[Packages]
|
||||
MdePkg/MdePkg.dec
|
||||
MdeModulePkg/MdeModulePkg.dec
|
||||
MsWheaPkg/MsWheaPkg.dec
|
||||
|
||||
[LibraryClasses]
|
||||
BaseLib
|
||||
DebugLib
|
||||
IoLib
|
||||
PcdLib
|
||||
|
||||
[Protocols]
|
||||
|
||||
[Pcd]
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaEarlyStorageDefaultValue
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaReportPcatCapacity
|
||||
|
||||
[Guids]
|
|
@ -0,0 +1,53 @@
|
|||
## @file
|
||||
# Package declaration file for Microsoft WHEA Package
|
||||
#
|
||||
# Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
# All rights reserved.
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
# 1. Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions and the following disclaimer.
|
||||
# 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions and the following disclaimer in the documentation
|
||||
# and/or other materials provided with the distribution.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
# IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
# LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
# OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
# ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
##
|
||||
|
||||
|
||||
[Defines]
|
||||
DEC_SPECIFICATION = 0x00010017
|
||||
PACKAGE_NAME = MsWheaPkg
|
||||
PACKAGE_VERSION = 0.1
|
||||
PACKAGE_GUID = B34D6A40-334D-4596-836E-ECCD0409CD2D
|
||||
|
||||
[Guids]
|
||||
gMsWheaPkgTokenSpaceGuid = { 0x9b859fdb, 0xcae9, 0x44f8, { 0x80, 0x86, 0xbb, 0xc0, 0xb2, 0x69, 0x3a, 0x1d } }
|
||||
gMsWheaReportServiceGuid = { 0x8efebc4a, 0x5222, 0x409c, { 0xa5, 0x9f, 0x6f, 0x06, 0xdd, 0xb7, 0x96, 0x78 } }
|
||||
|
||||
[Includes]
|
||||
Include
|
||||
|
||||
[Protocols]
|
||||
|
||||
[Ppis]
|
||||
|
||||
[LibraryClasses]
|
||||
MsWheaEarlyStorageLib|Include/Library/MsWheaEarlyStorageLib.h
|
||||
|
||||
[PcdsFeatureFlag]
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaReportTestEnable|FALSE|BOOLEAN|0x00000001
|
||||
|
||||
[PcdsFixedAtBuild]
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaReportPcatCapacity|0x00000100|UINT32|0x00000002
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaEarlyStorageDefaultValue|0xFF|UINT8|0x00000003
|
|
@ -0,0 +1,141 @@
|
|||
## @file
|
||||
# Microsoft Whea Package, routing ReportStatusCode here to store as Hardware
|
||||
# Error Record.
|
||||
#
|
||||
# Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
# All rights reserved.
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
# 1. Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions and the following disclaimer.
|
||||
# 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions and the following disclaimer in the documentation
|
||||
# and/or other materials provided with the distribution.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
# IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
# LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
# OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
# ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
##
|
||||
|
||||
################################################################################
|
||||
[Defines]
|
||||
PLATFORM_NAME = MsWheaPkg
|
||||
PLATFORM_GUID = EB995458-4F79-49F8-8F1F-977B581701D5
|
||||
PLATFORM_VERSION = 0.1
|
||||
DSC_SPECIFICATION = 0x00010005
|
||||
OUTPUT_DIRECTORY = Build/MsWheaPkg
|
||||
SUPPORTED_ARCHITECTURES = IA32|X64
|
||||
BUILD_TARGETS = DEBUG|RELEASE
|
||||
SKUID_IDENTIFIER = DEFAULT
|
||||
|
||||
################################################################################
|
||||
#
|
||||
# Library Class section - list of all Library Classes needed by this Platform.
|
||||
#
|
||||
################################################################################
|
||||
[LibraryClasses]
|
||||
#
|
||||
# Entry Point Libraries
|
||||
#
|
||||
UefiDriverEntryPoint|MdePkg/Library/UefiDriverEntryPoint/UefiDriverEntryPoint.inf
|
||||
#
|
||||
# Common Libraries
|
||||
#
|
||||
BaseLib|MdePkg/Library/BaseLib/BaseLib.inf
|
||||
BaseMemoryLib|MdePkg/Library/BaseMemoryLib/BaseMemoryLib.inf
|
||||
|
||||
##MSCHANGE Begin
|
||||
!if $(TARGET) == DEBUG
|
||||
#if debug is enabled provide StackCookie support lib so that we can link to /GS exports
|
||||
RngLib|MdePkg/Library/BaseRngLib/BaseRngLib.inf
|
||||
NULL|MdePkg/Library/BaseBinSecurityLibRng/BaseBinSecurityLibRng.inf
|
||||
!endif
|
||||
##MSCHANGE End
|
||||
|
||||
|
||||
UefiLib|MdePkg/Library/UefiLib/UefiLib.inf
|
||||
PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf
|
||||
PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
|
||||
MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
|
||||
UefiBootServicesTableLib|MdePkg/Library/UefiBootServicesTableLib/UefiBootServicesTableLib.inf
|
||||
UefiRuntimeServicesTableLib|MdePkg/Library/UefiRuntimeServicesTableLib/UefiRuntimeServicesTableLib.inf
|
||||
DebugLib|MdePkg/Library/BaseDebugLibNull/BaseDebugLibNull.inf
|
||||
DebugPrintErrorLevelLib|MdePkg/Library/BaseDebugPrintErrorLevelLib/BaseDebugPrintErrorLevelLib.inf
|
||||
DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
|
||||
ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
|
||||
OemHookStatusCodeLib|MdeModulePkg/Library/OemHookStatusCodeLibNull/OemHookStatusCodeLibNull.inf
|
||||
HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
|
||||
SerialPortLib|MdePkg/Library/BaseSerialPortLibNull/BaseSerialPortLibNull.inf
|
||||
IoLib|MdePkg/Library/BaseIoLibIntrinsic/BaseIoLibIntrinsic.inf
|
||||
|
||||
MsWheaEarlyStorageLib|MsWheaPkg/Library/MsWheaEarlyStorageLib/MsWheaEarlyStorageLib.inf
|
||||
|
||||
# UNIT TEST APPLICATION RELATED
|
||||
[LibraryClasses.X64.UEFI_APPLICATION]
|
||||
UnitTestLib|MsUnitTestPkg/Library/UnitTestLib/UnitTestLib.inf
|
||||
UnitTestAssertLib|MsUnitTestPkg/Library/UnitTestAssertLib/UnitTestAssertLib.inf
|
||||
UnitTestLogLib|MsUnitTestPkg/Library/UnitTestLogLib/UnitTestLogLib.inf
|
||||
UnitTestPersistenceLib|MsUnitTestPkg/Library/UnitTestPersistenceLibNull/UnitTestPersistenceLibNull.inf
|
||||
UnitTestBootUsbLib|MsUnitTestPkg/Library/UnitTestBootUsbClassLib/UnitTestBootUsbClassLib.inf
|
||||
UnitTestResultReportLib|MsUnitTestPkg/Library/UnitTestResultReportPlainTextOutputLib/UnitTestResultReportLib.inf
|
||||
|
||||
UefiBootManagerLib|MdeModulePkg/Library/UefiBootManagerLib/UefiBootManagerLib.inf
|
||||
#TimerLib|MdePkg/Library/BaseTimerLibNullTemplate/BaseTimerLibNullTemplate.inf
|
||||
PerformanceLib|MdePkg/Library/BasePerformanceLibNull/BasePerformanceLibNull.inf
|
||||
Performance2Lib|MdePkg/Library/BasePerformance2LibNull/BasePerformance2LibNull.inf
|
||||
PeCoffGetEntryPointLib|MdePkg/Library/BasePeCoffGetEntryPointLib/BasePeCoffGetEntryPointLib.inf
|
||||
DxeServicesTableLib|MdePkg/Library/DxeServicesTableLib/DxeServicesTableLib.inf
|
||||
DxeServicesLib|MdePkg/Library/DxeServicesLib/DxeServicesLib.inf
|
||||
HiiLib|MdeModulePkg/Library/UefiHiiLib/UefiHiiLib.inf
|
||||
SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf
|
||||
UefiHiiServicesLib|MdeModulePkg/Library/UefiHiiServicesLib/UefiHiiServicesLib.inf
|
||||
|
||||
ShellLib|ShellPkg/Library/UefiShellLib/UefiShellLib.inf
|
||||
FileHandleLib|MdePkg/Library/UefiFileHandleLib/UefiFileHandleLib.inf
|
||||
UefiApplicationEntryPoint|MdePkg/Library/UefiApplicationEntryPoint/UefiApplicationEntryPoint.inf
|
||||
|
||||
[LibraryClasses.common.PEIM]
|
||||
PeimEntryPoint|MdePkg/Library/PeimEntryPoint/PeimEntryPoint.inf
|
||||
PeiServicesLib|MdePkg/Library/PeiServicesLib/PeiServicesLib.inf
|
||||
PeiServicesTablePointerLib|MdePkg/Library/PeiServicesTablePointerLib/PeiServicesTablePointerLib.inf
|
||||
HobLib|MdePkg/Library/PeiHobLib/PeiHobLib.inf
|
||||
MemoryAllocationLib|MdePkg/Library/PeiMemoryAllocationLib/PeiMemoryAllocationLib.inf
|
||||
ReportStatusCodeLib|MdeModulePkg/Library/PeiReportStatusCodeLib/PeiReportStatusCodeLib.inf
|
||||
|
||||
[PcdsFixedAtBuild]
|
||||
# Enabled support for HwErrRec and increased the size of HwErrRec region on flash
|
||||
gEfiMdePkgTokenSpaceGuid.PcdHardwareErrorRecordLevel|1
|
||||
gEfiMdeModulePkgTokenSpaceGuid.PcdHwErrStorageSize|0x00001000
|
||||
# This is copied from MdePkg.dec for self reference
|
||||
# gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize|0x400
|
||||
|
||||
################################################################################
|
||||
#
|
||||
# Components section - list of all Components needed by this Platform.
|
||||
#
|
||||
################################################################################
|
||||
[Components]
|
||||
MsWheaPkg/Library/MsWheaEarlyStorageLib/MsWheaEarlyStorageLib.inf
|
||||
|
||||
[Components.IA32]
|
||||
MsWheaPkg/MsWheaReport/Pei/MsWheaReportPei.inf {
|
||||
<LibraryClasses>
|
||||
DebugLib|MdePkg/Library/BaseDebugLibSerialPort/BaseDebugLibSerialPort.inf
|
||||
}
|
||||
|
||||
[Components.X64]
|
||||
MsWheaPkg/MsWheaReport/Dxe/MsWheaReportDxe.inf
|
||||
|
||||
# UNIT TEST APPLICATION RELATED
|
||||
MsWheaPkg/UnitTests/MsWheaReportUnitTestApp/MsWheaReportUnitTestApp.inf
|
||||
|
||||
[BuildOptions]
|
||||
*_*_*_CC_FLAGS = -D DISABLE_NEW_DEPRECATED_INTERFACES
|
|
@ -0,0 +1,451 @@
|
|||
/** @file -- MsWheaReportDxe.c
|
||||
|
||||
This Dxe driver will produce a RSC listener that listens to reported status codes.
|
||||
|
||||
Certains errors will be stored to flash upon reproting, under gEfiHardwareErrorVariableGuid
|
||||
with VarName "HwErrRecXXXX", where "XXXX" are hexadecimal digits;
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#include <Uefi.h>
|
||||
#include <Library/UefiLib.h>
|
||||
#include <Library/HobLib.h>
|
||||
#include <Library/PcdLib.h>
|
||||
#include <Library/ReportStatusCodeLib.h>
|
||||
#include <Protocol/ReportStatusCodeHandler.h>
|
||||
#include <Library/UefiDriverEntryPoint.h>
|
||||
#include <Library/UefiBootServicesTableLib.h>
|
||||
#include <Library/UefiRuntimeServicesTableLib.h>
|
||||
#include "MsWheaReportCommon.h"
|
||||
#include "MsWheaReportHER.h"
|
||||
#include "MsWheaEarlyStorageMgr.h"
|
||||
#include "MsWheaReportList.h"
|
||||
|
||||
STATIC EFI_RSC_HANDLER_PROTOCOL *mRscHandlerProtocol = NULL;
|
||||
|
||||
STATIC EFI_EVENT mWriteArchAvailEvent = NULL;
|
||||
STATIC EFI_EVENT mVarArchAvailEvent = NULL;
|
||||
STATIC EFI_EVENT mExitBootServicesEvent = NULL;
|
||||
|
||||
STATIC BOOLEAN mWriteArchAvailable = FALSE;
|
||||
STATIC BOOLEAN mVarArchAvailable = FALSE;
|
||||
STATIC BOOLEAN mExitBootHasOccurred = FALSE;
|
||||
|
||||
STATIC LIST_ENTRY mMsWheaEntryList;
|
||||
|
||||
/**
|
||||
Handler function that validates input arguments, and store on flash/CMOS for OS to process.
|
||||
|
||||
Note: It is the reporter's responsibility to make sure the format of each blob is compliant
|
||||
with specifications. Malformed data will fail the entire reporting.
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
@param[in] PayloadPtr The pointer to reported error block payload, the content will be copied
|
||||
@param[in] PayloadSize The size of reported error block payload
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_ACCESS_DENIED Exit boot has locked the report function
|
||||
@retval EFI_OUT_OF_RESOURCES List cannot make the space for requested error block payload
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero length payload detected
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaReportHandlerDxe(
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN VOID *PayloadPtr,
|
||||
IN UINT32 PayloadSize
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": enter...\n"));
|
||||
|
||||
if (mExitBootHasOccurred != FALSE) {
|
||||
// This function is locked due to Exit Boot has occurred
|
||||
Status = EFI_ACCESS_DENIED;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Input argument sanity check
|
||||
if ((PayloadPtr == NULL) ||
|
||||
(PayloadSize == 0) ||
|
||||
(MsWheaEntryMD == NULL)) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if ((mWriteArchAvailable != FALSE) && (mVarArchAvailable != FALSE)) {
|
||||
// Variable service is ready, store to HwErrRecXXXX
|
||||
Status = MsWheaReportHERAdd(MsWheaEntryMD, PayloadPtr, PayloadSize);
|
||||
}
|
||||
else {
|
||||
// Add to linked list, similar to hob list
|
||||
Status = MsWheaAddReportEvent(&mMsWheaEntryList, MsWheaEntryMD, PayloadPtr, PayloadSize);
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
Added module phase information and route reported status code value and extended data to ReportHwErrRecRouter
|
||||
for further processing.
|
||||
|
||||
@param[in] CodeType Indicates the type of status code being reported.
|
||||
@param[in] Value Describes the current status of a hardware or software entity. This
|
||||
includes information about the class and subclass that is used to
|
||||
classify the entity as well as an operation.
|
||||
@param[in] Instance The enumeration of a hardware or software entity within the system.
|
||||
Valid instance numbers start with 1.
|
||||
@param[in] CallerId This optional parameter may be used to identify the caller. This
|
||||
parameter allows the status code driver to apply different rules to
|
||||
different callers.
|
||||
@param[in] Data This optional parameter may be used to pass additional data.
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval Others Any other error that rises from Variable Services, Boot Services,
|
||||
Runtime Services, etc.
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaRscHandlerDxe (
|
||||
IN EFI_STATUS_CODE_TYPE CodeType,
|
||||
IN EFI_STATUS_CODE_VALUE Value,
|
||||
IN UINT32 Instance,
|
||||
IN EFI_GUID *CallerId,
|
||||
IN EFI_STATUS_CODE_DATA *Data OPTIONAL
|
||||
)
|
||||
{
|
||||
MS_WHEA_ERROR_PHASE CurrentPhase;
|
||||
|
||||
if ((mWriteArchAvailable != FALSE) && (mVarArchAvailable != FALSE)) {
|
||||
CurrentPhase = MS_WHEA_PHASE_DXE_RUNTIME;
|
||||
}
|
||||
else {
|
||||
CurrentPhase = MS_WHEA_PHASE_DXE;
|
||||
}
|
||||
|
||||
return ReportHwErrRecRouter(CodeType,
|
||||
Value,
|
||||
Instance,
|
||||
CallerId,
|
||||
Data,
|
||||
CurrentPhase,
|
||||
MsWheaReportHandlerDxe);
|
||||
}
|
||||
|
||||
/**
|
||||
This routine processes the reported errors during PEI phase through hob list
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval Others See MsWheaReportHandlerDxe function for more details
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaProcHob (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
UINT16 EntrySize = 0;
|
||||
VOID *GuidHob = NULL;
|
||||
VOID *MsWheaReportEntry = NULL;
|
||||
MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD = NULL;
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": enter...\n"));
|
||||
|
||||
GuidHob = GetFirstGuidHob(&gMsWheaReportServiceGuid);
|
||||
if (GuidHob == NULL) {
|
||||
// This means no reported errors during Pei phase, job done!
|
||||
Status = EFI_SUCCESS;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
while (GuidHob != NULL) {
|
||||
MsWheaReportEntry = GET_GUID_HOB_DATA(GuidHob);
|
||||
EntrySize = GET_GUID_HOB_DATA_SIZE(GuidHob);
|
||||
MsWheaEntryMD = (MS_WHEA_ERROR_ENTRY_MD *) MsWheaReportEntry;
|
||||
if ((EntrySize != 0) && (EntrySize >= MsWheaEntryMD->PayloadSize)) {
|
||||
// Report this entry
|
||||
Status = MsWheaReportHandlerDxe(MsWheaEntryMD,
|
||||
MsWheaEntryMD + 1,
|
||||
MsWheaEntryMD->PayloadSize - sizeof(MS_WHEA_ERROR_ENTRY_MD));
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Hob entry process failed %r\n", Status));
|
||||
}
|
||||
}
|
||||
else {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__": Bad entry: EntrySize: %08X, PayloadSize: %08X\n",
|
||||
EntrySize,
|
||||
MsWheaEntryMD->PayloadSize));
|
||||
}
|
||||
|
||||
GuidHob = GetNextGuidHob(&gMsWheaReportServiceGuid, GET_NEXT_HOB(GuidHob));
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": exit...%r\n", Status));
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine processes the reported errors during Dxe phase through linked list
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null head entry pointer detected
|
||||
@retval Others See MsWheaReportHandlerDxe function for more details
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaProcList (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
VOID *MsWheaReportEntry = NULL;
|
||||
MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD = NULL;
|
||||
MS_WHEA_LIST_ENTRY *MsWheaListEntry = NULL;
|
||||
LIST_ENTRY *HeadList = NULL;
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": enter...\n"));
|
||||
|
||||
while (IsListEmpty(&mMsWheaEntryList) == FALSE) {
|
||||
HeadList = GetFirstNode(&mMsWheaEntryList);
|
||||
MsWheaListEntry = CR(HeadList, MS_WHEA_LIST_ENTRY, Link, MS_WHEA_LIST_ENTRY_SIGNATURE);
|
||||
|
||||
if (MsWheaListEntry->PayloadPtr != NULL) {
|
||||
MsWheaReportEntry = MsWheaListEntry->PayloadPtr;
|
||||
MsWheaEntryMD = (MS_WHEA_ERROR_ENTRY_MD *) MsWheaReportEntry;
|
||||
|
||||
Status = MsWheaReportHandlerDxe(MsWheaEntryMD,
|
||||
MsWheaEntryMD + 1,
|
||||
MsWheaEntryMD->PayloadSize - sizeof(MS_WHEA_ERROR_ENTRY_MD));
|
||||
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Linked list entry process failed %r\n", Status));
|
||||
}
|
||||
}
|
||||
|
||||
MsWheaDeleteReportEvent(&mMsWheaEntryList);
|
||||
}
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": exit...\n"));
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
Process all previously reported status errors during PEI/early Dxe/previous boots
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval Others See each individual function for more details
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaProcessPrevError (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
|
||||
Status = MsWheaESProcess(MsWheaReportHandlerDxe);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": CMOS entries process failed %r\n", Status));
|
||||
}
|
||||
|
||||
Status = MsWheaProcHob();
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Hob entries process failed %r\n", Status));
|
||||
}
|
||||
|
||||
Status = MsWheaProcList();
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": List entries process failed %r\n", Status));
|
||||
}
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
Callback of exit boot event. This will unregister RSC handler in this module.
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
MsWheaReportDxeExitBoot (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": enter...\n"));
|
||||
|
||||
if (mExitBootHasOccurred != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Been here already...\n"));
|
||||
Status = EFI_ACCESS_DENIED;
|
||||
}
|
||||
else {
|
||||
mExitBootHasOccurred = TRUE;
|
||||
Status = mRscHandlerProtocol->Unregister(MsWheaRscHandlerDxe);
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": Protocol unregister result %r\n", Status));
|
||||
}
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": exit...%r\n", Status));
|
||||
}
|
||||
|
||||
/**
|
||||
Register Exit Boot callback and process previous errors when variable service is ready
|
||||
|
||||
@param[in] Event Event whose notification function is being invoked.
|
||||
@param[in] Context The pointer to the notification function's context, which is
|
||||
implementation-dependent.
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
MsWheaArchCallback (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
|
||||
if ((Event == mWriteArchAvailEvent) && (mWriteArchAvailable == FALSE)) {
|
||||
mWriteArchAvailable = TRUE;
|
||||
}
|
||||
else if ((Event == mVarArchAvailEvent) && (mVarArchAvailable == FALSE)) {
|
||||
mVarArchAvailable = TRUE;
|
||||
}
|
||||
else {
|
||||
// Unrecognized event or all available already, do nothing
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if ((mVarArchAvailable == FALSE) || (mWriteArchAvailable == FALSE)) {
|
||||
// Some protocol(s) not ready
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// register for the exit boot event
|
||||
Status = gBS->CreateEventEx(EVT_NOTIFY_SIGNAL,
|
||||
TPL_NOTIFY,
|
||||
MsWheaReportDxeExitBoot,
|
||||
NULL,
|
||||
&gEfiEventExitBootServicesGuid,
|
||||
&mExitBootServicesEvent);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ " failed to register of MsWhea report exit boot (%r)\n", Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// collect all reported events during PEI and pre-DXE Runtime
|
||||
Status = MsWheaProcessPrevError();
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ " processing hob list failed (%r)\n", Status));
|
||||
}
|
||||
|
||||
if (PcdGetBool(PcdMsWheaReportTestEnable) != FALSE) {
|
||||
MsWheaInSituTest(MS_WHEA_PHASE_DXE_RUNTIME);
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
return;
|
||||
}
|
||||
|
||||
/**
|
||||
Register Write Archetecture and Variable Archetecture callbacks
|
||||
|
||||
@param[in] Event Event whose notification function is being invoked.
|
||||
@param[in] Context The pointer to the notification function's context, which is
|
||||
implementation-dependent.
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
MsWheaRegisterCallbacks (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
VOID *Registration; // Just a dummy, not used
|
||||
|
||||
// register for Write Archetecture Protocol Callback
|
||||
mWriteArchAvailEvent = EfiCreateProtocolNotifyEvent(&gEfiVariableWriteArchProtocolGuid,
|
||||
TPL_CALLBACK,
|
||||
MsWheaArchCallback,
|
||||
NULL,
|
||||
&Registration);
|
||||
|
||||
// register for Variable Archetecture Protocol Callback
|
||||
mVarArchAvailEvent = EfiCreateProtocolNotifyEvent(&gEfiVariableArchProtocolGuid,
|
||||
TPL_CALLBACK,
|
||||
MsWheaArchCallback,
|
||||
NULL,
|
||||
&Registration);
|
||||
}
|
||||
|
||||
/**
|
||||
Entry to MsWheaReportDxe, register RSC handler and callback functions
|
||||
|
||||
@param[in] ImageHandle The image handle.
|
||||
@param[in] SystemTable The system table.
|
||||
|
||||
@retval Status From internal routine or boot object, should not fail
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaReportDxeEntry (
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": enter...\n"));
|
||||
|
||||
// init linked list, all fields should be 0
|
||||
InitializeListHead(&mMsWheaEntryList);
|
||||
|
||||
// locate the RSC protocol
|
||||
Status = gBS->LocateProtocol(&gEfiRscHandlerProtocolGuid, NULL, (VOID**)&mRscHandlerProtocol);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ " failed to register MsWhea report RSC handler (%r)\n", Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// register for the RSC callback handler
|
||||
Status = mRscHandlerProtocol->Register(MsWheaRscHandlerDxe, TPL_HIGH_LEVEL);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ " failed to register MsWhea report RSC handler (%r)\n", Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
|
||||
if (PcdGetBool(PcdMsWheaReportTestEnable) != FALSE) {
|
||||
MsWheaInSituTest(MS_WHEA_PHASE_DXE);
|
||||
}
|
||||
|
||||
MsWheaRegisterCallbacks();
|
||||
|
||||
Cleanup:
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": exit (%r)\n", Status));
|
||||
return Status;
|
||||
}
|
|
@ -0,0 +1,94 @@
|
|||
## @file -- MsWheaReportDxe.inf
|
||||
#
|
||||
# MsWheaReportDxe implements Microsoft WHEA report service for Dxe phase.
|
||||
#
|
||||
# Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
# All rights reserved.
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
# 1. Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions and the following disclaimer.
|
||||
# 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions and the following disclaimer in the documentation
|
||||
# and/or other materials provided with the distribution.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
# IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
# LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
# OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
# ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
##
|
||||
|
||||
[Defines]
|
||||
INF_VERSION = 0x00010005
|
||||
BASE_NAME = MsWheaReportDxe
|
||||
FILE_GUID = 995F045B-0265-46A4-8D21-001211A24A4F
|
||||
MODULE_TYPE = DXE_DRIVER
|
||||
VERSION_STRING = 1.0
|
||||
ENTRY_POINT = MsWheaReportDxeEntry
|
||||
|
||||
#
|
||||
# The following information is for reference only and not required by the
|
||||
# build tools.
|
||||
#
|
||||
# VALID_ARCHITECTURES = IA32 X64 IPF EBC
|
||||
#
|
||||
|
||||
[Sources]
|
||||
../MsWheaReportCommon.h
|
||||
../MsWheaReportCommon.c
|
||||
../MsWheaEarlyStorageMgr.c
|
||||
../MsWheaEarlyStorageMgr.h
|
||||
MsWheaReportDxe.c
|
||||
MsWheaReportHER.c
|
||||
MsWheaReportHER.h
|
||||
MsWheaReportList.c
|
||||
MsWheaReportList.h
|
||||
|
||||
[Packages]
|
||||
MdePkg/MdePkg.dec
|
||||
MdeModulePkg/MdeModulePkg.dec
|
||||
MsWheaPkg/MsWheaPkg.dec
|
||||
|
||||
[LibraryClasses]
|
||||
BaseLib
|
||||
BaseMemoryLib
|
||||
UefiLib
|
||||
DebugLib
|
||||
HobLib
|
||||
MemoryAllocationLib
|
||||
PcdLib
|
||||
PrintLib
|
||||
ReportStatusCodeLib
|
||||
UefiBootServicesTableLib
|
||||
UefiDriverEntryPoint
|
||||
UefiRuntimeServicesTableLib
|
||||
MsWheaEarlyStorageLib
|
||||
|
||||
[Protocols]
|
||||
gEfiAcpiTableProtocolGuid ## CONSUMES
|
||||
gEfiRuntimeArchProtocolGuid ## CONSUMES
|
||||
gEfiRscHandlerProtocolGuid ## CONSUMES
|
||||
gEfiVariableWriteArchProtocolGuid ## CONSUMES
|
||||
gEfiVariableArchProtocolGuid ## CONSUMES
|
||||
|
||||
[Pcd]
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaReportTestEnable
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaReportPcatCapacity
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaEarlyStorageDefaultValue
|
||||
|
||||
[Guids]
|
||||
gEfiHardwareErrorVariableGuid ## CONSUMES
|
||||
gEfiEventExitBootServicesGuid ## CONSUMES
|
||||
gMsWheaReportServiceGuid ## SOMETIMES_CONSUMES
|
||||
gEfiFirmwareErrorSectionGuid ## SOMETIMES_CONSUMES
|
||||
gEfiEventNotificationTypeBootGuid ## SOMETIMES_CONSUMES
|
||||
|
||||
[Depex]
|
||||
gEfiRscHandlerProtocolGuid
|
|
@ -0,0 +1,298 @@
|
|||
/** @file -- MsWheaReportHER.c
|
||||
|
||||
This source implements backend routines to support storing persistent hardware
|
||||
error records in UEFI.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#include <Library/UefiRuntimeServicesTableLib.h>
|
||||
#include <Library/PrintLib.h>
|
||||
#include "MsWheaReportHER.h"
|
||||
|
||||
/**
|
||||
|
||||
This routine accepts the pointer to the MS WHEA entry metadata, payload and payload length, allocate and
|
||||
fill (AnF) in the buffer with supplied information. Then return the pointer of processed buffer.
|
||||
|
||||
Note: Caller is responsible for freeing the valid returned buffer!!!
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
@param[in] PayloadPtr The pointer to payload
|
||||
@param[in, out] PayloadSize The pointer to payload length, this will be updated to the totally
|
||||
allocated/operated size if operation succeeded
|
||||
|
||||
@retval NULL if any errors, otherwise filled and allocated buffer will be returned.
|
||||
|
||||
**/
|
||||
STATIC
|
||||
VOID *
|
||||
MsWheaAnFBuffer (
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN OUT UINT32 *PayloadSize,
|
||||
IN CONST VOID *PayloadPtr
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
UINT8 *Buffer = NULL;
|
||||
UINT32 BufferIndex = 0;
|
||||
UINT32 ErrorPayloadSize = 0;
|
||||
|
||||
EFI_COMMON_ERROR_RECORD_HEADER *CperHdr;
|
||||
EFI_ERROR_SECTION_DESCRIPTOR *CperErrSecDscp;
|
||||
EFI_FIRMWARE_ERROR_DATA *EfiFirmwareErrorData;
|
||||
|
||||
DEBUG((DEBUG_INFO,__FUNCTION__" enter...\n"));
|
||||
|
||||
if ((PayloadSize == NULL) ||
|
||||
(PayloadPtr == NULL) ||
|
||||
(MsWheaEntryMD == NULL)) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
ErrorPayloadSize = sizeof(EFI_FIRMWARE_ERROR_DATA) + *PayloadSize;
|
||||
|
||||
Buffer = AllocateZeroPool(sizeof(EFI_COMMON_ERROR_RECORD_HEADER) +
|
||||
sizeof(EFI_ERROR_SECTION_DESCRIPTOR) +
|
||||
ErrorPayloadSize);
|
||||
if (Buffer == NULL) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Grab pointers to each header
|
||||
CperHdr = (EFI_COMMON_ERROR_RECORD_HEADER*)&Buffer[BufferIndex];
|
||||
BufferIndex += sizeof(EFI_COMMON_ERROR_RECORD_HEADER);
|
||||
|
||||
CperErrSecDscp = (EFI_ERROR_SECTION_DESCRIPTOR*)&Buffer[BufferIndex];
|
||||
BufferIndex += sizeof(EFI_ERROR_SECTION_DESCRIPTOR);
|
||||
|
||||
EfiFirmwareErrorData = (EFI_FIRMWARE_ERROR_DATA*)&Buffer[BufferIndex];
|
||||
BufferIndex += sizeof(EFI_FIRMWARE_ERROR_DATA);
|
||||
|
||||
// Fill out error type based headers according to UEFI Spec...
|
||||
CreateHeadersDefault(CperHdr,
|
||||
CperErrSecDscp,
|
||||
EfiFirmwareErrorData,
|
||||
MsWheaEntryMD,
|
||||
ErrorPayloadSize);
|
||||
|
||||
// Copy payload section
|
||||
CopyMem(&Buffer[BufferIndex], PayloadPtr, *PayloadSize);
|
||||
BufferIndex += (*PayloadSize);
|
||||
|
||||
// Update PayloadSize as the recorded error has Headers and Payload merged
|
||||
*PayloadSize = BufferIndex;
|
||||
Cleanup:
|
||||
DEBUG((DEBUG_INFO,__FUNCTION__" exit %r...\n", Status));
|
||||
return (VOID*) Buffer;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine accepts the pointer to a UINT16 number. It will iterate through each HwErrRecXXXX and stops
|
||||
after 0xFFFF iterations or spotted a slot that returns EFI_NOT_FOUND.
|
||||
|
||||
@param[out] next The pointer to output result holder
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval EFI_INVALID_PARAMETER Input pointer is NULL.
|
||||
@retval EFI_OUT_OF_RESOURCES No available slot for HwErrRec.
|
||||
@retval Others See GetVariable for more details
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaFindNextAvailableSlot (
|
||||
OUT UINT16 *next
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
UINT32 Index = 0;
|
||||
UINTN Size = 0;
|
||||
CHAR16 VarName[EFI_HW_ERR_REC_VAR_NAME_LEN];
|
||||
|
||||
if (next == NULL) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if ((gRT == NULL) || (gRT->GetVariable == NULL)) {
|
||||
Status = EFI_NOT_READY;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
for (Index = 0; Index <= MAX_UINT16; Index++) {
|
||||
Size = 0;
|
||||
UnicodeSPrint(VarName, sizeof(VarName), L"%s%04X", EFI_HW_ERR_REC_VAR_NAME, (UINT16)(Index & MAX_UINT16));
|
||||
Status = gRT->GetVariable(VarName,
|
||||
&gEfiHardwareErrorVariableGuid,
|
||||
NULL,
|
||||
&Size,
|
||||
NULL);
|
||||
if (Status == EFI_NOT_FOUND) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
// Translate result corresponds to this specific function
|
||||
if (Status == EFI_NOT_FOUND) {
|
||||
*next = (UINT16)(Index & MAX_UINT16);
|
||||
Status = EFI_SUCCESS;
|
||||
} else if (Status == EFI_SUCCESS) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
} else {
|
||||
// Do Nothing, pass on the error
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
Clear all the HwErrRec entries on flash.
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval Others See GetVariable/SetVariable for more details
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaClearAllEntries (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
UINT32 Index = 0;
|
||||
CHAR16 VarName[EFI_HW_ERR_REC_VAR_NAME_LEN];
|
||||
UINTN Size = 0;
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ " enter\n"));
|
||||
|
||||
for (Index = 0; Index <= MAX_UINT16; Index++) {
|
||||
Size = 0;
|
||||
UnicodeSPrint(VarName, sizeof(VarName), L"%s%04X", EFI_HW_ERR_REC_VAR_NAME, Index);
|
||||
Status = gRT->GetVariable(VarName,
|
||||
&gEfiHardwareErrorVariableGuid,
|
||||
NULL,
|
||||
&Size,
|
||||
NULL);
|
||||
if (Status == EFI_NOT_FOUND) {
|
||||
// Do nothing
|
||||
continue;
|
||||
}
|
||||
else if (Status != EFI_BUFFER_TOO_SMALL) {
|
||||
// We have other problems here..
|
||||
break;
|
||||
}
|
||||
|
||||
Status = gRT->SetVariable(VarName,
|
||||
&gEfiHardwareErrorVariableGuid,
|
||||
EFI_VARIABLE_NON_VOLATILE |
|
||||
EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_RUNTIME_ACCESS |
|
||||
EFI_VARIABLE_HARDWARE_ERROR_RECORD,
|
||||
0,
|
||||
NULL);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ " Clear HwErrRec has an issue...\n"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if ((Status == EFI_SUCCESS) || (Status == EFI_NOT_FOUND)) {
|
||||
Status = EFI_SUCCESS;
|
||||
}
|
||||
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ " exit...\n"));
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine accepts the pointer to the MS WHEA entry metadata, error specific data payload and its size
|
||||
then store on the flash as HwErrRec awaiting to be picked up by OS (Refer to UEFI Spec 2.7A)
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
@param[in] PayloadPtr The pointer to reported error block payload, the content will be copied
|
||||
@param[in] PayloadSize The size of reported error block payload
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval EFI_INVALID_PARAMETER Input has NULL pointer as input.
|
||||
@retval EFI_OUT_OF_RESOURCES Not enough spcae for the requested space.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaReportHERAdd (
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN CONST VOID *PayloadPtr,
|
||||
IN UINT32 PayloadSize
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
UINT16 Index = 0;
|
||||
VOID *Buffer = NULL;
|
||||
UINT32 Size = PayloadSize;
|
||||
CHAR16 VarName[EFI_HW_ERR_REC_VAR_NAME_LEN];
|
||||
|
||||
// 1. Find an available variable name for next write
|
||||
Status = MsWheaFindNextAvailableSlot(&Index);
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Find the next available slot failed (%r)\n", Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// 2. Fill out headers
|
||||
Buffer = MsWheaAnFBuffer(MsWheaEntryMD, &Size, PayloadPtr);
|
||||
if (Buffer == NULL) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Buffer allocate and fill failed (%r)\n", Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// 3. Save the record to flash
|
||||
UnicodeSPrint(VarName, sizeof(VarName), L"%s%04X", EFI_HW_ERR_REC_VAR_NAME, Index);
|
||||
Status = gRT->SetVariable(VarName,
|
||||
&gEfiHardwareErrorVariableGuid,
|
||||
EFI_VARIABLE_NON_VOLATILE |
|
||||
EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_RUNTIME_ACCESS |
|
||||
EFI_VARIABLE_HARDWARE_ERROR_RECORD,
|
||||
Size,
|
||||
Buffer);
|
||||
if (EFI_ERROR(Status)) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Write size of %d at index %04X errored with (%r)\n", Size, Index, Status));
|
||||
} else {
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": Write size of %d at index %04X succeeded\n", Size, Index));
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
if (Buffer) {
|
||||
FreePool(Buffer);
|
||||
}
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": exit (%r)\n", Status));
|
||||
return Status;
|
||||
}
|
|
@ -0,0 +1,70 @@
|
|||
/** @file -- MsWheaReportHER.h
|
||||
|
||||
This header defines API that will save supplied payload via HwErrRec.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#ifndef __MS_WHEA_REPORT_HER__
|
||||
#define __MS_WHEA_REPORT_HER__
|
||||
|
||||
#include "MsWheaReportCommon.h"
|
||||
|
||||
/**
|
||||
|
||||
Clear all the HwErrRec entries on flash.
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval Others See GetVariable/SetVariable for more details
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaClearAllEntries (
|
||||
VOID
|
||||
);
|
||||
|
||||
/**
|
||||
|
||||
This routine accepts the pointer to the MS WHEA entry metadata, error specific data payload and its size
|
||||
then store on the flash as HwErrRec awaiting to be picked up by OS (Refer to UEFI Spec 2.7A)
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
@param[in] PayloadPtr The pointer to reported error block payload, the content will be copied
|
||||
@param[in] PayloadSize The size of reported error block payload
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval EFI_INVALID_PARAMETER Input has NULL pointer as input.
|
||||
@retval EFI_OUT_OF_RESOURCES Not enough spcae for the requested space.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaReportHERAdd (
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN CONST VOID *PayloadPtr,
|
||||
IN UINT32 PayloadSize
|
||||
);
|
||||
|
||||
#endif // __MS_WHEA_REPORT_HER__
|
|
@ -0,0 +1,201 @@
|
|||
/** @file -- MsWheaReportList.c
|
||||
|
||||
This source implements common methods to support logging of non-fatal Microsoft
|
||||
WHEA errors in UEFI.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#include "MsWheaReportList.h"
|
||||
|
||||
/**
|
||||
|
||||
This function creates a new entry to be added to the linked list
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error linked list
|
||||
@param[in] PayloadPtr The pointer to payload
|
||||
@param[in] PayloadSize The pointer to payload length
|
||||
|
||||
@retval MS_WHEA_LIST_ENTRY * Pointer to the created list entry.
|
||||
@retval NULL Null pointer due to invalid parameter or out of resources.
|
||||
|
||||
**/
|
||||
STATIC
|
||||
MS_WHEA_LIST_ENTRY *
|
||||
CreateNewEntry (
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN CONST VOID *PayloadPtr,
|
||||
IN UINT32 PayloadSize
|
||||
)
|
||||
{
|
||||
MS_WHEA_LIST_ENTRY *MsWheaListEntry = NULL;
|
||||
UINT32 Index = 0;
|
||||
|
||||
// Input argument sanity check
|
||||
if ((PayloadPtr == NULL) ||
|
||||
(PayloadSize == 0) ||
|
||||
(MsWheaEntryMD == NULL)) {
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
MsWheaListEntry = AllocateZeroPool(sizeof(MS_WHEA_LIST_ENTRY));
|
||||
if (MsWheaListEntry == NULL) {
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
MsWheaListEntry->Signature = MS_WHEA_LIST_ENTRY_SIGNATURE;
|
||||
|
||||
MsWheaListEntry->PayloadPtr = AllocateZeroPool(PayloadSize + sizeof(MS_WHEA_ERROR_ENTRY_MD));
|
||||
if (MsWheaListEntry->PayloadPtr == NULL) {
|
||||
FreePool(MsWheaListEntry);
|
||||
MsWheaListEntry = NULL;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Copy linked list and payload
|
||||
Index = 0;
|
||||
CopyMem(&((UINT8*)MsWheaListEntry->PayloadPtr)[Index], MsWheaEntryMD, sizeof(MS_WHEA_ERROR_ENTRY_MD));
|
||||
|
||||
Index += sizeof(MS_WHEA_ERROR_ENTRY_MD);
|
||||
CopyMem(&((UINT8*)MsWheaListEntry->PayloadPtr)[Index], PayloadPtr, PayloadSize);
|
||||
|
||||
Index += PayloadSize;
|
||||
((MS_WHEA_ERROR_ENTRY_MD*)MsWheaListEntry->PayloadPtr)->PayloadSize = Index;
|
||||
|
||||
MsWheaListEntry->PayloadSize = Index;
|
||||
|
||||
Cleanup:
|
||||
return MsWheaListEntry;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine accepts the MS WHEA linked list and the reported data and data length, then add the data to the
|
||||
existed list, First In First Out (FIFO)
|
||||
|
||||
@param[in] MsWheaLinkedList Supplies a MS WHEA error linked list header.
|
||||
@param[in] PayloadPtr The pointer to reported error block, the content will be copied.
|
||||
@param[in] PayloadSize The size of reported error block.
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval EFI_INVALID_PARAMETER Input has NULL pointer as input.
|
||||
@retval EFI_OUT_OF_RESOURCES Not enough spcae for the requested space.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaAddReportEvent(
|
||||
IN LIST_ENTRY *MsWheaLinkedList,
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN CONST VOID *PayloadPtr,
|
||||
IN UINT32 PayloadSize
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
MS_WHEA_LIST_ENTRY *MsWheaListEntry;
|
||||
|
||||
// Caller has to supply valid pointers to linked list and data.
|
||||
if (MsWheaLinkedList == NULL) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
MsWheaListEntry = CreateNewEntry(MsWheaEntryMD, PayloadPtr, PayloadSize);
|
||||
if (MsWheaListEntry == NULL) {
|
||||
// This error code may not be true, but something is knowingly wrong
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Added the initialized entry into the linked list
|
||||
InsertTailList(MsWheaLinkedList, &MsWheaListEntry->Link);
|
||||
|
||||
Status = EFI_SUCCESS;
|
||||
|
||||
Cleanup:
|
||||
if (EFI_ERROR(Status)) {
|
||||
// Clean up the memory remainder, if any errors
|
||||
if ((MsWheaListEntry != NULL) && (MsWheaListEntry->PayloadPtr != NULL)) {
|
||||
FreePool(MsWheaListEntry->PayloadPtr);
|
||||
}
|
||||
if (MsWheaListEntry != NULL) {
|
||||
FreePool(MsWheaListEntry);
|
||||
}
|
||||
}
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine accepts the MS WHEA linked list, remove and free an element from the list
|
||||
|
||||
@param[in] MsWheaLinkedList Supplies a MS WHEA linked list header.
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval EFI_INVALID_PARAMETER Input has NULL pointer as input.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaDeleteReportEvent(
|
||||
IN LIST_ENTRY *MsWheaLinkedList
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
MS_WHEA_LIST_ENTRY *MsWheaListEntry = NULL;
|
||||
LIST_ENTRY *HeadList = NULL;
|
||||
|
||||
// Caller has to supply valid pointers to linked list.
|
||||
if (MsWheaLinkedList == NULL) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// linked list needs to have content, if not, it shouldn't be an issue;
|
||||
if (IsListEmpty(MsWheaLinkedList) != FALSE) {
|
||||
Status = EFI_SUCCESS;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Retrieve a temporary data holder
|
||||
HeadList = GetFirstNode(MsWheaLinkedList);
|
||||
if (HeadList == NULL) {
|
||||
// Shouldn't happen, since we've checked the linked list has more than one entry...
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
MsWheaListEntry = CR(HeadList, MS_WHEA_LIST_ENTRY, Link, MS_WHEA_LIST_ENTRY_SIGNATURE);
|
||||
|
||||
// House keeping for the linked list
|
||||
RemoveEntryList(HeadList);
|
||||
if (MsWheaListEntry->PayloadPtr != NULL) {
|
||||
FreePool(MsWheaListEntry->PayloadPtr);
|
||||
}
|
||||
FreePool(MsWheaListEntry);
|
||||
|
||||
Status = EFI_SUCCESS;
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
|
@ -0,0 +1,83 @@
|
|||
/** @file -- MsWheaReportList.h
|
||||
|
||||
This header defines API that will save supplied payload on heap for pre-ExitBoot usage.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#ifndef __MS_WHEA_REPORT_LIST__
|
||||
#define __MS_WHEA_REPORT_LIST__
|
||||
|
||||
#include "MsWheaReportCommon.h"
|
||||
|
||||
#define MS_WHEA_LIST_ENTRY_SIGNATURE MS_WHEA_ERROR_SIGNATURE
|
||||
|
||||
// The linked list node to recover necessary information from each error block
|
||||
typedef struct MS_WHEA_LIST_ENTRY_T_DEF {
|
||||
UINT32 Signature;
|
||||
UINT32 PayloadSize;
|
||||
VOID *PayloadPtr;
|
||||
LIST_ENTRY Link;
|
||||
} MS_WHEA_LIST_ENTRY;
|
||||
|
||||
/**
|
||||
|
||||
This routine accepts the MS WHEA metadata and the reported data and data length, then add the data to the
|
||||
existed list, First In First Out (FIFO)
|
||||
|
||||
@param[in] MsWheaLinkedList Supplies a MS WHEA error linked list header.
|
||||
@param[in] PayloadPtr The pointer to reported error block, the content will be copied.
|
||||
@param[in] PayloadSize The size of reported error block.
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval EFI_INVALID_PARAMETER Input has NULL pointer as input.
|
||||
@retval EFI_OUT_OF_RESOURCES Not enough spcae for the requested space.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaAddReportEvent(
|
||||
IN LIST_ENTRY *MsWheaLinkedList,
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN CONST VOID *PayloadPtr,
|
||||
IN UINT32 PayloadSize
|
||||
);
|
||||
|
||||
/**
|
||||
|
||||
This routine accepts the MS WHEA metadata, remove and free an element from the list
|
||||
|
||||
@param[in] MsWheaLinkedList Supplies a MS WHEA linked list header.
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval EFI_INVALID_PARAMETER Input has NULL pointer as input.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaDeleteReportEvent(
|
||||
IN LIST_ENTRY *MsWheaLinkedList
|
||||
);
|
||||
|
||||
#endif // __MS_WHEA_REPORT_LIST__
|
|
@ -0,0 +1,801 @@
|
|||
/** @file -- MsWheaEarlyStorageMgr.c
|
||||
|
||||
This source utilizes early storage APIs for MsWheaReport usage.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#include <Uefi/UefiBaseType.h>
|
||||
#include <Library/MsWheaEarlyStorageLib.h>
|
||||
#include "MsWheaEarlyStorageMgr.h"
|
||||
|
||||
typedef struct _MS_WHEA_EARLY_STORAGE_HEADER {
|
||||
UINT32 Signature;
|
||||
UINT8 IsStorageFull;
|
||||
UINT8 Reserved;
|
||||
MS_WHEA_ERROR_PHASE FullPhase;
|
||||
} MS_WHEA_EARLY_STORAGE_HEADER;
|
||||
|
||||
#define MS_WHEA_EARLY_STORAGE_SIGNATURE MS_WHEA_ERROR_SIGNATURE
|
||||
#define MS_WHEA_EARLY_STORAGE_HEADER_SIZE (sizeof(MS_WHEA_EARLY_STORAGE_HEADER))
|
||||
#define MS_WHEA_EARLY_STORAGE_DATA_OFFSET MS_WHEA_EARLY_STORAGE_HEADER_SIZE
|
||||
|
||||
/**
|
||||
|
||||
This routine returns the maximum number of bytes that can be stored in the PEI event store.
|
||||
|
||||
@retval Count The maximum number of bytes that can be stored in the MS WHEA store.
|
||||
|
||||
**/
|
||||
STATIC
|
||||
UINT8
|
||||
MsWheaESGetMaxDataCount (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
return (UINT8)((MsWheaEarlyStorageGetMaxSize() - (MS_WHEA_EARLY_STORAGE_DATA_OFFSET)) & 0xFF);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine reads the specified data region from the MS WHEA store.
|
||||
|
||||
@param[in] Ptr The pointer to hold intended read data
|
||||
@param[in] Size The size of intended read data
|
||||
@param[in] Offset The offset of read data, starting from
|
||||
Early MS_WHEA_EARLY_STORAGE_DATA_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESReadData (
|
||||
VOID *Ptr,
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
if (Offset >= MsWheaESGetMaxDataCount()) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = MsWheaEarlyStorageRead(Ptr, Size, MS_WHEA_EARLY_STORAGE_DATA_OFFSET + Offset);
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
|
||||
This routine writes the specified data region from the MS WHEA store.
|
||||
|
||||
@param[in] Ptr The pointer to hold intended written data
|
||||
@param[in] Size The size of intended written data
|
||||
@param[in] Offset The offset of written data, starting from
|
||||
MS_WHEA_EARLY_STORAGE_DATA_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESWriteData (
|
||||
VOID *Ptr,
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
if (Offset >= MsWheaESGetMaxDataCount()) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = MsWheaEarlyStorageWrite(Ptr, Size, MS_WHEA_EARLY_STORAGE_DATA_OFFSET + Offset);
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine clears the specified data region from the MS WHEA store.
|
||||
|
||||
@param[in] Size The size of intended clear data
|
||||
@param[in] Offset The offset of clear data, starting from
|
||||
Early MS_WHEA_EARLY_STORAGE_DATA_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESClearData (
|
||||
UINT8 Size,
|
||||
UINT8 Offset
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
if (Offset >= MsWheaESGetMaxDataCount()) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = MsWheaEarlyStorageClear(Size, MS_WHEA_EARLY_STORAGE_DATA_OFFSET + Offset);
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine dumps the contents of the early storage.
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
MsWheaESDump (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
UINT8 Data;
|
||||
UINT8 Index;
|
||||
EFI_STATUS Status;
|
||||
|
||||
DEBUG((DEBUG_INFO, "CMOS MS WHEA Store..."));
|
||||
for (Index = 0; Index < MsWheaEarlyStorageGetMaxSize(); Index ++) {
|
||||
Status = MsWheaESReadData(&Data, sizeof(Data), Index);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__": Reading Early Storage %d failed %r", Index, Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if ((Index % 16) == 0) {
|
||||
DEBUG((DEBUG_INFO, "\n0x%02x: ", Index));
|
||||
}
|
||||
|
||||
DEBUG((DEBUG_INFO, "%02x ", Data));
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
DEBUG((DEBUG_INFO, "\n"));
|
||||
return;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine clears all bytes in Data region
|
||||
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
MsWheaESClearAllData (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
MsWheaESClearData(MsWheaESGetMaxDataCount(), MS_WHEA_EARLY_STORAGE_DATA_OFFSET);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine reads the Early Storage MS WHEA store header.
|
||||
|
||||
@param Header Supplies a pointer that will hold the Early Storage header.
|
||||
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
MsWheaESReadHeader (
|
||||
MS_WHEA_EARLY_STORAGE_HEADER *Header
|
||||
)
|
||||
{
|
||||
if (Header == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
MsWheaEarlyStorageRead(Header, MS_WHEA_EARLY_STORAGE_HEADER_SIZE, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine writes the passed Early Storage MS WHEA store header.
|
||||
|
||||
@param Header Supplies a pointer that holds the target Early Storage header.
|
||||
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
MsWheaESWriteHeader (
|
||||
MS_WHEA_EARLY_STORAGE_HEADER *Header
|
||||
)
|
||||
{
|
||||
if (Header == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
MsWheaEarlyStorageWrite(Header, MS_WHEA_EARLY_STORAGE_HEADER_SIZE, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine returns a boolean indicating if the MS WHEA store is valid.
|
||||
|
||||
@retval TRUE if the MS WHEA store is valid, else FALSE.
|
||||
|
||||
**/
|
||||
STATIC
|
||||
BOOLEAN
|
||||
MsWheaESRegionIsValid (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
MS_WHEA_EARLY_STORAGE_HEADER Header;
|
||||
|
||||
MsWheaESReadHeader(&Header);
|
||||
if (Header.Signature != MS_WHEA_EARLY_STORAGE_SIGNATURE) {
|
||||
return FALSE;
|
||||
}
|
||||
else {
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine finds a contiguous memory that has default value of specified size in data region
|
||||
from the MS WHEA store.
|
||||
|
||||
@param[in] Size The size of intended clear data
|
||||
@param[out] Offset The pointer to receive returned offset value, starting from
|
||||
Early MS_WHEA_EARLY_STORAGE_DATA_OFFSET
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_OUT_OF_RESOURCES Null pointer or zero or over length request detected
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESFindSlot (
|
||||
IN UINT8 Size,
|
||||
IN UINT8 *Offset
|
||||
)
|
||||
{
|
||||
UINT16 i = 0;
|
||||
UINT8 val = 0;
|
||||
UINT8 ceiling;
|
||||
UINT8 remainder = Size;
|
||||
EFI_STATUS Status = EFI_OUT_OF_RESOURCES;
|
||||
|
||||
ceiling = MsWheaESGetMaxDataCount();
|
||||
|
||||
for (i = 0; i < ceiling; i ++) {
|
||||
if (remainder == Size) {
|
||||
*Offset = (UINT8) i;
|
||||
}
|
||||
|
||||
MsWheaESReadData(&val, sizeof(UINT8), (UINT8) i);
|
||||
if (val != PcdGet8(PcdMsWheaEarlyStorageDefaultValue)) {
|
||||
remainder = Size;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (remainder > 0) {
|
||||
remainder --;
|
||||
} else {
|
||||
Status = EFI_SUCCESS;
|
||||
break;
|
||||
}
|
||||
}
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine initialized the Early Storage MS WHEA store.
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
MsWheaESInit (
|
||||
VOID
|
||||
)
|
||||
{
|
||||
MS_WHEA_EARLY_STORAGE_HEADER Header;
|
||||
|
||||
MsWheaESReadHeader(&Header);
|
||||
|
||||
// Check if the Early Storage has the signature. If it does, the store has already been initialized
|
||||
// and there's nothing more to do.
|
||||
if (Header.Signature == MS_WHEA_EARLY_STORAGE_SIGNATURE) {
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": init early storage...\n"));
|
||||
|
||||
// Clear the rest of the Early Storage store.
|
||||
MsWheaESClearAllData();
|
||||
|
||||
// Zero all the fields in the
|
||||
SetMem(&Header, MS_WHEA_EARLY_STORAGE_HEADER_SIZE, 0);
|
||||
|
||||
// Sign the header signature.
|
||||
Header.Signature = MS_WHEA_EARLY_STORAGE_SIGNATURE;
|
||||
MsWheaESWriteHeader(&Header);
|
||||
|
||||
Cleanup:
|
||||
MsWheaESDump();
|
||||
return;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine will extract necessary Rev 0 information from supplied metadata and store onto the next
|
||||
contiguously available Early Storage data region
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval Others See MsWheaESFindSlot and MsWheaESWriteData for more details
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESV0InfoStore (
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD
|
||||
)
|
||||
{
|
||||
UINT8 Offset = 0;
|
||||
EFI_STATUS Status;
|
||||
MS_WHEA_EARLY_STORAGE_ENTRY_V0 WheaV0;
|
||||
|
||||
Status = MsWheaESFindSlot(sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V0), &Offset);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
WheaV0.Rev = MsWheaEntryMD->MsWheaErrorHdr.Rev;
|
||||
WheaV0.Phase = MsWheaEntryMD->MsWheaErrorHdr.Phase;
|
||||
WheaV0.ErrorStatusCode = MsWheaEntryMD->ErrorStatusCode;
|
||||
|
||||
Status = MsWheaESWriteData(&WheaV0, sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V0), Offset);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Clear V0 Early Storage failed at %d %r\n", Offset, Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine will extract necessary Rev 1 information from supplied metadata and store onto the next
|
||||
contiguously available Early Storage data region
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval Others See MsWheaESFindSlot and MsWheaESWriteData for more
|
||||
details
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESV1InfoStore (
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD
|
||||
)
|
||||
{
|
||||
UINT8 Offset = 0;
|
||||
EFI_STATUS Status;
|
||||
MS_WHEA_EARLY_STORAGE_ENTRY_V1 WheaV1;
|
||||
|
||||
Status = MsWheaESFindSlot(sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V1), &Offset);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
WheaV1.Rev = MsWheaEntryMD->MsWheaErrorHdr.Rev;
|
||||
WheaV1.Phase = MsWheaEntryMD->MsWheaErrorHdr.Phase;
|
||||
WheaV1.ErrorStatusCode = MsWheaEntryMD->ErrorStatusCode;
|
||||
WheaV1.CriticalInfo = MsWheaEntryMD->MsWheaErrorHdr.CriticalInfo;
|
||||
WheaV1.ReporterID = MsWheaEntryMD->MsWheaErrorHdr.ReporterID;
|
||||
|
||||
Status = MsWheaESWriteData(&WheaV1, sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V1), Offset);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Clear V0 Early Storage failed at %d %r\n", Offset, Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine will read Rev 0 information from specified offset on Early Storage data region and fill in the
|
||||
metadata based on read value
|
||||
|
||||
@param[out] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
@param[in, out] Offset The pointer to specified offset, will be updated to the end of
|
||||
processed data upon successful operation
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer detected
|
||||
@retval Others See MsWheaESFindSlot and MsWheaESReadData for more
|
||||
details
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESGetV0Info (
|
||||
OUT MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN OUT UINT8 *Offset
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
MS_WHEA_EARLY_STORAGE_ENTRY_V0 WheaV0;
|
||||
|
||||
if (MsWheaEntryMD == NULL) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
SetMem(&WheaV0, sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V0), 0);
|
||||
SetMem(MsWheaEntryMD, sizeof(MS_WHEA_ERROR_ENTRY_MD), 0);
|
||||
|
||||
Status = MsWheaESReadData(&WheaV0, sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V0), *Offset);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Read V0 Early Storage storage failed at %d %r\n", Offset, Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Signature = MS_WHEA_ERROR_SIGNATURE;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Rev = WheaV0.Rev;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Phase = WheaV0.Phase;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.ErrorSeverity = EFI_GENERIC_ERROR_FATAL;
|
||||
MsWheaEntryMD->ErrorStatusCode = WheaV0.ErrorStatusCode;
|
||||
MsWheaEntryMD->PayloadSize = sizeof(MS_WHEA_ERROR_ENTRY_MD) + sizeof(MS_WHEA_ERROR_HDR);
|
||||
|
||||
Status = MsWheaESClearData(sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V0), *Offset);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Clear V0 Early Storage storage failed at %d %r\n", Offset, Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
*Offset = *Offset + sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V0);
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine will read Rev 1 information from specified offset on Early Storage data region and fill in the
|
||||
metadata based on read value
|
||||
|
||||
@param[out] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
@param[in, out] Offset The pointer to specified offset, will be updated to the end of
|
||||
processed data upon successful operation
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer detected
|
||||
@retval Others See MsWheaESFindSlot and MsWheaESReadData for more
|
||||
details
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESGetV1Info (
|
||||
OUT MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN UINT8 *Offset
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
MS_WHEA_EARLY_STORAGE_ENTRY_V1 WheaV1;
|
||||
|
||||
if (MsWheaEntryMD == NULL) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
SetMem(&WheaV1, sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V1), 0);
|
||||
SetMem(MsWheaEntryMD, sizeof(MS_WHEA_ERROR_ENTRY_MD), 0);
|
||||
|
||||
Status = MsWheaESReadData(&WheaV1, sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V1), *Offset);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Read V1 Early Storage storage failed at %d %r\n", Offset, Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Signature = MS_WHEA_ERROR_SIGNATURE;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Rev = WheaV1.Rev;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Phase = WheaV1.Phase;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.ErrorSeverity = EFI_GENERIC_ERROR_FATAL;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.CriticalInfo = WheaV1.CriticalInfo;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.ReporterID = WheaV1.ReporterID;
|
||||
MsWheaEntryMD->ErrorStatusCode = WheaV1.ErrorStatusCode;
|
||||
MsWheaEntryMD->PayloadSize = sizeof(MS_WHEA_ERROR_ENTRY_MD) + sizeof(MS_WHEA_ERROR_HDR);
|
||||
|
||||
Status = MsWheaESClearData(sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V1), *Offset);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Clear V1 Early Storage storage failed at %d %r\n", Offset, Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
*Offset = *Offset + sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_V1);
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine will Set Early Storage header IsStorageFull flag and mark the system stage if the signature is
|
||||
legit
|
||||
|
||||
@param[in] Phase Current envirnment stage by the time of report
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_NOT_FOUND Early Storage header region is not valid
|
||||
@retval Others See MsWheaESFindSlot and MsWheaESReadData for more
|
||||
details
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESSetHeaderFull (
|
||||
MS_WHEA_ERROR_PHASE Phase
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
MS_WHEA_EARLY_STORAGE_HEADER Header;
|
||||
|
||||
MsWheaESReadHeader(&Header);
|
||||
|
||||
if (Header.Signature != MS_WHEA_EARLY_STORAGE_SIGNATURE) {
|
||||
Status = EFI_NOT_FOUND;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if (Header.IsStorageFull != FALSE) {
|
||||
Status = EFI_SUCCESS;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Set this field to any non-zero value;
|
||||
Header.IsStorageFull = PcdGet8(PcdMsWheaEarlyStorageDefaultValue);
|
||||
Header.FullPhase = Phase;
|
||||
MsWheaESWriteHeader(&Header);
|
||||
|
||||
Status = EFI_SUCCESS;
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
This routine will read Early Storage header and fill out the Metadata if header indicates the Early Storage
|
||||
is full
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_NOT_STARTED Metadata is not filled as Early Storage is not full
|
||||
@retval EFI_INVALID_PARAMETER Null pointer detected
|
||||
@retval EFI_NOT_FOUND Early Storage header region is not valid
|
||||
@retval Others See MsWheaESFindSlot and MsWheaESReadData for more
|
||||
details
|
||||
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaESCheckHeader (
|
||||
OUT MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
MS_WHEA_EARLY_STORAGE_HEADER Header;
|
||||
|
||||
MsWheaESReadHeader(&Header);
|
||||
if (Header.Signature != MS_WHEA_EARLY_STORAGE_SIGNATURE) {
|
||||
Status = EFI_NOT_FOUND;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if (Header.IsStorageFull == FALSE) {
|
||||
Status = EFI_NOT_STARTED;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if (MsWheaEntryMD == NULL) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
SetMem(MsWheaEntryMD, sizeof(MS_WHEA_ERROR_ENTRY_MD), 0);
|
||||
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Signature = MS_WHEA_ERROR_SIGNATURE;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Rev = MS_WHEA_REV_0;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Phase = Header.FullPhase;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.ErrorSeverity = EFI_GENERIC_ERROR_RECOVERABLE;
|
||||
MsWheaEntryMD->ErrorStatusCode = MS_WHEA_ERROR_EARLY_STORAGE_STORE_FULL;
|
||||
MsWheaEntryMD->PayloadSize = sizeof(MS_WHEA_ERROR_ENTRY_MD) + sizeof(MS_WHEA_ERROR_HDR);
|
||||
|
||||
// Reset the header after processing
|
||||
SetMem(&Header, MS_WHEA_EARLY_STORAGE_HEADER_SIZE, 0);
|
||||
Header.Signature = MS_WHEA_EARLY_STORAGE_SIGNATURE;
|
||||
|
||||
MsWheaESWriteHeader(&Header);
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine will store data onto Early Storage data region based on supplied MS WHEA metadata
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval Others See MsWheaESFindSlot and MsWheaESWriteData for more
|
||||
details
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaESStoreEntry (
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD
|
||||
)
|
||||
{
|
||||
MS_WHEA_REV Rev = 0;
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
|
||||
if (MsWheaEntryMD == NULL) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": input pointer cannot be null!\n"));
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Make sure the Early Storage is valid.
|
||||
if (MsWheaESRegionIsValid() == FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": the Early Storage is not valid!\n"));
|
||||
Status = EFI_NOT_FOUND;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Rev = MsWheaEntryMD->MsWheaErrorHdr.Rev;
|
||||
switch (Rev) {
|
||||
case MS_WHEA_REV_0:
|
||||
// Fall through
|
||||
case MS_WHEA_REV_WILDCARD:
|
||||
// Store Rev0/Wildcard structure
|
||||
Status = MsWheaESV0InfoStore(MsWheaEntryMD);
|
||||
break;
|
||||
case MS_WHEA_REV_1:
|
||||
// Store Rev1 structure
|
||||
Status = MsWheaESV1InfoStore(MsWheaEntryMD);
|
||||
break;
|
||||
default:
|
||||
// Any unsupported revisions are not stored
|
||||
Status = EFI_UNSUPPORTED;
|
||||
break;
|
||||
}
|
||||
|
||||
if (Status == EFI_OUT_OF_RESOURCES) {
|
||||
// Early Storage is full, write the header error section
|
||||
MsWheaESSetHeaderFull(MsWheaEntryMD->MsWheaErrorHdr.Phase);
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine processes the stored errors on Early Storage data region
|
||||
|
||||
@param[in] ReportFn Callback function when a MS WHEA metadata is ready to report
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_INVALID_PARAMETER Null pointer detected
|
||||
@retval Others See implementation specific functions and MS_WHEA_ERR_REPORT_PS_FN
|
||||
definition for more details
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaESProcess (
|
||||
IN MS_WHEA_ERR_REPORT_PS_FN ReportFn
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
UINT8 Index = 0;
|
||||
MS_WHEA_REV mRevInfo;
|
||||
MS_WHEA_ERROR_ENTRY_MD MsWheaEntryMD;
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": enter...\n"));
|
||||
|
||||
if (ReportFn == NULL) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Input fucntion pointer cannot be null!\n"));
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Make sure the Early Storage is valid.
|
||||
if (MsWheaESRegionIsValid() == FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": the Early Storage is not valid!\n"));
|
||||
Status = EFI_NOT_FOUND;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Check if there is indication of Early Storage full, report it if so
|
||||
Status = MsWheaESCheckHeader(&MsWheaEntryMD);
|
||||
if (EFI_ERROR(Status) == FALSE) {
|
||||
Status = ReportFn(&MsWheaEntryMD, &MsWheaEntryMD.MsWheaErrorHdr, sizeof(MS_WHEA_ERROR_HDR));
|
||||
}
|
||||
else {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Early Storage header check status: %r\n", Status));
|
||||
}
|
||||
|
||||
// Go through normal entries
|
||||
while (Index < (MsWheaESGetMaxDataCount() - sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_COMMON))) {
|
||||
|
||||
Status = MsWheaESReadData(&mRevInfo,
|
||||
sizeof(MS_WHEA_REV),
|
||||
Index + OFFSET_OF(MS_WHEA_EARLY_STORAGE_ENTRY_COMMON, Rev));
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Early Storage storage read Index %d failed: %r\n", Index, Status));
|
||||
Index += sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_COMMON);
|
||||
continue;
|
||||
}
|
||||
|
||||
switch (mRevInfo) {
|
||||
case MS_WHEA_REV_WILDCARD:
|
||||
// Fall through
|
||||
case MS_WHEA_REV_0:
|
||||
Status = MsWheaESGetV0Info(&MsWheaEntryMD, &Index);
|
||||
if (EFI_ERROR(Status) == FALSE) {
|
||||
Status = ReportFn(&MsWheaEntryMD, &MsWheaEntryMD.MsWheaErrorHdr, sizeof(MS_WHEA_ERROR_HDR));
|
||||
}
|
||||
else {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": V0 Early Storage storage process failed %r\n", Status));
|
||||
Index += sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_COMMON);
|
||||
}
|
||||
break;
|
||||
case MS_WHEA_REV_1:
|
||||
Status = MsWheaESGetV1Info(&MsWheaEntryMD, &Index);
|
||||
if (EFI_ERROR(Status) == FALSE) {
|
||||
Status = ReportFn(&MsWheaEntryMD, &MsWheaEntryMD.MsWheaErrorHdr, sizeof(MS_WHEA_ERROR_HDR));
|
||||
}
|
||||
else {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": V1 Early Storage storage process failed %r\n", Status));
|
||||
Index += sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_COMMON);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
Index += sizeof(MS_WHEA_EARLY_STORAGE_ENTRY_COMMON);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// This is needed incase there is leftover garbage in default/failed cases
|
||||
MsWheaESClearAllData();
|
||||
|
||||
Cleanup:
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": exit...\n"));
|
||||
return Status;
|
||||
}
|
|
@ -0,0 +1,74 @@
|
|||
/** @file -- MsWheaEarlyStorageMgr.h
|
||||
|
||||
This header defines APIs to manipulate early storage for MsWheaReport usage.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#ifndef __MS_WHEA_EARLY_STORAGE_MGR__
|
||||
#define __MS_WHEA_EARLY_STORAGE_MGR__
|
||||
|
||||
#include "MsWheaReportCommon.h"
|
||||
|
||||
/**
|
||||
|
||||
This routine initialized the Early Storage MS WHEA store.
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
MsWheaESInit (
|
||||
VOID
|
||||
);
|
||||
|
||||
/**
|
||||
This routine will store data onto Early Storage data region based on supplied MS WHEA metadata
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval Others See MsWheaStoreCMOSFindSlot and MsWheaCMOSStoreWriteData for more details
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaESStoreEntry (
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD
|
||||
);
|
||||
|
||||
/**
|
||||
This routine processes the stored errors on Early Storage data region
|
||||
|
||||
@param[in] ReportFn Callback function when a MS WHEA metadata is ready to report
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval Others See implementation specific functions and MS_WHEA_ERR_REPORT_PS_FN
|
||||
definition for more details
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaESProcess (
|
||||
IN MS_WHEA_ERR_REPORT_PS_FN ReportFn
|
||||
);
|
||||
|
||||
#endif // __MS_WHEA_EARLY_STORAGE_MGR__
|
|
@ -0,0 +1,579 @@
|
|||
/** @file -- MsWheaReportCommon.c
|
||||
|
||||
This source implements MsWheaReport helpers shared by both PEI and DXE phases.
|
||||
|
||||
The APIs include populating fields in Common Platform Error (CPER) related headers,
|
||||
fill out timestamp based on CMOS, CMOS information storage, etc. The populated
|
||||
headers can be used to report Microsoft WHEA to OS via Hardware Error Records (HwErrRec).
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#include <Library/ReportStatusCodeLib.h>
|
||||
#include "MsWheaEarlyStorageMgr.h"
|
||||
#include "MsWheaReportCommon.h"
|
||||
|
||||
#define CPER_HDR_SEC_CNT 0x01
|
||||
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_CODE 0xA0A0A0A0
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_SIZE 0x40
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_SHORT_SIZE 0x08
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_PATTERN 0xC0
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_PHASE_BSFT 0x03
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_PI_BMSK 0x07
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_PATTERN 0xC0
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_REV_UNSUP 0x66
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_INFO 0x30303030
|
||||
#define MS_WHEA_IN_SITU_TEST_ERROR_ID 0x50505050
|
||||
|
||||
/************************************ Header Section *************************************/
|
||||
|
||||
/**
|
||||
This routine will fill out the CPER header for caller.
|
||||
|
||||
Zeroed: Flags, PersistenceInfo;
|
||||
|
||||
@param[out] CperHdr Supplies a pointer to CPER header structure
|
||||
@param[in] PayloadSize Length of entire payload to be included within this entry, refer to
|
||||
UEFI Spec for more information
|
||||
@param[in] ErrorSeverity Error severity of this entry
|
||||
@param[in] ErrorStatusCode Reported Status Code from ReportStatucCode* function
|
||||
@param[in] RecordIDGuid RecordID for error source identification, default to
|
||||
gMsWheaReportServiceGuid if NULL
|
||||
@param[in] NotificationType Notification type GUID of this entry, default to
|
||||
gEfiEventNotificationTypeBootGuid if NULL
|
||||
|
||||
@retval EFI_SUCCESS The operation completed successfully
|
||||
@retval EFI_INVALID_PARAMETER Any required input pointer is NULL
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
CreateCperHdrDefaultMin (
|
||||
OUT EFI_COMMON_ERROR_RECORD_HEADER *CperHdr,
|
||||
IN UINT32 PayloadSize,
|
||||
IN UINT32 ErrorSeverity,
|
||||
IN UINT32 ErrorStatusCode,
|
||||
IN EFI_GUID *RecordIDGuid OPTIONAL,
|
||||
IN EFI_GUID *NotificationType OPTIONAL
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
|
||||
if (CperHdr == NULL) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
SetMem(CperHdr, sizeof(EFI_COMMON_ERROR_RECORD_HEADER), 0);
|
||||
|
||||
CperHdr->SignatureStart = EFI_ERROR_RECORD_SIGNATURE_START;
|
||||
CperHdr->Revision = EFI_ERROR_RECORD_REVISION;
|
||||
CperHdr->SignatureEnd = EFI_ERROR_RECORD_SIGNATURE_END;
|
||||
CperHdr->SectionCount = CPER_HDR_SEC_CNT;
|
||||
CperHdr->ErrorSeverity = ErrorSeverity;
|
||||
CperHdr->ValidationBits = EFI_ERROR_RECORD_HEADER_PLATFORM_ID_VALID;
|
||||
CperHdr->RecordLength = (UINT32)(sizeof(EFI_COMMON_ERROR_RECORD_HEADER) + sizeof(EFI_ERROR_SECTION_DESCRIPTOR) + PayloadSize);
|
||||
|
||||
CperHdr->ValidationBits &= (~EFI_ERROR_RECORD_HEADER_TIME_STAMP_VALID);
|
||||
CopyGuid(&CperHdr->PlatformID, &gMsWheaReportServiceGuid);
|
||||
//SetMem(&CperHdr->PartitionID, sizeof(EFI_GUID), 0); // Not used, left zero.
|
||||
if (RecordIDGuid != NULL) {
|
||||
CopyGuid(&CperHdr->CreatorID, RecordIDGuid);
|
||||
}
|
||||
else {
|
||||
// Default to MS WHEA Service guid
|
||||
CopyGuid(&CperHdr->CreatorID, &gMsWheaReportServiceGuid);
|
||||
}
|
||||
|
||||
if (NotificationType) {
|
||||
CopyGuid(&CperHdr->NotificationType, NotificationType);
|
||||
}
|
||||
else {
|
||||
// Default to Boot Error
|
||||
CopyGuid(&CperHdr->NotificationType, &gEfiEventNotificationTypeBootGuid);
|
||||
}
|
||||
|
||||
// This is can be modified further
|
||||
CperHdr->RecordID = ErrorStatusCode;
|
||||
CperHdr->Flags |= EFI_HW_ERROR_FLAGS_PREVERR;
|
||||
//CperHdr->PersistenceInfo = 0;// Untouched.
|
||||
//SetMem(&CperHdr->Resv1, sizeof(CperHdr->Resv1), 0); // Reserved field, should be 0.
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine will fill out the CPER Section Descriptor for caller.
|
||||
|
||||
Zeroed: SectionFlags, FruId, FruString;
|
||||
|
||||
@param[out] CperErrSecDscp Supplies a pointer to CPER header structure
|
||||
@param[in] PayloadSize Length of entire payload to be included within this entry, refer to
|
||||
UEFI Spec for more information
|
||||
@param[in] ErrorSeverity Error severity of this entry
|
||||
@param[in] SectionType Section type GUID of this entry, default to
|
||||
gEfiFirmwareErrorSectionGuid if NULL
|
||||
|
||||
@retval EFI_SUCCESS The operation completed successfully
|
||||
@retval EFI_INVALID_PARAMETER Any required input pointer is NULL
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
CreateCperErrSecDscpDefaultMin (
|
||||
OUT EFI_ERROR_SECTION_DESCRIPTOR *CperErrSecDscp,
|
||||
IN UINT32 PayloadSize,
|
||||
IN UINT32 ErrorSeverity,
|
||||
IN EFI_GUID *SectionType OPTIONAL
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
|
||||
if (CperErrSecDscp == NULL) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
SetMem(CperErrSecDscp, sizeof(EFI_ERROR_SECTION_DESCRIPTOR), 0);
|
||||
|
||||
CperErrSecDscp->SectionOffset = sizeof(EFI_COMMON_ERROR_RECORD_HEADER) + sizeof(EFI_ERROR_SECTION_DESCRIPTOR);
|
||||
CperErrSecDscp->SectionLength = (UINT32) PayloadSize;
|
||||
CperErrSecDscp->Revision = MS_WHEA_SECTION_REVISION;
|
||||
//CperErrSecDscp->SecValidMask = 0;
|
||||
|
||||
//CperErrSecDscp->Resv1 = 0; // Reserved field, should be 0.
|
||||
//CperErrSecDscp->SectionFlags = 0; // Untouched.
|
||||
|
||||
if (SectionType) {
|
||||
CopyGuid(&CperErrSecDscp->SectionType, SectionType);
|
||||
}
|
||||
else {
|
||||
// Default to Firmware Error
|
||||
CopyGuid(&CperErrSecDscp->SectionType, &gEfiFirmwareErrorSectionGuid);
|
||||
}
|
||||
|
||||
//SetMem(&CperErrSecDscp->FruId, sizeof(CperErrSecDscp->FruId), 0); // Untouched.
|
||||
CperErrSecDscp->Severity = ErrorSeverity;
|
||||
//SetMem(CperErrSecDscp->FruString, sizeof(CperErrSecDscp->FruString), 0); // Untouched.
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine will fill out the Firmware Error Data header structure for caller.
|
||||
|
||||
@param[out] EfiFirmwareErrorData Supplies a pointer to Firmware Error Data header structure
|
||||
@param[in] ErrorStatusCode Reported Status Code from ReportStatucCode* function
|
||||
@param[in] RecordIDGuid RecordID for error source identification, default to
|
||||
gMsWheaReportServiceGuid if NULL
|
||||
|
||||
@retval EFI_SUCCESS The operation completed successfully
|
||||
@retval EFI_INVALID_PARAMETER Any required input pointer is NULL
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
CreateFwErrDataDefaultMin (
|
||||
OUT EFI_FIRMWARE_ERROR_DATA *EfiFirmwareErrorData,
|
||||
IN UINT32 ErrorStatusCode,
|
||||
IN EFI_GUID *RecordIDGuid OPTIONAL
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
if (EfiFirmwareErrorData == NULL) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
SetMem(EfiFirmwareErrorData, sizeof(EFI_FIRMWARE_ERROR_DATA), 0);
|
||||
|
||||
EfiFirmwareErrorData->ErrorType = EFI_FIRMWARE_ERROR_TYPE_SOC_TYPE2;
|
||||
EfiFirmwareErrorData->Revision = EFI_FIRMWARE_ERROR_REVISION;
|
||||
//SetMem(&EfiFirmwareErrorData->Resv1, sizeof(EfiFirmwareErrorData->Resv1), 0); // Reserved field.
|
||||
//EfiFirmwareErrorData->RecordId = 0; // Must be set to NULL
|
||||
|
||||
if (RecordIDGuid != NULL) {
|
||||
CopyGuid(&EfiFirmwareErrorData->RecordIdGuid, RecordIDGuid);
|
||||
}
|
||||
else {
|
||||
// Default to MS WHEA Service guid
|
||||
CopyGuid(&EfiFirmwareErrorData->RecordIdGuid, &gMsWheaReportServiceGuid);
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine will populate certain MS WHEA metadata fields based on supplied information
|
||||
|
||||
@param[in] Value Reported Status Code from ReportStatucCode* function
|
||||
@param[in] CurrentPhase Supplies the boot phase the reporting module is in
|
||||
@param[in] ReportHdr Supplies the pointer to reported MS WHEA header, will be treated as
|
||||
wildcard if cannot decode signature
|
||||
@param[in] CallerId Supplies the CallerId, will be populated into CPER table CreatorID
|
||||
field if supplied, else default to gMsWheaReportServiceGuid
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
**/
|
||||
STATIC
|
||||
VOID
|
||||
GenMsWheaEntryHeaderHelper (
|
||||
IN EFI_STATUS_CODE_VALUE Value,
|
||||
IN MS_WHEA_ERROR_PHASE CurrentPhase,
|
||||
IN CONST MS_WHEA_ERROR_HDR *ReportHdr OPTIONAL,
|
||||
IN CONST EFI_GUID *CallerId OPTIONAL,
|
||||
OUT MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD
|
||||
)
|
||||
{
|
||||
MS_WHEA_REV Rev = 0;
|
||||
|
||||
if (MsWheaEntryMD == NULL) {
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
SetMem(MsWheaEntryMD, sizeof(MS_WHEA_ERROR_ENTRY_MD), 0);
|
||||
|
||||
// Sanity check first
|
||||
if ((ReportHdr == NULL) || (ReportHdr->Signature != MS_WHEA_ERROR_SIGNATURE)) {
|
||||
// Could not understand this payload, wild card and severity set to informational
|
||||
Rev = MS_WHEA_REV_WILDCARD;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.ErrorSeverity = EFI_GENERIC_ERROR_INFO;
|
||||
}
|
||||
else {
|
||||
Rev = ReportHdr->Rev;
|
||||
}
|
||||
|
||||
MsWheaEntryMD->ErrorStatusCode = Value;
|
||||
|
||||
if (CallerId != NULL) {
|
||||
CopyGuid(&MsWheaEntryMD->CallerID, CallerId);
|
||||
}
|
||||
|
||||
if (Rev == MS_WHEA_REV_WILDCARD) {
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Signature = MS_WHEA_ERROR_SIGNATURE;
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Rev = Rev;
|
||||
}
|
||||
else {
|
||||
CopyMem(&MsWheaEntryMD->MsWheaErrorHdr, ReportHdr, sizeof(MS_WHEA_ERROR_HDR));
|
||||
}
|
||||
MsWheaEntryMD->MsWheaErrorHdr.Phase = CurrentPhase;
|
||||
|
||||
Cleanup:
|
||||
return;
|
||||
}
|
||||
|
||||
/**
|
||||
This routine will fill CPER related headers with certain preset values;
|
||||
|
||||
Presets: NotificationType: gEfiEventNotificationTypeBootGuid; SectionType: gEfiFirmwareErrorSectionGuid;
|
||||
Zeroed: CPER Header: Flags, RecordID; Section Descriptor: SectionFlags, FruId, FruString;
|
||||
|
||||
@param[out] CperHdr Supplies a pointer to CPER header structure
|
||||
@param[out] CperErrSecDscp Supplies a pointer to CPER Section Decsriptor structure
|
||||
@param[out] EfiFirmwareErrorData Supplies a pointer to Firmware Error Data header structure
|
||||
@param[in] MsWheaEntryMD Supplies a pointer to reported MS WHEA error metadata
|
||||
@param[in] PayloadSize Length of entire payload to be included within this entry, refer to
|
||||
UEFI Spec for more information
|
||||
|
||||
@retval EFI_SUCCESS The operation completed successfully
|
||||
@retval EFI_INVALID_PARAMETER Any required input pointer is NULL
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
CreateHeadersDefault (
|
||||
OUT EFI_COMMON_ERROR_RECORD_HEADER *CperHdr,
|
||||
OUT EFI_ERROR_SECTION_DESCRIPTOR *CperErrSecDscp,
|
||||
OUT EFI_FIRMWARE_ERROR_DATA *EfiFirmwareErrorData,
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN UINT32 PayloadSize
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
|
||||
if ((CperHdr == NULL) ||
|
||||
(CperErrSecDscp == NULL) ||
|
||||
(EfiFirmwareErrorData == NULL) ||
|
||||
(MsWheaEntryMD == NULL)) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = CreateCperHdrDefaultMin(CperHdr,
|
||||
PayloadSize,
|
||||
MsWheaEntryMD->MsWheaErrorHdr.ErrorSeverity,
|
||||
MsWheaEntryMD->ErrorStatusCode,
|
||||
&MsWheaEntryMD->CallerID, NULL);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = CreateCperErrSecDscpDefaultMin(CperErrSecDscp,
|
||||
PayloadSize,
|
||||
MsWheaEntryMD->MsWheaErrorHdr.ErrorSeverity,
|
||||
NULL);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = CreateFwErrDataDefaultMin(EfiFirmwareErrorData,
|
||||
MsWheaEntryMD->ErrorStatusCode,
|
||||
&MsWheaEntryMD->CallerID);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/************************************ Reporter Section *************************************/
|
||||
|
||||
/**
|
||||
This routine will filter status code based on status type, decode reported extended data , if any,
|
||||
generate MS WHEA metadata based on decoded information and either 1. pass generated metadata to supplied
|
||||
callback function for further processing or 2. store onto CMOS if boot phase and error severtiy meets
|
||||
certain requirements
|
||||
|
||||
@param[in] CodeType Indicates the type of status code being reported.
|
||||
@param[in] Value Describes the current status of a hardware or software entity. This
|
||||
includes information about the class and subclass that is used to
|
||||
classify the entity as well as an operation.
|
||||
@param[in] Instance The enumeration of a hardware or software entity within the system.
|
||||
Valid instance numbers start with 1.
|
||||
@param[in] CallerId This optional parameter may be used to identify the caller. This
|
||||
parameter allows the status code driver to apply different rules to
|
||||
different callers.
|
||||
@param[in] Data This optional parameter may be used to pass additional data.
|
||||
@param[in] CurrentPhase This is passed by the RSC handler by indicating what to do next
|
||||
(store critical information on the CMOS)
|
||||
@param[in] ReportFn Function pointer collect input argument and save to HwErrRec for OS
|
||||
to process
|
||||
|
||||
@retval EFI_SUCCESS The operation completed successfully
|
||||
@retval EFI_INVALID_PARAMETER Any required input pointer is NULL
|
||||
@retval Others Any other error that rises from Variable Services, Boot Services,
|
||||
Runtime Services, etc.
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
ReportHwErrRecRouter (
|
||||
IN EFI_STATUS_CODE_TYPE CodeType,
|
||||
IN EFI_STATUS_CODE_VALUE Value,
|
||||
IN UINT32 Instance,
|
||||
IN CONST EFI_GUID *CallerId,
|
||||
IN CONST EFI_STATUS_CODE_DATA *Data OPTIONAL,
|
||||
IN MS_WHEA_ERROR_PHASE CurrentPhase,
|
||||
IN MS_WHEA_ERR_REPORT_PS_FN ReportFn
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
UINT32 DataSize;
|
||||
MS_WHEA_ERROR_ENTRY_MD MsWheaEntryMD;
|
||||
VOID *TempPtr = NULL;
|
||||
|
||||
if (ReportFn == NULL) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": Input fucntion pointer cannot be null!\n"));
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if ((CodeType & MS_WHEA_ERROR_STATUS_TYPE) != MS_WHEA_ERROR_STATUS_TYPE) {
|
||||
// Do Nothing for minor errors
|
||||
Status = EFI_SUCCESS;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if ((Data != NULL) && (Data->Size >= sizeof(MS_WHEA_ERROR_HDR))) {
|
||||
// Skip the EFI_STATUS_CODE_DATA in the beginning
|
||||
GenMsWheaEntryHeaderHelper(Value,
|
||||
CurrentPhase,
|
||||
(MS_WHEA_ERROR_HDR*)(Data + 1),
|
||||
CallerId,
|
||||
&MsWheaEntryMD);
|
||||
}
|
||||
else {
|
||||
// This is invoked by ReportStatusCode(), generated error header will be payload
|
||||
GenMsWheaEntryHeaderHelper(Value,
|
||||
CurrentPhase,
|
||||
NULL,
|
||||
CallerId,
|
||||
&MsWheaEntryMD);
|
||||
}
|
||||
|
||||
if ((MsWheaEntryMD.MsWheaErrorHdr.ErrorSeverity == EFI_GENERIC_ERROR_FATAL) &&
|
||||
((CurrentPhase == MS_WHEA_PHASE_DXE) || (CurrentPhase == MS_WHEA_PHASE_PEI))) {
|
||||
Status = MsWheaESStoreEntry(&MsWheaEntryMD);
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
if (Data == NULL) {
|
||||
// Wildcard report without extended data
|
||||
DataSize = sizeof(MS_WHEA_ERROR_HDR);
|
||||
TempPtr = AllocatePool(DataSize);
|
||||
if (TempPtr == NULL) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto Cleanup;
|
||||
}
|
||||
CopyMem(TempPtr, &MsWheaEntryMD.MsWheaErrorHdr, DataSize);
|
||||
}
|
||||
else if ((Data->Size < sizeof(MS_WHEA_ERROR_HDR)) ||
|
||||
(((MS_WHEA_ERROR_HDR*)(Data + 1))->Signature != MS_WHEA_ERROR_SIGNATURE)) {
|
||||
// Wildcard report without formatted header
|
||||
DataSize = sizeof(MS_WHEA_ERROR_HDR) + Data->Size;
|
||||
TempPtr = AllocatePool(DataSize);
|
||||
if (TempPtr == NULL) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto Cleanup;
|
||||
}
|
||||
CopyMem(TempPtr, &MsWheaEntryMD.MsWheaErrorHdr, sizeof(MS_WHEA_ERROR_HDR));
|
||||
CopyMem(&((UINT8*)TempPtr)[sizeof(MS_WHEA_ERROR_HDR)], Data + 1, Data->Size);
|
||||
}
|
||||
else {
|
||||
// Well-formatted data
|
||||
DataSize = Data->Size;
|
||||
TempPtr = AllocatePool(DataSize);
|
||||
if (TempPtr == NULL) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto Cleanup;
|
||||
}
|
||||
CopyMem(TempPtr, Data + 1, Data->Size);
|
||||
// Overwrite the header since reporter might alter the data fields such as Phase
|
||||
CopyMem(TempPtr, &MsWheaEntryMD.MsWheaErrorHdr, sizeof(MS_WHEA_ERROR_HDR));
|
||||
}
|
||||
Status = ReportFn(&MsWheaEntryMD, TempPtr, DataSize);
|
||||
|
||||
Cleanup:
|
||||
if (TempPtr != NULL) {
|
||||
FreePool(TempPtr);
|
||||
}
|
||||
return Status;
|
||||
}
|
||||
|
||||
/************************************ Test Section *************************************/
|
||||
|
||||
/**
|
||||
This routine will create a few ReportStatusCode calls to test the implementation of backend service.
|
||||
1. This function should be invoked after evaluating gMsWheaPkgTokenSpaceGuid.PcdMsWheaReportTestEnable;
|
||||
2. Only the modules creating backend services should use this function;
|
||||
|
||||
@param[out] CurrentPhase Supplies the boot phase the reporting module is in
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
MsWheaInSituTest(
|
||||
IN MS_WHEA_ERROR_PHASE CurrentPhase
|
||||
)
|
||||
{
|
||||
UINT8 Data[sizeof(MS_WHEA_ERROR_HDR) + MS_WHEA_IN_SITU_TEST_ERROR_SIZE];
|
||||
UINT32 Size = sizeof(MS_WHEA_ERROR_HDR) + MS_WHEA_IN_SITU_TEST_ERROR_SIZE;
|
||||
MS_WHEA_ERROR_HDR *mMsWheaErrHdr;
|
||||
UINT8 TestIndex;
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": enter...\n"));
|
||||
|
||||
SetMem(Data, sizeof(MS_WHEA_ERROR_HDR), 0);
|
||||
|
||||
mMsWheaErrHdr = (MS_WHEA_ERROR_HDR*)Data;
|
||||
mMsWheaErrHdr->Signature = MS_WHEA_ERROR_SIGNATURE;
|
||||
mMsWheaErrHdr->CriticalInfo = MS_WHEA_IN_SITU_TEST_ERROR_INFO;
|
||||
mMsWheaErrHdr->ReporterID = MS_WHEA_IN_SITU_TEST_ERROR_ID;
|
||||
mMsWheaErrHdr->ErrorSeverity = EFI_GENERIC_ERROR_FATAL;
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": Fatal error report rev 0...\n"));
|
||||
TestIndex = 0;
|
||||
SetMem((mMsWheaErrHdr + 1),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_SIZE,
|
||||
(UINT8)(MS_WHEA_IN_SITU_TEST_ERROR_PATTERN |
|
||||
((CurrentPhase<<MS_WHEA_IN_SITU_TEST_ERROR_PHASE_BSFT) + TestIndex)));
|
||||
mMsWheaErrHdr->Rev = MS_WHEA_REV_0;
|
||||
ReportStatusCodeWithExtendedData((EFI_ERROR_MAJOR|EFI_ERROR_CODE),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_CODE,
|
||||
Data,
|
||||
Size);
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": Fatal error report rev 1...\n"));
|
||||
TestIndex ++;
|
||||
SetMem((mMsWheaErrHdr + 1),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_SIZE,
|
||||
(UINT8)(MS_WHEA_IN_SITU_TEST_ERROR_PATTERN |
|
||||
((CurrentPhase<<MS_WHEA_IN_SITU_TEST_ERROR_PHASE_BSFT) + TestIndex)));
|
||||
mMsWheaErrHdr->Rev = MS_WHEA_REV_1;
|
||||
ReportStatusCodeWithExtendedData((EFI_ERROR_MAJOR|EFI_ERROR_CODE),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_CODE,
|
||||
Data,
|
||||
Size);
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": Fatal error report unsupported rev...\n"));
|
||||
TestIndex ++;
|
||||
SetMem((mMsWheaErrHdr + 1),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_SIZE,
|
||||
(UINT8)(MS_WHEA_IN_SITU_TEST_ERROR_PATTERN |
|
||||
((CurrentPhase<<MS_WHEA_IN_SITU_TEST_ERROR_PHASE_BSFT) + TestIndex)));
|
||||
mMsWheaErrHdr->Rev = MS_WHEA_IN_SITU_TEST_ERROR_REV_UNSUP;
|
||||
ReportStatusCodeWithExtendedData((EFI_ERROR_MAJOR|EFI_ERROR_CODE),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_CODE,
|
||||
Data,
|
||||
Size);
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": Non-fatal error report unsupported rev...\n"));
|
||||
TestIndex ++;
|
||||
SetMem((mMsWheaErrHdr + 1),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_SIZE,
|
||||
(UINT8)(MS_WHEA_IN_SITU_TEST_ERROR_PATTERN |
|
||||
((CurrentPhase<<MS_WHEA_IN_SITU_TEST_ERROR_PHASE_BSFT) + TestIndex)));
|
||||
mMsWheaErrHdr->ErrorSeverity = EFI_GENERIC_ERROR_RECOVERABLE;
|
||||
ReportStatusCodeWithExtendedData((EFI_ERROR_MAJOR|EFI_ERROR_CODE),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_CODE,
|
||||
Data,
|
||||
Size);
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": Non-fatal error report rev wildcard...\n"));
|
||||
TestIndex ++;
|
||||
SetMem((mMsWheaErrHdr + 1),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_SIZE,
|
||||
(UINT8)(MS_WHEA_IN_SITU_TEST_ERROR_PATTERN |
|
||||
((CurrentPhase<<MS_WHEA_IN_SITU_TEST_ERROR_PHASE_BSFT) + TestIndex)));
|
||||
ReportStatusCodeWithExtendedData((EFI_ERROR_MAJOR|EFI_ERROR_CODE),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_CODE,
|
||||
(mMsWheaErrHdr + 1),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_SIZE);
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": Non-fatal error report rev short payload...\n"));
|
||||
TestIndex ++;
|
||||
SetMem((mMsWheaErrHdr + 1),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_SHORT_SIZE,
|
||||
(UINT8)(MS_WHEA_IN_SITU_TEST_ERROR_PATTERN |
|
||||
((CurrentPhase<<MS_WHEA_IN_SITU_TEST_ERROR_PHASE_BSFT) + TestIndex)));
|
||||
ReportStatusCodeWithExtendedData((EFI_ERROR_MAJOR|EFI_ERROR_CODE),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_CODE,
|
||||
(mMsWheaErrHdr + 1),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_SHORT_SIZE);
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": Non-fatal error report rev short...\n"));
|
||||
TestIndex ++;
|
||||
ReportStatusCode((EFI_ERROR_MAJOR|EFI_ERROR_CODE),
|
||||
MS_WHEA_IN_SITU_TEST_ERROR_CODE);
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": exit...\n"));
|
||||
}
|
|
@ -0,0 +1,169 @@
|
|||
/** @file -- MsWheaReportCommon.h
|
||||
|
||||
This header defines MsWheaReport related helper functions.
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#ifndef __MS_WHEA_REPORT_COMMON__
|
||||
#define __MS_WHEA_REPORT_COMMON__
|
||||
|
||||
#include <Guid/Cper.h>
|
||||
#include <Protocol/AcpiTable.h>
|
||||
#include <Library/DebugLib.h>
|
||||
#include <Library/BaseLib.h>
|
||||
#include <Library/BaseMemoryLib.h>
|
||||
#include <Library/MemoryAllocationLib.h>
|
||||
#include <MsWheaErrorStatus.h>
|
||||
|
||||
/************************************ Definition Section *************************************/
|
||||
|
||||
/**
|
||||
Definition wrapper to unify all bert/hwerrrec related specification versioning
|
||||
**/
|
||||
#define EFI_FIRMWARE_ERROR_REVISION 0x0002 // Set Firmware Error Record Revision to 2 as per UEFI Spec 2.7A
|
||||
#define MS_WHEA_SECTION_REVISION 0x0100 // Set Section Descriptor Revision to 1.0 as per UEFI Spec 2.7A
|
||||
|
||||
#define EFI_HW_ERR_REC_VAR_NAME L"HwErrRec"
|
||||
#define EFI_HW_ERR_REC_VAR_NAME_LEN 16 // Buffer length covers at least "HwErrRec####\0"
|
||||
|
||||
/**
|
||||
MS WHEA error entry metadata:
|
||||
|
||||
MsWheaErrorHdr: MS WHEA error header, either from payload or self-generated if wildcard.
|
||||
PayloadSize: Payload size of this error, when used for hob/linked list operation, including a MS WHEA
|
||||
metadata and a well formatted payload (starting with a MS_WHEA_ERROR_HDR, followed by raw
|
||||
payload).
|
||||
ErrorStatusCode: Reported Status Code value from ReportStatusCode*
|
||||
CallerID: Caller ID for identification purpose
|
||||
**/
|
||||
typedef struct MS_WHEA_ERROR_ENTRY_MD_T_DEF {
|
||||
MS_WHEA_ERROR_HDR MsWheaErrorHdr;
|
||||
UINT32 PayloadSize;
|
||||
UINT32 ErrorStatusCode;
|
||||
EFI_GUID CallerID;
|
||||
} MS_WHEA_ERROR_ENTRY_MD;
|
||||
|
||||
/**
|
||||
This routine accepts the Common Platform Error Record header and Section
|
||||
Descriptor and correspthen store on the flash as HwErrRec awaiting to be picked up by OS
|
||||
(Refer to UEFI Spec 2.7A)
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
@param[in] PayloadPtr The pointer to reported error block, the content will be copied
|
||||
@param[in] PayloadSize The size of a well formatted payload (starting with a
|
||||
MS_WHEA_ERROR_HDR, followed by raw payload)
|
||||
|
||||
@retval EFI_SUCCESS Entry addition is successful.
|
||||
@retval EFI_INVALID_PARAMETER Input has NULL pointer as input.
|
||||
@retval EFI_OUT_OF_RESOURCES Not enough spcae for the requested space.
|
||||
**/
|
||||
typedef
|
||||
EFI_STATUS
|
||||
(EFIAPI *MS_WHEA_ERR_REPORT_PS_FN) (
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN VOID *PayloadPtr,
|
||||
IN UINT32 PayloadSize
|
||||
);
|
||||
|
||||
/************************************ Function Section *************************************/
|
||||
|
||||
/**
|
||||
This routine will fill CPER related headers with certain preset values;
|
||||
|
||||
Presets: NotificationType: gEfiEventNotificationTypeBootGuid; SectionType: gEfiFirmwareErrorSectionGuid;
|
||||
Zeroed: CPER Header: Flags, RecordID; Section Descriptor: SectionFlags, FruId, FruString;
|
||||
|
||||
@param[out] CperHdr Supplies a pointer to CPER header structure
|
||||
@param[out] CperErrSecDscp Supplies a pointer to CPER Section Decsriptor structure
|
||||
@param[out] EfiFirmwareErrorData Supplies a pointer to Firmware Error Data header structure
|
||||
@param[in] MsWheaEntryMD Supplies a pointer to reported MS WHEA error metadata
|
||||
@param[in] PayloadSize Length of entire payload to be included within this entry, refer to
|
||||
UEFI Spec for more information
|
||||
|
||||
@retval EFI_SUCCESS The operation completed successfully
|
||||
@retval EFI_INVALID_PARAMETER Any required input pointer is NULL
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
CreateHeadersDefault (
|
||||
OUT EFI_COMMON_ERROR_RECORD_HEADER *CperHdr,
|
||||
OUT EFI_ERROR_SECTION_DESCRIPTOR *CperErrSecDscp,
|
||||
OUT EFI_FIRMWARE_ERROR_DATA *EfiFirmwareErrorData,
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN UINT32 PayloadSize
|
||||
);
|
||||
|
||||
/**
|
||||
This routine will filter status code based on status type, decode reported extended data , if any,
|
||||
generate MS WHEA metadata based on decoded information and either 1. pass generated metadata to supplied
|
||||
callback function for further processing or 2. store onto CMOS if boot phase and error severtiy meets
|
||||
certain requirements
|
||||
|
||||
@param[in] CodeType Indicates the type of status code being reported.
|
||||
@param[in] Value Describes the current status of a hardware or software entity. This
|
||||
includes information about the class and subclass that is used to
|
||||
classify the entity as well as an operation.
|
||||
@param[in] Instance The enumeration of a hardware or software entity within the system.
|
||||
Valid instance numbers start with 1.
|
||||
@param[in] CallerId This optional parameter may be used to identify the caller. This
|
||||
parameter allows the status code driver to apply different rules to
|
||||
different callers.
|
||||
@param[in] Data This optional parameter may be used to pass additional data.
|
||||
@param[in] CurrentPhase This is passed by the RSC handler by indicating what to do next
|
||||
(store critical information on the CMOS)
|
||||
@param[in] ReportFn Function pointer collect input argument and save to HwErrRec for OS
|
||||
to process
|
||||
|
||||
@retval EFI_SUCCESS The operation completed successfully
|
||||
@retval EFI_INVALID_PARAMETER Any required input pointer is NULL
|
||||
@retval Others Any other error that rises from Variable Services, Boot Services,
|
||||
Runtime Services, etc.
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
ReportHwErrRecRouter (
|
||||
IN EFI_STATUS_CODE_TYPE CodeType,
|
||||
IN EFI_STATUS_CODE_VALUE Value,
|
||||
IN UINT32 Instance,
|
||||
IN CONST EFI_GUID *CallerId,
|
||||
IN CONST EFI_STATUS_CODE_DATA *Data OPTIONAL,
|
||||
IN MS_WHEA_ERROR_PHASE CurrentPhase,
|
||||
IN MS_WHEA_ERR_REPORT_PS_FN ReportFn
|
||||
);
|
||||
|
||||
/**
|
||||
This routine will create a few ReportStatusCode calls to test the implementation of backend service.
|
||||
1. This function should be invoked after evaluating gMsWheaPkgTokenSpaceGuid.PcdMsWheaReportTestEnable;
|
||||
2. Only the modules creating backend services should use this function;
|
||||
|
||||
@param[out] CurrentPhase Supplies the boot phase the reporting module is in
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
MsWheaInSituTest(
|
||||
IN MS_WHEA_ERROR_PHASE CurrentPhase
|
||||
);
|
||||
|
||||
#endif //__MS_WHEA_REPORT_COMMON__
|
|
@ -0,0 +1,188 @@
|
|||
/** @file -- MsWheaReportPei.c
|
||||
|
||||
This Pei module will produce a RSC listener that listens to reported status codes.
|
||||
|
||||
Certains errors will be collected and added to Hob List and waiting to be collected
|
||||
and/or stored during Dxe phase;
|
||||
|
||||
Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
All rights reserved.
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
1. Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
**/
|
||||
|
||||
#include <Library/PeiServicesLib.h>
|
||||
#include <Guid/VariableFormat.h>
|
||||
#include <Library/PcdLib.h>
|
||||
#include <Library/HobLib.h>
|
||||
#include <Library/ReportStatusCodeLib.h>
|
||||
#include <Ppi/ReportStatusCodeHandler.h>
|
||||
#include "MsWheaEarlyStorageMgr.h"
|
||||
#include "MsWheaReportCommon.h"
|
||||
|
||||
/**
|
||||
Handler function that validates input arguments, and create a hob list entry for this input for later process.
|
||||
|
||||
@param[in] MsWheaEntryMD The pointer to reported MS WHEA error metadata
|
||||
@param[in] PayloadPtr The pointer to reported error block payload, the content will be copied
|
||||
@param[in] PayloadSize The size of reported error block payload
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval EFI_OUT_OF_RESOURCES List cannot make the space for requested error block payload
|
||||
@retval EFI_INVALID_PARAMETER Null pointer or zero length payload detected or length and header
|
||||
length field exceeds variable limit
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaReportHandlerPei(
|
||||
IN MS_WHEA_ERROR_ENTRY_MD *MsWheaEntryMD,
|
||||
IN VOID *PayloadPtr,
|
||||
IN UINT32 PayloadSize
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
UINT32 Index;
|
||||
UINT32 Size;
|
||||
VOID *MsWheaReportEntry = NULL;
|
||||
|
||||
if ((PayloadPtr == NULL) ||
|
||||
(PayloadSize == 0) ||
|
||||
(MsWheaEntryMD == NULL) ||
|
||||
((PayloadSize +
|
||||
sizeof(EFI_COMMON_ERROR_RECORD_HEADER) +
|
||||
sizeof(EFI_ERROR_SECTION_DESCRIPTOR) +
|
||||
sizeof(AUTHENTICATED_VARIABLE_HEADER) +
|
||||
EFI_HW_ERR_REC_VAR_NAME_LEN * sizeof(CHAR16)) >
|
||||
PcdGet32 (PcdMaxHardwareErrorVariableSize)) ) {
|
||||
Status = EFI_INVALID_PARAMETER;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
// Add this block to the list
|
||||
Size = sizeof(MS_WHEA_ERROR_ENTRY_MD) + PayloadSize;
|
||||
|
||||
MsWheaReportEntry = BuildGuidHob(&gMsWheaReportServiceGuid, Size);
|
||||
if (MsWheaReportEntry == NULL) {
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
ZeroMem(MsWheaReportEntry, Size);
|
||||
|
||||
Index = 0;
|
||||
CopyMem(&((UINT8*)MsWheaReportEntry)[Index], MsWheaEntryMD, sizeof(MS_WHEA_ERROR_ENTRY_MD));
|
||||
|
||||
Index = sizeof(MS_WHEA_ERROR_ENTRY_MD);
|
||||
CopyMem(&((UINT8*)MsWheaReportEntry)[Index], PayloadPtr, PayloadSize);
|
||||
|
||||
((MS_WHEA_ERROR_ENTRY_MD*)MsWheaReportEntry)->PayloadSize = Size;
|
||||
|
||||
Cleanup:
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
Added module phase information and route reported status code value and extended data to ReportHwErrRecRouter
|
||||
for further processing.
|
||||
|
||||
@param[in] PeiServices Pointer to PEI services table.
|
||||
@param[in] CodeType Indicates the type of status code being reported.
|
||||
@param[in] Value Describes the current status of a hardware or software entity. This
|
||||
includes information about the class and subclass that is used to
|
||||
classify the entity as well as an operation.
|
||||
@param[in] Instance The enumeration of a hardware or software entity within the system.
|
||||
Valid instance numbers start with 1.
|
||||
@param[in] CallerId This optional parameter may be used to identify the caller. This
|
||||
parameter allows the status code driver to apply different rules to
|
||||
different callers.
|
||||
@param[in] Data This optional parameter may be used to pass additional data.
|
||||
|
||||
@retval EFI_SUCCESS Operation is successful
|
||||
@retval Others Any other error that rises from Variable Services, Boot Services,
|
||||
Runtime Services, etc.
|
||||
**/
|
||||
STATIC
|
||||
EFI_STATUS
|
||||
MsWheaRscHandlerPei (
|
||||
IN CONST EFI_PEI_SERVICES** PeiServices,
|
||||
IN EFI_STATUS_CODE_TYPE CodeType,
|
||||
IN EFI_STATUS_CODE_VALUE Value,
|
||||
IN UINT32 Instance,
|
||||
IN CONST EFI_GUID *CallerId,
|
||||
IN CONST EFI_STATUS_CODE_DATA *Data OPTIONAL
|
||||
)
|
||||
{
|
||||
return ReportHwErrRecRouter(CodeType,
|
||||
Value,
|
||||
Instance,
|
||||
CallerId,
|
||||
Data,
|
||||
MS_WHEA_PHASE_PEI,
|
||||
MsWheaReportHandlerPei);
|
||||
}
|
||||
|
||||
/**
|
||||
Entry to MsWheaReportPei.
|
||||
|
||||
@param FileHandle The image handle.
|
||||
@param PeiServices The PEI services table.
|
||||
|
||||
@retval Status From internal routine or boot object, should not fail
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
MsWheaReportPeiEntry (
|
||||
IN EFI_PEI_FILE_HANDLE FileHandle,
|
||||
IN CONST EFI_PEI_SERVICES **PeiServices
|
||||
)
|
||||
{
|
||||
|
||||
EFI_STATUS Status = EFI_SUCCESS;
|
||||
EFI_PEI_RSC_HANDLER_PPI *RscHandlerPpi;
|
||||
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": enter...\n"));
|
||||
|
||||
// Insert signature and clear the space, if not already clear
|
||||
MsWheaESInit();
|
||||
|
||||
Status = PeiServicesLocatePpi(&gEfiPeiRscHandlerPpiGuid,
|
||||
0,
|
||||
NULL,
|
||||
(VOID**)&RscHandlerPpi);
|
||||
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": failed to locate PEI RSC Handler PPI (%r)\n", Status));
|
||||
goto Cleanup;
|
||||
}
|
||||
|
||||
Status = RscHandlerPpi->Register(MsWheaRscHandlerPei);
|
||||
if (EFI_ERROR(Status) != FALSE) {
|
||||
DEBUG((DEBUG_ERROR, __FUNCTION__ ": failed to register PEI RSC Handler PPI (%r)\n", Status));
|
||||
}
|
||||
|
||||
if (PcdGetBool(PcdMsWheaReportTestEnable) != FALSE) {
|
||||
MsWheaInSituTest(MS_WHEA_PHASE_PEI);
|
||||
}
|
||||
|
||||
Cleanup:
|
||||
DEBUG((DEBUG_INFO, __FUNCTION__ ": exit (%r)\n", Status));
|
||||
return Status;
|
||||
}
|
|
@ -0,0 +1,85 @@
|
|||
## @file -- MsWheaReportPei.inf
|
||||
#
|
||||
# MsWheaReportPei implements Microsoft WHEA report service for PEI phase.
|
||||
#
|
||||
# Copyright (c) 2018, Microsoft Corporation
|
||||
|
||||
# All rights reserved.
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
# 1. Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions and the following disclaimer.
|
||||
# 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions and the following disclaimer in the documentation
|
||||
# and/or other materials provided with the distribution.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
# IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
# LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
# OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
# ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
##
|
||||
|
||||
[Defines]
|
||||
INF_VERSION = 0x00010005
|
||||
BASE_NAME = MsWheaReportPei
|
||||
FILE_GUID = 57A2921A-7BC2-43C5-AA5D-064EDCBB992F
|
||||
MODULE_TYPE = PEIM
|
||||
VERSION_STRING = 1.0
|
||||
ENTRY_POINT = MsWheaReportPeiEntry
|
||||
|
||||
#
|
||||
# The following information is for reference only and not required by the
|
||||
# build tools.
|
||||
#
|
||||
# VALID_ARCHITECTURES = IA32 X64 IPF EBC
|
||||
#
|
||||
|
||||
[Sources]
|
||||
../MsWheaReportCommon.h
|
||||
../MsWheaReportCommon.c
|
||||
../MsWheaEarlyStorageMgr.c
|
||||
../MsWheaEarlyStorageMgr.h
|
||||
MsWheaReportPei.c
|
||||
|
||||
[Packages]
|
||||
MdePkg/MdePkg.dec
|
||||
MdeModulePkg/MdeModulePkg.dec
|
||||
MsWheaPkg/MsWheaPkg.dec
|
||||
|
||||
[LibraryClasses]
|
||||
BaseLib
|
||||
BaseMemoryLib
|
||||
DebugLib
|
||||
HobLib
|
||||
IoLib
|
||||
MemoryAllocationLib
|
||||
PcdLib
|
||||
ReportStatusCodeLib
|
||||
PeimEntryPoint
|
||||
PeiServicesLib
|
||||
MsWheaEarlyStorageLib
|
||||
|
||||
[Protocols]
|
||||
|
||||
[Pcd]
|
||||
gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaReportTestEnable
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaReportPcatCapacity
|
||||
gMsWheaPkgTokenSpaceGuid.PcdMsWheaEarlyStorageDefaultValue
|
||||
|
||||
[Ppis]
|
||||
gEfiPeiRscHandlerPpiGuid ## CONSUMES
|
||||
|
||||
[Guids]
|
||||
gMsWheaReportServiceGuid ## SOMETIMES_CONSUMES
|
||||
gEfiFirmwareErrorSectionGuid ## SOMETIMES_CONSUMES
|
||||
gEfiEventNotificationTypeBootGuid ## SOMETIMES_CONSUMES
|
||||
|
||||
[Depex]
|
||||
gEfiPeiRscHandlerPpiGuid
|
Разница между файлами не показана из-за своего большого размера
Загрузить разницу
|
@ -0,0 +1,80 @@
|
|||
## @file MsWheaReportUnitTestApp.inf
|
||||
#
|
||||
# Tests for MS WHEA report tests with various payloads and error severities.
|
||||
##
|
||||
# Copyright (c) 2018, Microsoft Corporation
|
||||
#
|
||||
# All rights reserved.
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
# 1. Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions and the following disclaimer.
|
||||
# 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions and the following disclaimer in the documentation
|
||||
# and/or other materials provided with the distribution.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||
# IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
|
||||
# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
# LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
||||
# OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
# ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
##
|
||||
|
||||
[Defines]
|
||||
INF_VERSION = 0x00010005
|
||||
BASE_NAME = MsWheaReportUnitTestApp
|
||||
FILE_GUID = 75C3E1C3-40EE-4CC2-AF40-5ADE47870D86
|
||||
VERSION_STRING = 1.0
|
||||
MODULE_TYPE = UEFI_APPLICATION
|
||||
ENTRY_POINT = MsWheaReportUnitTestAppEntryPoint
|
||||
|
||||
#
|
||||
# The following information is for reference only and not required by the build tools.
|
||||
#
|
||||
# VALID_ARCHITECTURES = IA32 X64
|
||||
#
|
||||
|
||||
|
||||
[Sources]
|
||||
MsWheaReportUnitTestApp.c
|
||||
|
||||
[Packages]
|
||||
MdePkg/MdePkg.dec
|
||||
MdeModulePkg/MdeModulePkg.dec
|
||||
MsUnitTestPkg/MsUnitTestPkg.dec
|
||||
MsWheaPkg/MsWheaPkg.dec
|
||||
ShellPkg/ShellPkg.dec
|
||||
|
||||
[LibraryClasses]
|
||||
DebugLib
|
||||
UefiApplicationEntryPoint
|
||||
UefiBootServicesTableLib
|
||||
UnitTestLib
|
||||
UnitTestLogLib
|
||||
UnitTestPersistenceLib
|
||||
UnitTestAssertLib
|
||||
PrintLib
|
||||
ReportStatusCodeLib
|
||||
MemoryAllocationLib
|
||||
BaseLib
|
||||
ShellLib
|
||||
PcdLib
|
||||
UefiLib
|
||||
|
||||
[Protocols]
|
||||
|
||||
[Guids]
|
||||
gEfiEventNotificationTypeBootGuid ## CONSUMES
|
||||
gEfiFirmwareErrorSectionGuid ## CONSUMES
|
||||
gEfiHardwareErrorVariableGuid ## CONSUMES
|
||||
gMsWheaReportServiceGuid ## CONSUMES
|
||||
|
||||
[FixedPcd]
|
||||
gEfiMdeModulePkgTokenSpaceGuid.PcdHwErrStorageSize ## CONSUMES
|
||||
gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize ## CONSUMES
|
||||
gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableSize ## CONSUMES
|
Загрузка…
Ссылка в новой задаче