From nobody Mon Feb 9 18:44:16 2026 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) client-ip=66.175.222.108; envelope-from=bounce+27952+72314+1787277+3901457@groups.io; helo=mail02.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+72314+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1614652146; cv=none; d=zohomail.com; s=zohoarc; b=DkuWRAjR2Ti0y9qNJGXfOUjvP0Is6SVuSmi2p3jzUqudAN4z7lxWVLGLYaKQI99KC44N/DsQzSTv7QpiExravJq15M1kw3wx9Vi4t24RuvmnMpRINZ3JtWbJVYbhwhwP2lj09G2T57NOoj7z1pTYLsExrMpQNn2ElaMwbJPSBuI= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1614652146; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Id:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:References:Sender:Subject:To; bh=71JxPQLaoSvle6PmoAe5B0xwTKLPzKoiCpdGFTBgYvw=; b=h5Kf4AATMB6k+5YzDgA6Wq4Az5kaOJHIJ/9+71UL5VE3qa9oRA/KLvLfPmoyOAZi18tuFQOdqZaG9S7aEhzDmnkOIkKcYGsZIhr6NqMmu5VJOu73j0TvUMWLV7ObD8ZGFFhgDJORQAkKRFQ3EFqYhDSd2F87PIvtu53vCF+YUmI= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce+27952+72314+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) header.from= Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by mx.zohomail.com with SMTPS id 1614652146919470.95474816672095; Mon, 1 Mar 2021 18:29:06 -0800 (PST) Return-Path: X-Received: by 127.0.0.2 with SMTP id CTmmYY1788612xXtCdZiAoFb; Mon, 01 Mar 2021 18:29:06 -0800 X-Received: from mga02.intel.com (mga02.intel.com []) by mx.groups.io with SMTP id smtpd.web12.3173.1614652144809506276 for ; Mon, 01 Mar 2021 18:29:05 -0800 IronPort-SDR: 03LwGFK28WTE7U/RwJTHHKo7ghOpaALvy3wo6i8WirA4tTcPBxMReZacYdPyQX1pgRxSIoDbte I98Vg0nriLrQ== X-IronPort-AV: E=McAfee;i="6000,8403,9910"; a="173797234" X-IronPort-AV: E=Sophos;i="5.81,216,1610438400"; d="scan'208";a="173797234" X-Received: from fmsmga004.fm.intel.com ([10.253.24.48]) by orsmga101.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 01 Mar 2021 18:29:02 -0800 IronPort-SDR: CHwjJyqcvAMi9O/VzAcIVjuGIb4I8TZTtJdvR4vyn3lvvOHcbdKmY0pZX/z6FIJvaFONtzyIN7 hl3eQu3uUOBQ== X-IronPort-AV: E=Sophos;i="5.81,216,1610438400"; d="scan'208";a="427169869" X-Received: from nldesimo-desk1.amr.corp.intel.com ([10.212.174.59]) by fmsmga004-auth.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 01 Mar 2021 18:29:01 -0800 From: "Nate DeSimone" To: devel@edk2.groups.io Cc: Isaac Oram , Sai Chaganty , Liming Gao , Michael Kubacki Subject: [edk2-devel] [edk2-platforms] [PATCH v1 4/9] IpmiFeaturePkg: Add GenericIpmi driver common code Date: Mon, 1 Mar 2021 18:27:59 -0800 Message-Id: <20210302022804.8641-5-nathaniel.l.desimone@intel.com> In-Reply-To: <20210302022804.8641-1-nathaniel.l.desimone@intel.com> References: <20210302022804.8641-1-nathaniel.l.desimone@intel.com> MIME-Version: 1.0 Precedence: Bulk List-Unsubscribe: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,nathaniel.l.desimone@intel.com X-Gm-Message-State: ijjDvoQ2Yl9KExfb7h4I4wOpx1787277AA= Content-Transfer-Encoding: quoted-printable DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1614652146; bh=F8sjZ5NrozpIQ0uNhyJRCmQG/O3Yk4blsJ3Ydf8WlQg=; h=Cc:Date:From:Reply-To:Subject:To; b=L3qy98MjBTk+/GzC2MdVfqTo7V5nK9sI7lD6RyttOg/CchBJG63LiQKlX2U2kppbODS IYfFSFbpQvWNJYl/n4U0pDoKENRHF4v8kjiTgw+0yOHs0TvCnrhDrGfnzBJXnJyj0HV2G a6Agb5SUfQoZ5kAe3iYnShs0/M7UZRar6zg= X-ZohoMail-DKIM: pass (identity @groups.io) Content-Type: text/plain; charset="utf-8" From: Isaac Oram REF: https://bugzilla.tianocore.org/show_bug.cgi?id=3D3242 Adds phase independent code for the generic IPMI transport driver. Cc: Sai Chaganty Cc: Liming Gao Cc: Michael Kubacki Signed-off-by: Isaac Oram Co-authored-by: Nate DeSimone --- .../GenericIpmi/Common/IpmiBmc.c | 297 +++++++++++ .../GenericIpmi/Common/IpmiBmc.h | 44 ++ .../GenericIpmi/Common/IpmiBmcCommon.h | 179 +++++++ .../GenericIpmi/Common/IpmiHooks.c | 96 ++++ .../GenericIpmi/Common/IpmiHooks.h | 81 +++ .../GenericIpmi/Common/IpmiPhysicalLayer.h | 29 ++ .../GenericIpmi/Common/KcsBmc.c | 483 ++++++++++++++++++ .../GenericIpmi/Common/KcsBmc.h | 236 +++++++++ 8 files changed, 1445 insertions(+) create mode 100644 Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gener= icIpmi/Common/IpmiBmc.c create mode 100644 Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gener= icIpmi/Common/IpmiBmc.h create mode 100644 Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gener= icIpmi/Common/IpmiBmcCommon.h create mode 100644 Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gener= icIpmi/Common/IpmiHooks.c create mode 100644 Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gener= icIpmi/Common/IpmiHooks.h create mode 100644 Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gener= icIpmi/Common/IpmiPhysicalLayer.h create mode 100644 Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gener= icIpmi/Common/KcsBmc.c create mode 100644 Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gener= icIpmi/Common/KcsBmc.h diff --git a/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/= Common/IpmiBmc.c b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Generi= cIpmi/Common/IpmiBmc.c new file mode 100644 index 0000000000..03b8174e37 --- /dev/null +++ b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/Common/= IpmiBmc.c @@ -0,0 +1,297 @@ +/** @file + IPMI Transport common layer driver + + @copyright + Copyright 1999 - 2021 Intel Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent +**/ + +#include "IpmiBmc.h" + +EFI_STATUS +UpdateErrorStatus ( + IN UINT8 BmcError, + IPMI_BMC_INSTANCE_DATA *IpmiInstance + ) +/*++ + +Routine Description: + + Check if the completion code is a Soft Error and increment the count. T= he count + is not updated if the BMC is in Force Update Mode. + +Arguments: + + BmcError - Completion code to check + IpmiInstance - BMC instance data + +Returns: + + EFI_SUCCESS - Status + +--*/ +{ + UINT8 Errors[] =3D COMPLETION_CODES; + UINT16 CodeCount; + UINT8 i; + + CodeCount =3D sizeof (Errors) / sizeof (Errors[0]); + for (i =3D 0; i < CodeCount; i++) { + if (BmcError =3D=3D Errors[i]) { + // + // Don't change Bmc Status flag if the BMC is in Force Update Mode. + // + if (IpmiInstance->BmcStatus !=3D BMC_UPDATE_IN_PROGRESS) { + IpmiInstance->BmcStatus =3D BMC_SOFTFAIL; + } + + IpmiInstance->SoftErrorCount++; + break; + } + } + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +IpmiSendCommandToBmc ( + IN IPMI_TRANSPORT *This, + IN UINT8 NetFunction, + IN UINT8 Lun, + IN UINT8 Command, + IN UINT8 *CommandData, + IN UINT8 CommandDataSize, + IN OUT UINT8 *ResponseData, + IN OUT UINT8 *ResponseDataSize, + IN VOID *Context + ) +/*++ + +Routine Description: + + Send IPMI command to BMC + +Arguments: + + This - Pointer to IPMI protocol instance + NetFunction - Net Function of command to send + Lun - LUN of command to send + Command - IPMI command to send + CommandData - Pointer to command data buffer, if needed + CommandDataSize - Size of command data buffer + ResponseData - Pointer to response data buffer + ResponseDataSize - Pointer to response data buffer size + Context - Context + +Returns: + + EFI_INVALID_PARAMETER - One of the input values is bad + EFI_DEVICE_ERROR - IPMI command failed + EFI_BUFFER_TOO_SMALL - Response buffer is too small + EFI_UNSUPPORTED - Command is not supported by BMC + EFI_SUCCESS - Command completed successfully + +--*/ +{ + IPMI_BMC_INSTANCE_DATA *IpmiInstance; + UINT8 DataSize; + EFI_STATUS Status; + IPMI_COMMAND *IpmiCommand; + IPMI_RESPONSE *IpmiResponse; + UINT8 RetryCnt =3D IPMI_SEND_COMMAND_MAX_RETRY; + UINT8 Index; + + IpmiInstance =3D INSTANCE_FROM_SM_IPMI_BMC_THIS (This); + + while (RetryCnt--) { + // + // The TempData buffer is used for both sending command data and recei= ving + // response data. Since the command format is different from the resp= onse + // format, the buffer is cast to both structure definitions. + // + IpmiCommand =3D (IPMI_COMMAND*) IpmiInstance->TempData; + IpmiResponse =3D (IPMI_RESPONSE*) IpmiInstance->TempData; + + // + // Send IPMI command to BMC + // + IpmiCommand->Lun =3D Lun; + IpmiCommand->NetFunction =3D NetFunction; + IpmiCommand->Command =3D Command; + + // + // Ensure that the buffer is valid before attempting to copy the comma= nd data + // buffer into the IpmiCommand structure. + // + if (CommandDataSize > 0) { + if (CommandData =3D=3D NULL) { + return EFI_INVALID_PARAMETER; + } + + CopyMem ( + IpmiCommand->CommandData, + CommandData, + CommandDataSize + ); + } + + Status =3D SendDataToBmcPort ( + IpmiInstance->KcsTimeoutPeriod, + IpmiInstance->IpmiIoBase, + Context, + (UINT8 *) IpmiCommand, + (CommandDataSize + IPMI_COMMAND_HEADER_SIZE) + ); + + if (Status !=3D EFI_SUCCESS) { + IpmiInstance->BmcStatus =3D BMC_SOFTFAIL; + IpmiInstance->SoftErrorCount++; + return Status; + } + + // + // Get Response to IPMI Command from BMC. + // Subtract 1 from DataSize so memory past the end of the buffer can't= be written + // + DataSize =3D MAX_TEMP_DATA - 1; + Status =3D ReceiveBmcDataFromPort ( + IpmiInstance->KcsTimeoutPeriod, + IpmiInstance->IpmiIoBase, + Context, + (UINT8 *) IpmiResponse, + &DataSize + ); + + if (Status !=3D EFI_SUCCESS) { + IpmiInstance->BmcStatus =3D BMC_SOFTFAIL; + IpmiInstance->SoftErrorCount++; + return Status; + } + + // + // If we got this far without any error codes, but the DataSize less t= han IPMI_RESPONSE_HEADER_SIZE, then the + // command response failed, so do not continue. + // + if (DataSize < IPMI_RESPONSE_HEADER_SIZE) { + return EFI_DEVICE_ERROR; + } + + if ((IpmiResponse->CompletionCode !=3D COMP_CODE_NORMAL) && + (IpmiInstance->BmcStatus =3D=3D BMC_UPDATE_IN_PROGRESS)) { + // + // If the completion code is not normal and the BMC is in Force Upda= te + // mode, then update the error status and return EFI_UNSUPPORTED. + // + UpdateErrorStatus ( + IpmiResponse->CompletionCode, + IpmiInstance + ); + return EFI_UNSUPPORTED; + } else if (IpmiResponse->CompletionCode !=3D COMP_CODE_NORMAL) { + // + // Otherwise if the BMC is in normal mode, but the completion code + // is not normal, then update the error status and return device err= or. + // + UpdateErrorStatus ( + IpmiResponse->CompletionCode, + IpmiInstance + ); + // + // Intel Server System Integrated Baseboard Management Controller (B= MC) Firmware v0.62 + // D4h C Insufficient privilege, in KCS channel this indicates KCS P= olicy Control Mode is Deny All. + // In authenticated channels this indicates invalid authentication/p= rivilege. + // + if (IpmiResponse->CompletionCode =3D=3D COMP_INSUFFICIENT_PRIVILEGE)= { + return EFI_SECURITY_VIOLATION; + } else { + return EFI_DEVICE_ERROR; + } + } + + // + // Verify the response data buffer passed in is big enough. + // + if ((DataSize - IPMI_RESPONSE_HEADER_SIZE) > *ResponseDataSize) { + // + //Verify the response data matched with the cmd sent. + // + if ((IpmiResponse->NetFunction !=3D (NetFunction | 0x1)) || (IpmiRes= ponse->Command !=3D Command)) { + if (0 =3D=3D RetryCnt) { + return EFI_DEVICE_ERROR; + } else { + continue; + } + } + return EFI_BUFFER_TOO_SMALL; + } + + break; + } + // + // Copy data over to the response data buffer. + // + *ResponseDataSize =3D DataSize - IPMI_RESPONSE_HEADER_SIZE; + CopyMem ( + ResponseData, + IpmiResponse->ResponseData, + *ResponseDataSize + ); + + // + // Add completion code in response data to meet the requirement of IPMI = spec 2.0 + // + *ResponseDataSize +=3D 1; // Add one byte for Completion Code + for (Index =3D 1; Index < *ResponseDataSize; Index++) { + ResponseData [*ResponseDataSize - Index] =3D ResponseData [*ResponseDa= taSize - (Index + 1)]; + } + ResponseData [0] =3D IpmiResponse->CompletionCode; + + IpmiInstance->BmcStatus =3D BMC_OK; + return EFI_SUCCESS; +} + + +EFI_STATUS +EFIAPI +IpmiBmcStatus ( + IN IPMI_TRANSPORT *This, + OUT BMC_STATUS *BmcStatus, + OUT SM_COM_ADDRESS *ComAddress, + IN VOID *Context + ) +/*++ + +Routine Description: + + Updates the BMC status and returns the Com Address + +Arguments: + + This - Pointer to IPMI protocol instance + BmcStatus - BMC status + ComAddress - Com Address + Context - Context + +Returns: + + EFI_SUCCESS - Success + +--*/ +{ + IPMI_BMC_INSTANCE_DATA *IpmiInstance; + + IpmiInstance =3D INSTANCE_FROM_SM_IPMI_BMC_THIS (This); + + if ((IpmiInstance->BmcStatus =3D=3D BMC_SOFTFAIL) && (IpmiInstance->Soft= ErrorCount >=3D MAX_SOFT_COUNT)) { + IpmiInstance->BmcStatus =3D BMC_HARDFAIL; + } + + *BmcStatus =3D IpmiInstance->BmcStatus; + ComAddress->ChannelType =3D SmBmc; + ComAddress->Address.BmcAddress.LunAddress =3D 0x0; + ComAddress->Address.BmcAddress.SlaveAddress =3D IpmiInstance->SlaveAddre= ss; + ComAddress->Address.BmcAddress.ChannelAddress =3D 0x0; + + return EFI_SUCCESS; +} diff --git a/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/= Common/IpmiBmc.h b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Generi= cIpmi/Common/IpmiBmc.h new file mode 100644 index 0000000000..d306a085e5 --- /dev/null +++ b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/Common/= IpmiBmc.h @@ -0,0 +1,44 @@ +/** @file + IPMI Transport common layer driver head file + + @copyright + Copyright 1999 - 2021 Intel Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent +**/ + +#ifndef _IPMI_BMC_H_ +#define _IPMI_BMC_H_ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "IpmiBmcCommon.h" +#include "KcsBmc.h" + + +#define BMC_KCS_TIMEOUT 5 // [s] Single KSC request timeout + +// +// IPMI Instance signature +// +#define SM_IPMI_BMC_SIGNATURE SIGNATURE_32 ('i', 'p', 'm', 'i') +#define IPMI_SEND_COMMAND_MAX_RETRY 3 // Number of retries +#define INSTANCE_FROM_SM_IPMI_BMC_THIS(a) \ + CR ( \ + a, \ + IPMI_BMC_INSTANCE_DATA, \ + IpmiTransport, \ + SM_IPMI_BMC_SIGNATURE \ + ) + +#endif // _IPMI_BMC_H_ diff --git a/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/= Common/IpmiBmcCommon.h b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/= GenericIpmi/Common/IpmiBmcCommon.h new file mode 100644 index 0000000000..1e5dfd81f1 --- /dev/null +++ b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/Common/= IpmiBmcCommon.h @@ -0,0 +1,179 @@ +/** @file + IPMI Transport common layer driver common head file + + @copyright + Copyright 1999 - 2021 Intel Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent +**/ + +#ifndef _IPMI_COMMON_BMC_H_ +#define _IPMI_COMMON_BMC_H_ + +#define MAX_TEMP_DATA 255 // 160 Modified to increase number of bytes = transfered per command +#define BMC_SLAVE_ADDRESS 0x20 +#define MAX_SOFT_COUNT 10 +#define COMP_CODE_NORMAL 0x00 + +// +// IPMI command completion codes to check for in the UpdateErrorStatus rou= tine. +// These completion codes indicate a soft error and a running total of the= occurrences +// of these errors is maintained. +// +#define COMP_CODE_NODE_BUSY 0xC0 +#define COMP_CODE_TIMEOUT 0xC3 +#define COMP_CODE_OUT_OF_SPACE 0xC4 +#define COMP_CODE_OUT_OF_RANGE 0xC9 +#define COMP_CODE_CMD_RESP_NOT_PROVIDED 0xCE +#define COMP_CODE_FAIL_DUP_REQUEST 0xCF +#define COMP_CODE_SDR_REP_IN_UPDATE_MODE 0xD0 +#define COMP_CODE_DEV_IN_FW_UPDATE_MODE 0xD1 +#define COMP_CODE_BMC_INIT_IN_PROGRESS 0xD2 +// +// Intel Server System Integrated Baseboard Management Controller (BMC) Fi= rmware v0.62 +// D4h C Insufficient privilege, in KCS channel this indicates KCS Policy = Control Mode is Deny All. +// In authenticated channels this indicates invalid authentication/privile= ge. +// +#define COMP_INSUFFICIENT_PRIVILEGE 0xD4 +#define COMP_CODE_UNSPECIFIED 0xFF + +#define COMPLETION_CODES \ + { \ + COMP_CODE_NODE_BUSY, COMP_CODE_TIMEOUT, COMP_CODE_OUT_OF_SPACE, COMP_C= ODE_OUT_OF_RANGE, \ + COMP_CODE_CMD_RESP_NOT_PROVIDED, COMP_CODE_FAIL_DUP_REQUEST, COMP_CODE= _SDR_REP_IN_UPDATE_MODE, \ + COMP_CODE_DEV_IN_FW_UPDATE_MODE, COMP_CODE_BMC_INIT_IN_PROGRESS, COMP_= INSUFFICIENT_PRIVILEGE, COMP_CODE_UNSPECIFIED \ + } + +// +// Dxe Ipmi instance data +// +typedef struct { + UINTN Signature; + UINT64 KcsTimeoutPeriod; + UINT8 SlaveAddress; + UINT8 TempData[MAX_TEMP_DATA]; + BMC_STATUS BmcStatus; + UINT64 ErrorStatus; + UINT8 SoftErrorCount; + UINT16 IpmiIoBase; + IPMI_TRANSPORT IpmiTransport; + EFI_HANDLE IpmiSmmHandle; +} IPMI_BMC_INSTANCE_DATA; + +// +// Structure of IPMI Command buffer +// +#define IPMI_COMMAND_HEADER_SIZE 2 + +typedef struct { + UINT8 Lun : 2; + UINT8 NetFunction : 6; + UINT8 Command; + UINT8 CommandData[MAX_TEMP_DATA - IPMI_COMMAND_HEADER_SIZE]; +} IPMI_COMMAND; + +// +// Structure of IPMI Command response buffer +// +#define IPMI_RESPONSE_HEADER_SIZE 3 + +typedef struct { + UINT8 Lun : 2; + UINT8 NetFunction : 6; + UINT8 Command; + UINT8 CompletionCode; + UINT8 ResponseData[MAX_TEMP_DATA - IPMI_RESPONSE_HEADER_SIZE]; +} IPMI_RESPONSE; + +EFI_STATUS +EFIAPI +IpmiSendCommandToBmc ( + IN IPMI_TRANSPORT *This, + IN UINT8 NetFunction, + IN UINT8 Lun, + IN UINT8 Command, + IN UINT8 *CommandData, + IN UINT8 CommandDataSize, + IN OUT UINT8 *ResponseData, + IN OUT UINT8 *ResponseDataSize, + IN VOID *Context + ) +/*++ + +Routine Description: + + Send IPMI command to BMC + +Arguments: + + This - Pointer to IPMI protocol instance + NetFunction - Net Function of command to send + Lun - LUN of command to send + Command - IPMI command to send + CommandData - Pointer to command data buffer, if needed + CommandDataSize - Size of command data buffer + ResponseData - Pointer to response data buffer + ResponseDataSize - Pointer to response data buffer size + Context - Context + +Returns: + + EFI_INVALID_PARAMETER - One of the input values is bad + EFI_DEVICE_ERROR - IPMI command failed + EFI_BUFFER_TOO_SMALL - Response buffer is too small + EFI_SUCCESS - Command completed successfully + +--*/ +; + + +EFI_STATUS +EFIAPI +IpmiBmcStatus ( + IN IPMI_TRANSPORT *This, + OUT BMC_STATUS *BmcStatus, + OUT SM_COM_ADDRESS *ComAddress, + IN VOID *Context + ) +/*++ + +Routine Description: + + Updates the BMC status and returns the Com Address + +Arguments: + + This - Pointer to IPMI protocol instance + BmcStatus - BMC status + ComAddress - Com Address + Context - Context + +Returns: + + EFI_SUCCESS - Success + +--*/ +; + +VOID +GetDeviceSpecificTestResults ( + IN IPMI_BMC_INSTANCE_DATA *IpmiInstance + ) +/*++ + +Routine Description: + + This is a BMC specific routine to check the device specific self test re= sults as defined + in the Bensley BMC core specification. + +Arguments: + + IpmiInstance - Data structure describing BMC variables and used for sen= ding commands + +Returns: + + VOID + +--*/ +; + +#endif diff --git a/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/= Common/IpmiHooks.c b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gene= ricIpmi/Common/IpmiHooks.c new file mode 100644 index 0000000000..86ff7c0fdf --- /dev/null +++ b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/Common/= IpmiHooks.c @@ -0,0 +1,96 @@ +/** @file + IPMI common hook functions + + @copyright + Copyright 2014 - 2021 Intel Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent +**/ + +#include "IpmiHooks.h" + +EFI_STATUS +IpmiSendCommand ( + IN IPMI_TRANSPORT *This, + IN UINT8 NetFunction, + IN UINT8 Lun, + IN UINT8 Command, + IN UINT8 *CommandData, + IN UINT32 CommandDataSize, + IN OUT UINT8 *ResponseData, + IN OUT UINT32 *ResponseDataSize + ) +/*++ + +Routine Description: + + Send Ipmi Command in the right mode: HECI or KCS, to the + appropiate device, ME or BMC. + +Arguments: + + This - Pointer to IPMI protocol instance + NetFunction - Net Function of command to send + Lun - LUN of command to send + Command - IPMI command to send + CommandData - Pointer to command data buffer, if needed + CommandDataSize - Size of command data buffer + ResponseData - Pointer to response data buffer + ResponseDataSize - Pointer to response data buffer size + +Returns: + + EFI_INVALID_PARAMETER - One of the input values is bad + EFI_DEVICE_ERROR - IPMI command failed + EFI_BUFFER_TOO_SMALL - Response buffer is too small + EFI_UNSUPPORTED - Command is not supported by BMC + EFI_SUCCESS - Command completed successfully + +--*/ +{ + // + // This Will be unchanged ( BMC/KCS style ) + // + return IpmiSendCommandToBmc ( + This, + NetFunction, + Lun, + Command, + CommandData, + (UINT8) CommandDataSize, + ResponseData, + (UINT8*) ResponseDataSize, + NULL + ); +} // IpmiSendCommand() + +EFI_STATUS +IpmiGetBmcStatus ( + IN IPMI_TRANSPORT *This, + OUT BMC_STATUS *BmcStatus, + OUT SM_COM_ADDRESS *ComAddress + ) +/*++ + +Routine Description: + + Updates the BMC status and returns the Com Address + +Arguments: + + This - Pointer to IPMI protocol instance + BmcStatus - BMC status + ComAddress - Com Address + +Returns: + + EFI_SUCCESS - Success + +--*/ +{ + return IpmiBmcStatus ( + This, + BmcStatus, + ComAddress, + NULL + ); +} diff --git a/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/= Common/IpmiHooks.h b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Gene= ricIpmi/Common/IpmiHooks.h new file mode 100644 index 0000000000..083c9e70b0 --- /dev/null +++ b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/Common/= IpmiHooks.h @@ -0,0 +1,81 @@ +/** @file + IPMI common hook functions head file + + @copyright + Copyright 2014 - 2021 Intel Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent +**/ + +#ifndef _IPMI_HOOKS_H +#define _IPMI_HOOKS_H + +#include "IpmiBmc.h" + +// +// Internal(hook) function list +// +EFI_STATUS +IpmiSendCommand ( + IN IPMI_TRANSPORT *This, + IN UINT8 NetFunction, + IN UINT8 Lun, + IN UINT8 Command, + IN UINT8 *CommandData, + IN UINT32 CommandDataSize, + IN OUT UINT8 *ResponseData, + IN OUT UINT32 *ResponseDataSize + ) +/*++ + +Routine Description: + + Send IPMI command to BMC + +Arguments: + + This - Pointer to IPMI protocol instance + NetFunction - Net Function of command to send + Lun - LUN of command to send + Command - IPMI command to send + CommandData - Pointer to command data buffer, if needed + CommandDataSize - Size of command data buffer + ResponseData - Pointer to response data buffer + ResponseDataSize - Pointer to response data buffer size + +Returns: + + EFI_INVALID_PARAMETER - One of the input values is bad + EFI_DEVICE_ERROR - IPMI command failed + EFI_BUFFER_TOO_SMALL - Response buffer is too small + EFI_UNSUPPORTED - Command is not supported by BMC + EFI_SUCCESS - Command completed successfully + +--*/ +; + +EFI_STATUS +IpmiGetBmcStatus ( + IN IPMI_TRANSPORT *This, + OUT BMC_STATUS *BmcStatus, + OUT SM_COM_ADDRESS *ComAddress + ) +/*++ + +Routine Description: + + Updates the BMC status and returns the Com Address + +Arguments: + + This - Pointer to IPMI protocol instance + BmcStatus - BMC status + ComAddress - Com Address + +Returns: + + EFI_SUCCESS - Success + +--*/ +; + +#endif diff --git a/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/= Common/IpmiPhysicalLayer.h b/Features/Intel/OutOfBandManagement/IpmiFeature= Pkg/GenericIpmi/Common/IpmiPhysicalLayer.h new file mode 100644 index 0000000000..0215bd0e5a --- /dev/null +++ b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/Common/= IpmiPhysicalLayer.h @@ -0,0 +1,29 @@ +/** @file + IPMI Common physical layer functions. + + @copyright + Copyright 2014 - 2021 Intel Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent +**/ + +#ifndef _IPMI_PHYSICAL_LAYER_H +#define _IPMI_PHYSICAL_LAYER_H + +// +// KCS physical interface layer +// +EFI_STATUS +InitializeIpmiKcsPhysicalLayer ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ); + + +EFI_STATUS +SmmInitializeIpmiKcsPhysicalLayer ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ); + +#endif + diff --git a/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/= Common/KcsBmc.c b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Generic= Ipmi/Common/KcsBmc.c new file mode 100644 index 0000000000..7243d37cc5 --- /dev/null +++ b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/Common/= KcsBmc.c @@ -0,0 +1,483 @@ +/** @file + KCS Transport Hook. + + @copyright + Copyright 1999 - 2021 Intel Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent +**/ + +#include "KcsBmc.h" + +EFI_STATUS +KcsErrorExit ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context + ) +/*++ + +Routine Description: + + Check the KCS error status + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + KcsPort - The base port of KCS + Context - The Context for this operation + +Returns: + + EFI_DEVICE_ERROR - The device error happened + EFI_SUCCESS - Successfully check the KCS error status + +--*/ +{ + EFI_STATUS Status; + UINT8 KcsData; + KCS_STATUS KcsStatus; + UINT8 BmcStatus; + UINT8 RetryCount; + UINT64 TimeOut; + + TimeOut =3D 0; + RetryCount =3D 0; + while (RetryCount < KCS_ABORT_RETRY_COUNT) { + + TimeOut =3D 0; + do { + MicroSecondDelay (KCS_DELAY_UNIT); + KcsStatus.RawData =3D IoRead8 (KcsPort + 1); + if (KcsStatus.RawData =3D=3D 0xFF || (TimeOut >=3D KcsTimeoutPeriod)= ) { + RetryCount =3D KCS_ABORT_RETRY_COUNT; + break; + } + TimeOut++; + } while (KcsStatus.Status.Ibf); + + if (RetryCount >=3D KCS_ABORT_RETRY_COUNT) { + break; + } + + KcsData =3D KCS_ABORT; + IoWrite8 ((KcsPort + 1), KcsData); + + TimeOut =3D 0; + do { + MicroSecondDelay (KCS_DELAY_UNIT); + KcsStatus.RawData =3D IoRead8 (KcsPort + 1); + if (KcsStatus.RawData =3D=3D 0xFF || (TimeOut >=3D KcsTimeoutPeriod)= ) { + Status =3D EFI_DEVICE_ERROR; + goto LabelError; + } + TimeOut++; + } while (KcsStatus.Status.Ibf); + + KcsData =3D IoRead8 (KcsPort); + + KcsData =3D 0x0; + IoWrite8 (KcsPort, KcsData); + + TimeOut =3D 0; + do { + MicroSecondDelay (KCS_DELAY_UNIT); + KcsStatus.RawData =3D IoRead8 (KcsPort + 1); + if (KcsStatus.RawData =3D=3D 0xFF || (TimeOut >=3D KcsTimeoutPeriod)= ) { + Status =3D EFI_DEVICE_ERROR; + goto LabelError; + } + TimeOut++; + } while (KcsStatus.Status.Ibf); + + if (KcsStatus.Status.State =3D=3D KcsReadState) { + TimeOut =3D 0; + do { + MicroSecondDelay (KCS_DELAY_UNIT); + KcsStatus.RawData =3D IoRead8 (KcsPort + 1); + if (KcsStatus.RawData =3D=3D 0xFF || (TimeOut >=3D KcsTimeoutPerio= d)) { + Status =3D EFI_DEVICE_ERROR; + goto LabelError; + } + TimeOut++; + } while (!KcsStatus.Status.Obf); + + BmcStatus =3D IoRead8 (KcsPort); + + KcsData =3D KCS_READ; + IoWrite8 (KcsPort, KcsData); + + TimeOut =3D 0; + do { + MicroSecondDelay (KCS_DELAY_UNIT); + KcsStatus.RawData =3D IoRead8 (KcsPort + 1); + if (KcsStatus.RawData =3D=3D 0xFF || (TimeOut >=3D KcsTimeoutPerio= d)) { + Status =3D EFI_DEVICE_ERROR; + goto LabelError; + } + TimeOut++; + } while (KcsStatus.Status.Ibf); + + if (KcsStatus.Status.State =3D=3D KcsIdleState) { + TimeOut =3D 0; + do { + MicroSecondDelay (KCS_DELAY_UNIT); + KcsStatus.RawData =3D IoRead8 (KcsPort + 1); + if (KcsStatus.RawData =3D=3D 0xFF || (TimeOut >=3D KcsTimeoutPer= iod)) { + Status =3D EFI_DEVICE_ERROR; + goto LabelError; + } + TimeOut++; + } while (!KcsStatus.Status.Obf); + + KcsData =3D IoRead8 (KcsPort); + break; + + } else { + RetryCount++; + continue; + } + + } else { + RetryCount++; + continue; + } + } + + if (RetryCount >=3D KCS_ABORT_RETRY_COUNT) { + Status =3D EFI_DEVICE_ERROR; + goto LabelError; + } + + return EFI_SUCCESS; + +LabelError: + return Status; +} + +EFI_STATUS +KcsCheckStatus ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + KCS_STATE KcsState, + BOOLEAN *Idle, + VOID *Context + ) +/*++ + +Routine Description: + + Ckeck KCS status + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + KcsPort - The base port of KCS + KcsState - The state of KCS to be checked + Idle - If the KCS is idle + Context - The context for this operation + +Returns: + + EFI_SUCCESS - Checked the KCS status successfully + +--*/ +{ + EFI_STATUS Status; + KCS_STATUS KcsStatus; + UINT8 KcsData; + UINT64 TimeOut; + + if (Idle =3D=3D NULL) { + return EFI_INVALID_PARAMETER; + } + + *Idle =3D FALSE; + + TimeOut =3D 0; + do { + MicroSecondDelay (KCS_DELAY_UNIT); + KcsStatus.RawData =3D IoRead8 (KcsPort + 1); + if (KcsStatus.RawData =3D=3D 0xFF || (TimeOut >=3D KcsTimeoutPeriod)) { + Status =3D EFI_DEVICE_ERROR; + goto LabelError; + } + TimeOut++; + } while (KcsStatus.Status.Ibf); + + if (KcsState =3D=3D KcsWriteState) { + KcsData =3D IoRead8 (KcsPort); + } + + if (KcsStatus.Status.State !=3D KcsState) { + if ((KcsStatus.Status.State =3D=3D KcsIdleState) && (KcsState =3D=3D K= csReadState)) { + *Idle =3D TRUE; + } else { + Status =3D KcsErrorExit (KcsTimeoutPeriod, KcsPort, Context); + goto LabelError; + } + } + + if (KcsState =3D=3D KcsReadState) { + TimeOut =3D 0; + do { + MicroSecondDelay (KCS_DELAY_UNIT); + KcsStatus.RawData =3D IoRead8 (KcsPort + 1); + if (KcsStatus.RawData =3D=3D 0xFF || (TimeOut >=3D KcsTimeoutPeriod)= ) { + Status =3D EFI_DEVICE_ERROR; + goto LabelError; + } + TimeOut++; + } while (!KcsStatus.Status.Obf); + } + + if (KcsState =3D=3D KcsWriteState || (*Idle =3D=3D TRUE)) { + KcsData =3D IoRead8 (KcsPort); + } + + return EFI_SUCCESS; + +LabelError: + return Status; +} + +EFI_STATUS +SendDataToBmc ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context, + UINT8 *Data, + UINT8 DataSize + ) +/*++ + +Routine Description: + + Send data to BMC + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + Context - The context of this operation + Data - The data pointer to be sent + DataSize - The data size + +Returns: + + EFI_SUCCESS - Send out the data successfully + +--*/ +{ + KCS_STATUS KcsStatus; + UINT8 KcsData; + UINT16 KcsIoBase; + EFI_STATUS Status; + UINT8 i; + BOOLEAN Idle; + UINT64 TimeOut; + + KcsIoBase =3D KcsPort; + + TimeOut =3D 0; + + do { + MicroSecondDelay (KCS_DELAY_UNIT); + KcsStatus.RawData =3D IoRead8 (KcsIoBase + 1); + if ((KcsStatus.RawData =3D=3D 0xFF) || (TimeOut >=3D KcsTimeoutPeriod)= ) { + if ((Status =3D KcsErrorExit (KcsTimeoutPeriod, KcsIoBase, Context))= !=3D EFI_SUCCESS) { + return Status; + } + } + TimeOut++; + } while (KcsStatus.Status.Ibf); + + KcsData =3D KCS_WRITE_START; + IoWrite8 ((KcsIoBase + 1), KcsData); + if ((Status =3D KcsCheckStatus (KcsTimeoutPeriod, KcsIoBase, KcsWriteSta= te, &Idle, Context)) !=3D EFI_SUCCESS) { + return Status; + } + + for (i =3D 0; i < DataSize; i++) { + if (i =3D=3D (DataSize - 1)) { + if ((Status =3D KcsCheckStatus (KcsTimeoutPeriod, KcsIoBase, KcsWrit= eState, &Idle, Context)) !=3D EFI_SUCCESS) { + return Status; + } + + KcsData =3D KCS_WRITE_END; + IoWrite8 ((KcsIoBase + 1), KcsData); + } + + Status =3D KcsCheckStatus (KcsTimeoutPeriod, KcsIoBase, KcsWriteState,= &Idle, Context); + if (EFI_ERROR (Status)) { + return Status; + } + + IoWrite8 (KcsIoBase, Data[i]); + } + + return EFI_SUCCESS; +} + +EFI_STATUS +ReceiveBmcData ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context, + UINT8 *Data, + UINT8 *DataSize + ) +/*++ + +Routine Description: + + Routine Description: + + Receive data from BMC + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + Context - The context of this operation + Data - The buffer pointer + DataSize - The buffer size + +Returns: + + EFI_SUCCESS - Received data successfully + +--*/ +{ + UINT8 KcsData; + UINT16 KcsIoBase; + EFI_STATUS Status; + BOOLEAN Idle; + UINT8 Count; + + Count =3D 0; + KcsIoBase =3D KcsPort; + + while (TRUE) { + + if ((Status =3D KcsCheckStatus (KcsTimeoutPeriod, KcsIoBase, KcsReadSt= ate, &Idle, Context)) !=3D EFI_SUCCESS) { + return Status; + } + + if (Idle) { + *DataSize =3D Count; + break; + } + + // + //Need to check Data Size -1 to account for array access + // + if (Count >=3D *DataSize) { + return EFI_DEVICE_ERROR; + } + + Data[Count] =3D IoRead8 (KcsIoBase); + + Count++; + + KcsData =3D KCS_READ; + IoWrite8 (KcsIoBase, KcsData); + } + + return EFI_SUCCESS; +} + +EFI_STATUS +ReceiveBmcDataFromPort ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context, + UINT8 *Data, + UINT8 *DataSize + ) +/*++ + +Routine Description: + + Receive data from BMC + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + Context - The context of this operation + Data - The buffer pointer to receive data + DataSize - The buffer size + +Returns: + + EFI_SUCCESS - Received the data successfully + +--*/ +{ + EFI_STATUS Status; + UINT16 KcsIoBase; + UINT8 i; + UINT8 MyDataSize; + + MyDataSize =3D *DataSize; + KcsIoBase =3D KcsPort; + + for (i =3D 0; i < KCS_ABORT_RETRY_COUNT; i++) { + Status =3D ReceiveBmcData (KcsTimeoutPeriod, KcsIoBase, Context, Data,= DataSize); + if (EFI_ERROR (Status)) { + if ((Status =3D KcsErrorExit (KcsTimeoutPeriod, KcsIoBase, Context))= !=3D EFI_SUCCESS) { + return Status; + } + + *DataSize =3D MyDataSize; + } else { + return Status; + } + } + + return EFI_DEVICE_ERROR; +} + +EFI_STATUS +SendDataToBmcPort ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context, + UINT8 *Data, + UINT8 DataSize + ) +/*++ + +Routine Description: + + Send data to BMC + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + Context - The context of this operation + Data - The data pointer to be sent + DataSize - The data size + +Returns: + + EFI_SUCCESS - Send out the data successfully + +--*/ +{ + EFI_STATUS Status; + UINT16 KcsIoBase; + UINT8 i; + + KcsIoBase =3D KcsPort; + + for (i =3D 0; i < KCS_ABORT_RETRY_COUNT; i++) { + Status =3D SendDataToBmc (KcsTimeoutPeriod, KcsIoBase, Context, Data, = DataSize); + if (EFI_ERROR (Status)) { + if ((Status =3D KcsErrorExit (KcsTimeoutPeriod, KcsIoBase, Context))= !=3D EFI_SUCCESS) { + return Status; + } + } else { + return Status; + } + } + + return EFI_DEVICE_ERROR; +} diff --git a/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/= Common/KcsBmc.h b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/Generic= Ipmi/Common/KcsBmc.h new file mode 100644 index 0000000000..a8684cc4f6 --- /dev/null +++ b/Features/Intel/OutOfBandManagement/IpmiFeaturePkg/GenericIpmi/Common/= KcsBmc.h @@ -0,0 +1,236 @@ +/** @file + KCS Transport Hook head file. + + @copyright + Copyright 1999 - 2021 Intel Corporation.
+ SPDX-License-Identifier: BSD-2-Clause-Patent +**/ + +#ifndef _KCS_BMC_H +#define _KCS_BMC_H + +#include +#include +#include +#include + +#define KCS_WRITE_START 0x61 +#define KCS_WRITE_END 0x62 +#define KCS_READ 0x68 +#define KCS_GET_STATUS 0x60 +#define KCS_ABORT 0x60 +#define KCS_DELAY_UNIT 50 // [s] Each KSC IO delay + +// +// In OpenBMC, UpdateMode: the bit 7 of byte 4 in get device id command is= used for the BMC status: +// 0 means BMC is ready, 1 means BMC is not ready. +// At the very beginning of BMC power on, the status is 1 means BMC is in = booting process and not ready. It is not the flag for force update mode. +// +#define BMC_READY 0 + + +#define KCS_ABORT_RETRY_COUNT 1 + +//#define TIMEOUT64(a,b) ((INT64)((b) - (a)) < 0) + +typedef enum { + KcsIdleState, + KcsReadState, + KcsWriteState, + KcsErrorState +} KCS_STATE; + +typedef union { + UINT8 RawData; + struct { + UINT8 Obf : 1; + UINT8 Ibf : 1; + UINT8 SmAtn : 1; + UINT8 CD : 1; + UINT8 Oem1 : 1; + UINT8 Oem2 : 1; + UINT8 State : 2; + } Status; +} KCS_STATUS; + + +// +//External Fucntion List +// +EFI_STATUS +SendDataToBmcPort ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context, + UINT8 *Data, + UINT8 DataSize + ) +/*++ + +Routine Description: + + Send data to BMC + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + Context - The context of this operation + Data - The data pointer to be sent + DataSize - The data size + +Returns: + + EFI_SUCCESS - Send out the data successfully + +--*/ +; + +EFI_STATUS +ReceiveBmcDataFromPort ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context, + UINT8 *Data, + UINT8 *DataSize + ) +/*++ + +Routine Description: + + Routine Description: + + Receive data from BMC + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + Context - The context of this operation + Data - The buffer pointer + DataSize - The buffer size + +Returns: + + EFI_SUCCESS - Received data successfully + +--*/ +; + +// +//Internal Fucntion List +// +EFI_STATUS +KcsErrorExit ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context + ) +/*++ + +Routine Description: + + Check the KCS error status + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + KcsPort - The base port of KCS + Context - The Context for this operation + +Returns: + + EFI_DEVICE_ERROR - The device error happened + EFI_SUCCESS - Successfully check the KCS error status + +--*/ +; + +EFI_STATUS +KcsCheckStatus ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + KCS_STATE KcsState, + BOOLEAN *Idle, + VOID *Context + ) +/*++ + +Routine Description: + + Ckeck KCS status + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + KcsPort - The base port of KCS + KcsState - The state of KCS to be checked + Idle - If the KCS is idle + Context - The context for this operation + +Returns: + + EFI_SUCCESS - Checked the KCS status successfully + +--*/ +; + + +EFI_STATUS +SendDataToBmc ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context, + UINT8 *Data, + UINT8 DataSize + ) +/*++ + +Routine Description: + + Send data to BMC + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + Context - The context of this operation + Data - The data pointer to be sent + DataSize - The data size + +Returns: + + EFI_SUCCESS - Send out the data successfully + +--*/ +; + + +EFI_STATUS +ReceiveBmcData ( + UINT64 KcsTimeoutPeriod, + UINT16 KcsPort, + VOID *Context, + UINT8 *Data, + UINT8 *DataSize + ) +/*++ + +Routine Description: + + Routine Description: + + Receive data from BMC + +Arguments: + + IpmiInstance - The pointer of IPMI_BMC_INSTANCE_DATA + Context - The context of this operation + Data - The buffer pointer + DataSize - The buffer size + +Returns: + + EFI_SUCCESS - Received data successfully + +--*/ +; + +#endif --=20 2.27.0.windows.1 -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#72314): https://edk2.groups.io/g/devel/message/72314 Mute This Topic: https://groups.io/mt/81016656/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-=3D-