summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSergii Dmytruk <sergii.dmytruk@3mdeb.com>2021-10-22 01:02:32 +0300
committerMartin Roth <martin.roth@amd.corp-partner.google.com>2022-10-02 22:01:50 +0000
commitef7dd5d54df9137b8167e86838270a7c812b21f3 (patch)
tree7f21c3e30b189c6cfa1e00380f302f269d9f6ca6
parent36d7f82d98ff9127f38c2517d03b90107514bf33 (diff)
downloadcoreboot-ef7dd5d54df9137b8167e86838270a7c812b21f3.tar.gz
coreboot-ef7dd5d54df9137b8167e86838270a7c812b21f3.tar.bz2
coreboot-ef7dd5d54df9137b8167e86838270a7c812b21f3.zip
drivers/ipmi: prepare for adding more interfaces
De-duplicate common initialization code (self-test and device identification) and put it in a new ipmi_if.c unit, which is supposed to work with any underlying IPMI interface. Change-Id: Ia99da6fb63adb7bf556d3d6f7964b34831be8a2f Signed-off-by: Sergii Dmytruk <sergii.dmytruk@3mdeb.com> Reviewed-on: https://review.coreboot.org/c/coreboot/+/67056 Tested-by: build bot (Jenkins) <no-reply@coreboot.org> Reviewed-by: Krystian Hebel <krystian.hebel@3mdeb.com>
-rw-r--r--Documentation/drivers/ipmi_kcs.md9
-rw-r--r--src/drivers/ipmi/Makefile.inc4
-rw-r--r--src/drivers/ipmi/chip.h5
-rw-r--r--src/drivers/ipmi/ipmi_fru.c3
-rw-r--r--src/drivers/ipmi/ipmi_if.c101
-rw-r--r--src/drivers/ipmi/ipmi_if.h (renamed from src/drivers/ipmi/ipmi_kcs.h)41
-rw-r--r--src/drivers/ipmi/ipmi_kcs.c8
-rw-r--r--src/drivers/ipmi/ipmi_kcs_ops.c78
-rw-r--r--src/drivers/ipmi/ipmi_kcs_ops_premem.c113
-rw-r--r--src/drivers/ipmi/ipmi_ops.c13
-rw-r--r--src/drivers/ipmi/ipmi_ops.h2
-rw-r--r--src/drivers/ipmi/ipmi_ops_premem.c53
-rw-r--r--src/drivers/ipmi/ocp/ipmi_ocp.c7
-rw-r--r--src/drivers/ipmi/ocp/ipmi_ocp_romstage.c24
-rw-r--r--src/drivers/ipmi/supermicro_oem.c14
-rw-r--r--src/mainboard/ocp/deltalake/ipmi.c6
-rw-r--r--src/mainboard/ocp/deltalake/romstage.c4
-rw-r--r--src/mainboard/ocp/tiogapass/ipmi.c2
-rw-r--r--src/mainboard/ocp/tiogapass/romstage.c4
19 files changed, 245 insertions, 246 deletions
diff --git a/Documentation/drivers/ipmi_kcs.md b/Documentation/drivers/ipmi_kcs.md
index f6f0fb986a62..c4db492e0085 100644
--- a/Documentation/drivers/ipmi_kcs.md
+++ b/Documentation/drivers/ipmi_kcs.md
@@ -42,6 +42,15 @@ The following registers can be set:
* `gpe_interrupt`
* Integer
* The bit in GPE (SCI) used to notify about a change on the KCS.
+* `wait_for_bmc`
+ * Boolean
+ * Wait for BMC to boot. This can be used if the BMC takes a long time to boot
+ after PoR:
+ - AST2400 on Supermicro X11SSH: 34 s
+* `bmc_boot_timeout`
+ * Integer
+ * The timeout in seconds to wait for the IPMI service to be loaded.
+ Will be used if wait_for_bmc is true.
[IPMI]: https://www.intel.com/content/dam/www/public/us/en/documents/product-briefs/ipmi-second-gen-interface-spec-v2-rev1-1.pdf
diff --git a/src/drivers/ipmi/Makefile.inc b/src/drivers/ipmi/Makefile.inc
index e4bcf313ebca..85f3dde43746 100644
--- a/src/drivers/ipmi/Makefile.inc
+++ b/src/drivers/ipmi/Makefile.inc
@@ -1,8 +1,10 @@
+ramstage-$(CONFIG_IPMI_KCS) += ipmi_if.c
ramstage-$(CONFIG_IPMI_KCS) += ipmi_kcs.c
ramstage-$(CONFIG_IPMI_KCS) += ipmi_kcs_ops.c
ramstage-$(CONFIG_IPMI_KCS) += ipmi_ops.c
ramstage-$(CONFIG_IPMI_KCS) += ipmi_fru.c
ramstage-$(CONFIG_DRIVERS_IPMI_SUPERMICRO_OEM) += supermicro_oem.c
-romstage-$(CONFIG_IPMI_KCS_ROMSTAGE) += ipmi_kcs_ops_premem.c
+romstage-$(CONFIG_IPMI_KCS_ROMSTAGE) += ipmi_if.c
+romstage-$(CONFIG_IPMI_KCS_ROMSTAGE) += ipmi_ops_premem.c
romstage-$(CONFIG_IPMI_KCS_ROMSTAGE) += ipmi_kcs.c
romstage-$(CONFIG_IPMI_KCS_ROMSTAGE) += ipmi_ops.c
diff --git a/src/drivers/ipmi/chip.h b/src/drivers/ipmi/chip.h
index 4e9d9e1985b9..3b970c9fa409 100644
--- a/src/drivers/ipmi/chip.h
+++ b/src/drivers/ipmi/chip.h
@@ -8,6 +8,7 @@
#include <stdint.h>
struct drivers_ipmi_config {
+#if CONFIG(IPMI_KCS)
u8 bmc_i2c_address;
u8 have_nv_storage;
u8 nv_storage_device_address;
@@ -25,6 +26,9 @@ struct drivers_ipmi_config {
/* "POST complete" GPIO and polarity */
u32 post_complete_gpio;
bool post_complete_invert;
+ unsigned int uid; /* Auto-filled by ipmi_ssdt() */
+#endif
+
/*
* Wait for BMC to boot.
* This can be used if the BMC takes a long time to boot after PoR:
@@ -36,7 +40,6 @@ struct drivers_ipmi_config {
* Will be used if wait_for_bmc is true.
*/
u16 bmc_boot_timeout;
- unsigned int uid; /* Auto-filled by ipmi_ssdt() */
};
#endif /* _IMPI_CHIP_H_ */
diff --git a/src/drivers/ipmi/ipmi_fru.c b/src/drivers/ipmi/ipmi_fru.c
index 822e5bfa23c4..f16530705fe7 100644
--- a/src/drivers/ipmi/ipmi_fru.c
+++ b/src/drivers/ipmi/ipmi_fru.c
@@ -5,6 +5,7 @@
#include <delay.h>
#include <stdlib.h>
+#include "ipmi_if.h"
#include "ipmi_ops.h"
#define MAX_FRU_BUSY_RETRY 5
@@ -34,7 +35,7 @@ static enum cb_err ipmi_read_fru(const int port, struct ipmi_read_fru_data_req *
req->count = CONFIG_IPMI_FRU_SINGLE_RW_SZ;
while (retry_count <= MAX_FRU_BUSY_RETRY) {
- ret = ipmi_kcs_message(port, IPMI_NETFN_STORAGE, 0x0,
+ ret = ipmi_message(port, IPMI_NETFN_STORAGE, 0x0,
IPMI_READ_FRU_DATA, (const unsigned char *) req,
sizeof(*req), (unsigned char *) &rsp, sizeof(rsp));
if (rsp.resp.completion_code == 0x81) {
diff --git a/src/drivers/ipmi/ipmi_if.c b/src/drivers/ipmi/ipmi_if.c
new file mode 100644
index 000000000000..4ff900474175
--- /dev/null
+++ b/src/drivers/ipmi/ipmi_if.c
@@ -0,0 +1,101 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+
+#include "ipmi_if.h"
+
+#include <console/console.h>
+#include <delay.h>
+
+#include "chip.h"
+
+int ipmi_get_device_id(const struct device *dev, struct ipmi_devid_rsp *rsp)
+{
+ int ret;
+
+ ret = ipmi_message(dev->path.pnp.port, IPMI_NETFN_APPLICATION, 0,
+ IPMI_BMC_GET_DEVICE_ID, NULL, 0, (u8 *)rsp,
+ sizeof(*rsp));
+ if (ret < sizeof(struct ipmi_rsp) || rsp->resp.completion_code) {
+ printk(BIOS_ERR, "IPMI: %s command failed (ret=%d resp=0x%x)\n",
+ __func__, ret, rsp->resp.completion_code);
+ return 1;
+ }
+ if (ret != sizeof(*rsp)) {
+ printk(BIOS_ERR, "IPMI: %s response truncated\n", __func__);
+ return 1;
+ }
+ return 0;
+}
+
+static int ipmi_get_bmc_self_test_result(const struct device *dev,
+ struct ipmi_selftest_rsp *rsp)
+{
+ int ret;
+
+ ret = ipmi_message(dev->path.pnp.port, IPMI_NETFN_APPLICATION, 0,
+ IPMI_BMC_GET_SELFTEST_RESULTS, NULL, 0, (u8 *)rsp,
+ sizeof(*rsp));
+
+ if (ret < sizeof(struct ipmi_rsp) || rsp->resp.completion_code) {
+ printk(BIOS_ERR, "IPMI: %s command failed (ret=%d resp=0x%x)\n",
+ __func__, ret, rsp->resp.completion_code);
+ return 1;
+ }
+ if (ret != sizeof(*rsp)) {
+ printk(BIOS_ERR, "IPMI: %s response truncated\n", __func__);
+ return 1;
+ }
+
+ return 0;
+}
+
+int ipmi_process_self_test_result(const struct device *dev)
+{
+ int failure = 0;
+ uint8_t retry_count = 0;
+ struct ipmi_selftest_rsp selftestrsp = {0};
+
+ const struct drivers_ipmi_config *conf = dev->chip_info;
+ uint8_t retry_limit = 0;
+
+ if (conf && conf->wait_for_bmc)
+ retry_limit = conf->bmc_boot_timeout;
+
+ if (retry_limit == 0)
+ /* Try to get self-test results at least once */
+ retry_limit = 1;
+
+ printk(BIOS_INFO, "Get BMC self test result...");
+ for (retry_count = 0; retry_count < retry_limit; retry_count++) {
+ if (!ipmi_get_bmc_self_test_result(dev, &selftestrsp))
+ break;
+
+ mdelay(1000);
+ }
+
+ switch (selftestrsp.result) {
+ case IPMI_APP_SELFTEST_NO_ERROR: /* 0x55 */
+ printk(BIOS_DEBUG, "No Error\n");
+ break;
+ case IPMI_APP_SELFTEST_NOT_IMPLEMENTED: /* 0x56 */
+ printk(BIOS_DEBUG, "Function Not Implemented\n");
+ break;
+ case IPMI_APP_SELFTEST_ERROR: /* 0x57 */
+ printk(BIOS_ERR, "BMC: Corrupted or inaccessible data or device\n");
+ failure = 1;
+ break;
+ case IPMI_APP_SELFTEST_FATAL_HW_ERROR: /* 0x58 */
+ printk(BIOS_ERR, "BMC: Fatal Hardware Error\n");
+ failure = 1;
+ break;
+ case IPMI_APP_SELFTEST_RESERVED: /* 0xFF */
+ printk(BIOS_DEBUG, "Reserved\n");
+ break;
+
+ default: /* Other Device Specific Hardware Error */
+ printk(BIOS_ERR, "BMC: Device Specific Error: 0x%02x\n", selftestrsp.result);
+ failure = 1;
+ break;
+ }
+
+ return failure;
+}
diff --git a/src/drivers/ipmi/ipmi_kcs.h b/src/drivers/ipmi/ipmi_if.h
index 33ddd5f016ff..984b46953b18 100644
--- a/src/drivers/ipmi/ipmi_kcs.h
+++ b/src/drivers/ipmi/ipmi_if.h
@@ -1,7 +1,11 @@
/* SPDX-License-Identifier: GPL-2.0-only */
-#ifndef __IPMI_KCS_H
-#define __IPMI_KCS_H
+#ifndef __IPMI_IF_H
+#define __IPMI_IF_H
+
+/* Common API and code for different IPMI interfaces in different stages */
+
+#include <stdint.h>
#define IPMI_NETFN_CHASSIS 0x00
#define IPMI_NETFN_BRIDGE 0x02
@@ -25,16 +29,6 @@
#define IPMI_CMD_ACPI_POWERON 0x06
-extern int ipmi_kcs_message(int port, int netfn, int lun, int cmd,
- const unsigned char *inmsg, int inlen,
- unsigned char *outmsg, int outlen);
-
-/* Run basic IPMI init functions in romstage from the provided PnP device,
- * returns CB_SUCCESS on success and CB_ERR if an error occurred. */
-enum cb_err ipmi_kcs_premem_init(const u16 port, const u16 device);
-
-void ipmi_bmc_version(uint8_t *ipmi_bmc_major_revision, uint8_t *ipmi_bmc_minor_revision);
-
struct ipmi_rsp {
uint8_t lun;
uint8_t cmd;
@@ -61,4 +55,25 @@ struct ipmi_selftest_rsp {
uint8_t param;
} __packed;
-#endif
+struct device;
+
+/*
+ * Sends a command and reads its response. Input buffer is for payload, but
+ * output includes `struct ipmi_rsp` as a header. Returns number of bytes copied
+ * into the buffer or -1.
+ */
+int ipmi_message(int port, int netfn, int lun, int cmd,
+ const unsigned char *inmsg, int inlen,
+ unsigned char *outmsg, int outlen);
+
+/* Run basic IPMI init functions in romstage from the provided PnP device,
+ * returns CB_SUCCESS on success and CB_ERR if an error occurred. */
+enum cb_err ipmi_premem_init(const uint16_t port, const uint16_t device);
+
+int ipmi_get_device_id(const struct device *dev, struct ipmi_devid_rsp *rsp);
+
+int ipmi_process_self_test_result(const struct device *dev);
+
+void ipmi_bmc_version(uint8_t *ipmi_bmc_major_revision, uint8_t *ipmi_bmc_minor_revision);
+
+#endif /* __IPMI_IF_H */
diff --git a/src/drivers/ipmi/ipmi_kcs.c b/src/drivers/ipmi/ipmi_kcs.c
index 12cbe82f1413..667827224f5a 100644
--- a/src/drivers/ipmi/ipmi_kcs.c
+++ b/src/drivers/ipmi/ipmi_kcs.c
@@ -4,7 +4,7 @@
#include <device/device.h>
#include <arch/io.h>
#include <timer.h>
-#include "ipmi_kcs.h"
+#include "ipmi_if.h"
#define IPMI_KCS_STATE(_x) ((_x) >> 6)
@@ -219,9 +219,9 @@ static int ipmi_kcs_read_message(int port, unsigned char *msg, int len)
return ret;
}
-int ipmi_kcs_message(int port, int netfn, int lun, int cmd,
- const unsigned char *inmsg, int inlen,
- unsigned char *outmsg, int outlen)
+int ipmi_message(int port, int netfn, int lun, int cmd,
+ const unsigned char *inmsg, int inlen,
+ unsigned char *outmsg, int outlen)
{
if (ipmi_kcs_send_message(port, netfn, lun, cmd, inmsg, inlen)) {
printk(BIOS_ERR, "ipmi_kcs_send_message failed\n");
diff --git a/src/drivers/ipmi/ipmi_kcs_ops.c b/src/drivers/ipmi/ipmi_kcs_ops.c
index 4ffa91fe2319..a2ad7abd8651 100644
--- a/src/drivers/ipmi/ipmi_kcs_ops.c
+++ b/src/drivers/ipmi/ipmi_kcs_ops.c
@@ -24,7 +24,7 @@
#include <version.h>
#include <delay.h>
#include <timer.h>
-#include "ipmi_kcs.h"
+#include "ipmi_if.h"
#include "ipmi_supermicro_oem.h"
#include "chip.h"
@@ -37,46 +37,6 @@ static u8 bmc_revision_minor = 0x0;
static struct boot_state_callback bscb_post_complete;
-static int ipmi_get_device_id(struct device *dev, struct ipmi_devid_rsp *rsp)
-{
- int ret;
-
- ret = ipmi_kcs_message(dev->path.pnp.port, IPMI_NETFN_APPLICATION, 0,
- IPMI_BMC_GET_DEVICE_ID, NULL, 0, (u8 *)rsp,
- sizeof(*rsp));
- if (ret < sizeof(struct ipmi_rsp) || rsp->resp.completion_code) {
- printk(BIOS_ERR, "IPMI: %s command failed (ret=%d resp=0x%x)\n",
- __func__, ret, rsp->resp.completion_code);
- return 1;
- }
- if (ret != sizeof(*rsp)) {
- printk(BIOS_ERR, "IPMI: %s response truncated\n", __func__);
- return 1;
- }
- return 0;
-}
-
-static int ipmi_get_bmc_self_test_result(struct device *dev, struct ipmi_selftest_rsp *rsp)
-{
- int ret;
-
- ret = ipmi_kcs_message(dev->path.pnp.port, IPMI_NETFN_APPLICATION, 0,
- IPMI_BMC_GET_SELFTEST_RESULTS, NULL, 0, (u8 *)rsp,
- sizeof(*rsp));
-
- if (ret < sizeof(struct ipmi_rsp) || rsp->resp.completion_code) {
- printk(BIOS_ERR, "IPMI: %s command failed (ret=%d resp=0x%x)\n",
- __func__, ret, rsp->resp.completion_code);
- return 1;
- }
- if (ret != sizeof(*rsp)) {
- printk(BIOS_ERR, "IPMI: %s response truncated\n", __func__);
- return 1;
- }
-
- return 0;
-}
-
static void bmc_set_post_complete_gpio_callback(void *arg)
{
struct drivers_ipmi_config *conf = arg;
@@ -103,8 +63,6 @@ static void ipmi_kcs_init(struct device *dev)
uint32_t man_id = 0, prod_id = 0;
struct drivers_ipmi_config *conf = dev->chip_info;
const struct gpio_operations *gpio_ops;
- struct ipmi_selftest_rsp selftestrsp = {0};
- uint8_t retry_count;
if (!conf) {
printk(BIOS_WARNING, "IPMI: chip_info is missing! Skip init.\n");
@@ -154,41 +112,9 @@ static void ipmi_kcs_init(struct device *dev)
}
}
- printk(BIOS_INFO, "Get BMC self test result...");
- for (retry_count = 0; retry_count < conf->bmc_boot_timeout; retry_count++) {
- if (!ipmi_get_bmc_self_test_result(dev, &selftestrsp))
- break;
-
- mdelay(1000);
- }
-
- switch (selftestrsp.result) {
- case IPMI_APP_SELFTEST_NO_ERROR: /* 0x55 */
- printk(BIOS_DEBUG, "No Error\n");
- break;
- case IPMI_APP_SELFTEST_NOT_IMPLEMENTED: /* 0x56 */
- printk(BIOS_DEBUG, "Function Not Implemented\n");
- break;
- case IPMI_APP_SELFTEST_ERROR: /* 0x57 */
- printk(BIOS_ERR, "BMC: Corrupted or inaccessible data or device\n");
- /* Don't write tables if communication failed */
- dev->enabled = 0;
- break;
- case IPMI_APP_SELFTEST_FATAL_HW_ERROR: /* 0x58 */
- printk(BIOS_ERR, "BMC: Fatal Hardware Error\n");
- /* Don't write tables if communication failed */
- dev->enabled = 0;
- break;
- case IPMI_APP_SELFTEST_RESERVED: /* 0xFF */
- printk(BIOS_DEBUG, "Reserved\n");
- break;
-
- default: /* Other Device Specific Hardware Error */
- printk(BIOS_ERR, "BMC: Device Specific Error\n");
+ if (ipmi_process_self_test_result(dev))
/* Don't write tables if communication failed */
dev->enabled = 0;
- break;
- }
if (!ipmi_get_device_id(dev, &rsp)) {
/* Queried the IPMI revision from BMC */
diff --git a/src/drivers/ipmi/ipmi_kcs_ops_premem.c b/src/drivers/ipmi/ipmi_kcs_ops_premem.c
deleted file mode 100644
index e1ae0dc3e5b6..000000000000
--- a/src/drivers/ipmi/ipmi_kcs_ops_premem.c
+++ /dev/null
@@ -1,113 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0-only */
-
-#include <arch/io.h>
-#include <console/console.h>
-#include <device/pnp.h>
-#include <delay.h>
-#include <timer.h>
-
-#include "ipmi_kcs.h"
-#include "chip.h"
-
-static int ipmi_get_bmc_self_test_result(const struct device *dev,
- struct ipmi_selftest_rsp *rsp)
-{
- int ret;
-
- ret = ipmi_kcs_message(dev->path.pnp.port, IPMI_NETFN_APPLICATION, 0,
- IPMI_BMC_GET_SELFTEST_RESULTS, NULL, 0, (u8 *)rsp,
- sizeof(*rsp));
-
- if (ret < sizeof(struct ipmi_rsp) || rsp->resp.completion_code) {
- printk(BIOS_ERR, "IPMI: %s command failed (ret=%d resp=0x%x)\n",
- __func__, ret, rsp->resp.completion_code);
- return 1;
- }
- if (ret != sizeof(*rsp)) {
- printk(BIOS_ERR, "IPMI: %s response truncated\n", __func__);
- return 1;
- }
-
- return 0;
-}
-
-enum cb_err ipmi_kcs_premem_init(const u16 port, const u16 device)
-{
- const struct drivers_ipmi_config *conf = NULL;
- struct ipmi_selftest_rsp selftestrsp = {0};
- uint8_t retry_count;
- const struct device *dev;
-
- /* Find IPMI PNP device from devicetree in romstage */
- dev = dev_find_slot_pnp(port, device);
-
- if (!dev) {
- printk(BIOS_ERR, "IPMI: Cannot find PNP device port: %x, device %x\n",
- port, device);
- return CB_ERR;
- }
- if (!dev->enabled) {
- printk(BIOS_ERR, "IPMI: device is not enabled\n");
- return CB_ERR;
- }
- printk(BIOS_DEBUG, "IPMI: romstage PNP KCS 0x%x\n", dev->path.pnp.port);
- if (dev->chip_info)
- conf = dev->chip_info;
-
- if (conf && conf->wait_for_bmc && conf->bmc_boot_timeout) {
- struct stopwatch sw;
- stopwatch_init_msecs_expire(&sw, conf->bmc_boot_timeout * 1000);
- printk(BIOS_DEBUG, "IPMI: Waiting for BMC...\n");
-
- while (!stopwatch_expired(&sw)) {
- if (inb(dev->path.pnp.port) != 0xff)
- break;
- mdelay(100);
- }
- if (stopwatch_expired(&sw)) {
- printk(BIOS_INFO, "IPMI: Waiting for BMC timed out\n");
- return CB_ERR;
- }
- }
-
- printk(BIOS_INFO, "Get BMC self test result...");
- if (conf && conf->bmc_boot_timeout) {
- for (retry_count = 0; retry_count < conf->bmc_boot_timeout; retry_count++) {
- if (!ipmi_get_bmc_self_test_result(dev, &selftestrsp))
- break;
-
- mdelay(1000);
- }
- } else {
- /* At least run once */
- ipmi_get_bmc_self_test_result(dev, &selftestrsp);
- }
-
- int ret = CB_ERR;
- switch (selftestrsp.result) {
- case IPMI_APP_SELFTEST_NO_ERROR: /* 0x55 */
- printk(BIOS_DEBUG, "No Error\n");
- ret = CB_SUCCESS;
- break;
- case IPMI_APP_SELFTEST_NOT_IMPLEMENTED: /* 0x56 */
- printk(BIOS_DEBUG, "Function Not Implemented\n");
- ret = CB_SUCCESS;
- break;
- case IPMI_APP_SELFTEST_ERROR: /* 0x57 */
- printk(BIOS_ERR, "Corrupted or inaccessible data or device\n");
- break;
- case IPMI_APP_SELFTEST_FATAL_HW_ERROR: /* 0x58 */
- printk(BIOS_ERR, "Fatal Hardware Error\n");
- break;
- case IPMI_APP_SELFTEST_RESERVED: /* 0xFF */
- printk(BIOS_DEBUG, "Reserved\n");
- ret = CB_SUCCESS;
- break;
-
- default: /* Other Device Specific Hardware Error */
- printk(BIOS_ERR, "Device Specific Error 0x%x 0x%x\n", selftestrsp.result,
- selftestrsp.param);
- break;
- }
- return ret;
-}
diff --git a/src/drivers/ipmi/ipmi_ops.c b/src/drivers/ipmi/ipmi_ops.c
index 73a02e1f37c3..d9b3256eec34 100644
--- a/src/drivers/ipmi/ipmi_ops.c
+++ b/src/drivers/ipmi/ipmi_ops.c
@@ -2,6 +2,7 @@
#include <console/console.h>
#include "ipmi_ops.h"
+#include "ipmi_if.h"
#include <string.h>
#include <types.h>
@@ -18,7 +19,7 @@ enum cb_err ipmi_init_and_start_bmc_wdt(const int port, uint16_t countdown,
/* clear BIOS FRB2 expiration flag */
req.timer_use_expiration_flags_clr = 2;
req.initial_countdown_val = countdown;
- ret = ipmi_kcs_message(port, IPMI_NETFN_APPLICATION, 0x0,
+ ret = ipmi_message(port, IPMI_NETFN_APPLICATION, 0x0,
IPMI_BMC_SET_WDG_TIMER,
(const unsigned char *) &req, sizeof(req),
(unsigned char *) &rsp, sizeof(rsp));
@@ -32,7 +33,7 @@ enum cb_err ipmi_init_and_start_bmc_wdt(const int port, uint16_t countdown,
}
/* Reset command to start timer */
- ret = ipmi_kcs_message(port, IPMI_NETFN_APPLICATION, 0x0,
+ ret = ipmi_message(port, IPMI_NETFN_APPLICATION, 0x0,
IPMI_BMC_RESET_WDG_TIMER, NULL, 0,
(unsigned char *) &rsp, sizeof(rsp));
@@ -56,7 +57,7 @@ enum cb_err ipmi_stop_bmc_wdt(const int port)
struct ipmi_rsp resp;
/* Get current timer first */
- ret = ipmi_kcs_message(port, IPMI_NETFN_APPLICATION, 0x0,
+ ret = ipmi_message(port, IPMI_NETFN_APPLICATION, 0x0,
IPMI_BMC_GET_WDG_TIMER, NULL, 0,
(unsigned char *) &rsp, sizeof(rsp));
@@ -76,7 +77,7 @@ enum cb_err ipmi_stop_bmc_wdt(const int port)
rsp.data.timer_use &= ~(1 << 6);
rsp.data.initial_countdown_val = 0;
req = rsp.data;
- ret = ipmi_kcs_message(port, IPMI_NETFN_APPLICATION, 0x0,
+ ret = ipmi_message(port, IPMI_NETFN_APPLICATION, 0x0,
IPMI_BMC_SET_WDG_TIMER,
(const unsigned char *) &req, sizeof(req),
(unsigned char *) &resp, sizeof(resp));
@@ -104,7 +105,7 @@ enum cb_err ipmi_get_system_guid(const int port, uint8_t *uuid)
return CB_ERR;
}
- ret = ipmi_kcs_message(port, IPMI_NETFN_APPLICATION, 0x0,
+ ret = ipmi_message(port, IPMI_NETFN_APPLICATION, 0x0,
IPMI_BMC_GET_SYSTEM_GUID, NULL, 0,
(unsigned char *) &rsp, sizeof(rsp));
@@ -128,7 +129,7 @@ enum cb_err ipmi_add_sel(const int port, struct sel_event_record *sel)
return CB_ERR;
}
- ret = ipmi_kcs_message(port, IPMI_NETFN_STORAGE, 0x0,
+ ret = ipmi_message(port, IPMI_NETFN_STORAGE, 0x0,
IPMI_ADD_SEL_ENTRY, (const unsigned char *) sel,
16, (unsigned char *) &rsp, sizeof(rsp));
diff --git a/src/drivers/ipmi/ipmi_ops.h b/src/drivers/ipmi/ipmi_ops.h
index d900272e38af..7a92a28121a8 100644
--- a/src/drivers/ipmi/ipmi_ops.h
+++ b/src/drivers/ipmi/ipmi_ops.h
@@ -4,7 +4,7 @@
#define __IPMI_OPS_H
#include <types.h>
-#include "ipmi_kcs.h"
+#include "ipmi_if.h"
#define IPMI_BMC_RESET_WDG_TIMER 0x22
#define IPMI_BMC_SET_WDG_TIMER 0x24
#define IPMI_BMC_GET_WDG_TIMER 0x25
diff --git a/src/drivers/ipmi/ipmi_ops_premem.c b/src/drivers/ipmi/ipmi_ops_premem.c
new file mode 100644
index 000000000000..99c5842bb3dc
--- /dev/null
+++ b/src/drivers/ipmi/ipmi_ops_premem.c
@@ -0,0 +1,53 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+
+#include <arch/io.h>
+#include <console/console.h>
+#include <device/pnp.h>
+#include <delay.h>
+#include <timer.h>
+
+#include "ipmi_if.h"
+#include "chip.h"
+
+enum cb_err ipmi_premem_init(const u16 port, const u16 device)
+{
+ const struct drivers_ipmi_config *conf = NULL;
+ const struct device *dev;
+
+ /* Find IPMI PNP device from devicetree in romstage */
+ dev = dev_find_slot_pnp(port, device);
+
+ if (!dev) {
+ printk(BIOS_ERR, "IPMI: Cannot find PNP device port: %x, device %x\n",
+ port, device);
+ return CB_ERR;
+ }
+ if (!dev->enabled) {
+ printk(BIOS_ERR, "IPMI: device is not enabled\n");
+ return CB_ERR;
+ }
+ printk(BIOS_DEBUG, "IPMI: romstage PNP KCS 0x%x\n", dev->path.pnp.port);
+ if (dev->chip_info)
+ conf = dev->chip_info;
+
+ if (conf && conf->wait_for_bmc && conf->bmc_boot_timeout) {
+ struct stopwatch sw;
+ stopwatch_init_msecs_expire(&sw, conf->bmc_boot_timeout * 1000);
+ printk(BIOS_DEBUG, "IPMI: Waiting for BMC...\n");
+
+ while (!stopwatch_expired(&sw)) {
+ if (inb(dev->path.pnp.port) != 0xff)
+ break;
+ mdelay(100);
+ }
+ if (stopwatch_expired(&sw)) {
+ printk(BIOS_INFO, "IPMI: Waiting for BMC timed out\n");
+ return CB_ERR;
+ }
+ }
+
+ if (ipmi_process_self_test_result(dev))
+ return CB_ERR;
+
+ return CB_SUCCESS;
+}
diff --git a/src/drivers/ipmi/ocp/ipmi_ocp.c b/src/drivers/ipmi/ocp/ipmi_ocp.c
index 11161a8ae472..9f583be934ea 100644
--- a/src/drivers/ipmi/ocp/ipmi_ocp.c
+++ b/src/drivers/ipmi/ocp/ipmi_ocp.c
@@ -10,7 +10,7 @@
#include <console/console.h>
#include <device/device.h>
#include <device/pnp.h>
-#include <drivers/ipmi/ipmi_kcs.h>
+#include <drivers/ipmi/ipmi_if.h>
#include <drivers/ocp/dmi/ocp_dmi.h>
#include <types.h>
@@ -28,8 +28,9 @@ static enum cb_err ipmi_set_ppin(struct device *dev)
req.cpu1_lo = xeon_sp_ppin[1].lo;
req.cpu1_hi = xeon_sp_ppin[1].hi;
}
- ret = ipmi_kcs_message(dev->path.pnp.port, IPMI_NETFN_OEM, 0x0, IPMI_OEM_SET_PPIN,
- (const unsigned char *) &req, sizeof(req), (unsigned char *) &rsp, sizeof(rsp));
+ ret = ipmi_message(dev->path.pnp.port, IPMI_NETFN_OEM, 0x0, IPMI_OEM_SET_PPIN,
+ (const unsigned char *) &req, sizeof(req),
+ (unsigned char *) &rsp, sizeof(rsp));
if (ret < sizeof(struct ipmi_rsp) || rsp.completion_code) {
printk(BIOS_ERR, "IPMI: %s command failed (ret=%d resp=0x%x)\n",
diff --git a/src/drivers/ipmi/ocp/ipmi_ocp_romstage.c b/src/drivers/ipmi/ocp/ipmi_ocp_romstage.c
index 8e43d8d159e7..7b0b9ea0360f 100644
--- a/src/drivers/ipmi/ocp/ipmi_ocp_romstage.c
+++ b/src/drivers/ipmi/ocp/ipmi_ocp_romstage.c
@@ -1,7 +1,7 @@
/* SPDX-License-Identifier: GPL-2.0-or-later */
#include <console/console.h>
-#include <drivers/ipmi/ipmi_kcs.h>
+#include <drivers/ipmi/ipmi_if.h>
#include "ipmi_ocp.h"
@@ -10,9 +10,9 @@ enum cb_err ipmi_set_post_start(const int port)
int ret;
struct ipmi_rsp rsp;
- ret = ipmi_kcs_message(port, IPMI_NETFN_OEM, 0x0,
- IPMI_BMC_SET_POST_START, NULL, 0, (u8 *) &rsp,
- sizeof(rsp));
+ ret = ipmi_message(port, IPMI_NETFN_OEM, 0x0,
+ IPMI_BMC_SET_POST_START, NULL, 0, (u8 *) &rsp,
+ sizeof(rsp));
if (ret < sizeof(struct ipmi_rsp) || rsp.completion_code) {
printk(BIOS_ERR, "IPMI: %s command failed (ret=%d rsp=0x%x)\n",
@@ -42,10 +42,10 @@ enum cb_err ipmi_set_cmos_clear(void)
/* IPMI OEM get bios boot order command to check if the valid bit and
the CMOS clear bit are both set from the response BootMode byte. */
- ret = ipmi_kcs_message(CONFIG_BMC_KCS_BASE, IPMI_NETFN_OEM, 0x0,
- IPMI_OEM_GET_BIOS_BOOT_ORDER,
- NULL, 0,
- (unsigned char *) &rsp, sizeof(rsp));
+ ret = ipmi_message(CONFIG_BMC_KCS_BASE, IPMI_NETFN_OEM, 0x0,
+ IPMI_OEM_GET_BIOS_BOOT_ORDER,
+ NULL, 0,
+ (unsigned char *) &rsp, sizeof(rsp));
if (ret < sizeof(struct ipmi_rsp) || rsp.resp.completion_code) {
printk(BIOS_ERR, "IPMI: %s command failed (read ret=%d resp=0x%x)\n",
@@ -56,10 +56,10 @@ enum cb_err ipmi_set_cmos_clear(void)
if (!IS_CMOS_AND_VALID_BIT(rsp.data.boot_mode)) {
req = rsp.data;
SET_CMOS_AND_VALID_BIT(req.boot_mode);
- ret = ipmi_kcs_message(CONFIG_BMC_KCS_BASE, IPMI_NETFN_OEM, 0x0,
- IPMI_OEM_SET_BIOS_BOOT_ORDER,
- (const unsigned char *) &req, sizeof(req),
- (unsigned char *) &rsp, sizeof(rsp));
+ ret = ipmi_message(CONFIG_BMC_KCS_BASE, IPMI_NETFN_OEM, 0x0,
+ IPMI_OEM_SET_BIOS_BOOT_ORDER,
+ (const unsigned char *) &req, sizeof(req),
+ (unsigned char *) &rsp, sizeof(rsp));
if (ret < sizeof(struct ipmi_rsp) || rsp.resp.completion_code) {
printk(BIOS_ERR, "IPMI: %s command failed (sent ret=%d resp=0x%x)\n",
diff --git a/src/drivers/ipmi/supermicro_oem.c b/src/drivers/ipmi/supermicro_oem.c
index 9d5ffc77a460..7af4e3b8a475 100644
--- a/src/drivers/ipmi/supermicro_oem.c
+++ b/src/drivers/ipmi/supermicro_oem.c
@@ -3,7 +3,7 @@
#include <types.h>
#include <console/console.h>
-#include <drivers/ipmi/ipmi_kcs.h>
+#include <drivers/ipmi/ipmi_if.h>
#include <string.h>
#include <build.h>
#include "ipmi_supermicro_oem.h"
@@ -35,9 +35,9 @@ static void set_coreboot_ver(const uint16_t kcs_port)
bios_ver.str[i] = 0;
bios_ver.ver = IPMI_LUN0_AC_SET_BIOS_VER;
- ret = ipmi_kcs_message(kcs_port, IPMI_NETFN_OEM, 0, IPMI_LUN0_SET_BIOS_STRING,
- (const unsigned char *) &bios_ver, sizeof(bios_ver),
- (unsigned char *) &rsp, sizeof(rsp));
+ ret = ipmi_message(kcs_port, IPMI_NETFN_OEM, 0, IPMI_LUN0_SET_BIOS_STRING,
+ (const unsigned char *) &bios_ver, sizeof(bios_ver),
+ (unsigned char *) &rsp, sizeof(rsp));
if (ret < sizeof(rsp) || rsp.completion_code) {
printk(BIOS_ERR, "BMC_IPMI: %s command failed (ret=%d resp=0x%x)\n",
__func__, ret, rsp.completion_code);
@@ -54,9 +54,9 @@ static void set_coreboot_date(const uint16_t kcs_port)
bios_ver.str[15] = 0;
bios_ver.ver = IPMI_LUN0_AC_SET_BIOS_DATE;
- ret = ipmi_kcs_message(kcs_port, IPMI_NETFN_OEM, 0, IPMI_LUN0_SET_BIOS_STRING,
- (const unsigned char *) &bios_ver, sizeof(bios_ver),
- (unsigned char *) &rsp, sizeof(rsp));
+ ret = ipmi_message(kcs_port, IPMI_NETFN_OEM, 0, IPMI_LUN0_SET_BIOS_STRING,
+ (const unsigned char *) &bios_ver, sizeof(bios_ver),
+ (unsigned char *) &rsp, sizeof(rsp));
if (ret < sizeof(rsp) || rsp.completion_code) {
printk(BIOS_ERR, "BMC_IPMI: %s command failed (ret=%d resp=0x%x)\n",
__func__, ret, rsp.completion_code);
diff --git a/src/mainboard/ocp/deltalake/ipmi.c b/src/mainboard/ocp/deltalake/ipmi.c
index 25a5a27cba67..d990b87e8068 100644
--- a/src/mainboard/ocp/deltalake/ipmi.c
+++ b/src/mainboard/ocp/deltalake/ipmi.c
@@ -1,7 +1,7 @@
/* SPDX-License-Identifier: GPL-2.0-or-later */
#include <console/console.h>
-#include <drivers/ipmi/ipmi_kcs.h>
+#include <drivers/ipmi/ipmi_if.h>
#include <drivers/ipmi/ipmi_ops.h>
#include <drivers/ipmi/ocp/ipmi_ocp.h>
#include <drivers/vpd/vpd.h>
@@ -18,7 +18,7 @@ enum cb_err ipmi_get_pcie_config(uint8_t *pcie_config)
} __packed;
struct ipmi_config_rsp rsp;
- ret = ipmi_kcs_message(CONFIG_BMC_KCS_BASE, IPMI_NETFN_OEM, 0x0,
+ ret = ipmi_message(CONFIG_BMC_KCS_BASE, IPMI_NETFN_OEM, 0x0,
IPMI_OEM_GET_PCIE_CONFIG, NULL, 0, (unsigned char *) &rsp,
sizeof(rsp));
@@ -44,7 +44,7 @@ enum cb_err ipmi_get_slot_id(uint8_t *slot_id)
} __packed;
struct ipmi_config_rsp rsp;
- ret = ipmi_kcs_message(CONFIG_BMC_KCS_BASE, IPMI_NETFN_OEM, 0x0, IPMI_OEM_GET_BOARD_ID,
+ ret = ipmi_message(CONFIG_BMC_KCS_BASE, IPMI_NETFN_OEM, 0x0, IPMI_OEM_GET_BOARD_ID,
NULL, 0, (unsigned char *) &rsp, sizeof(rsp));
if (ret < sizeof(struct ipmi_rsp) || rsp.resp.completion_code) {
diff --git a/src/mainboard/ocp/deltalake/romstage.c b/src/mainboard/ocp/deltalake/romstage.c
index 05a7188da41e..2efed1ca84da 100644
--- a/src/mainboard/ocp/deltalake/romstage.c
+++ b/src/mainboard/ocp/deltalake/romstage.c
@@ -2,7 +2,7 @@
#include <console/console.h>
#include <console/uart.h>
-#include <drivers/ipmi/ipmi_kcs.h>
+#include <drivers/ipmi/ipmi_if.h>
#include <drivers/ipmi/ocp/ipmi_ocp.h>
#include <drivers/vpd/vpd.h>
#include <fsp/api.h>
@@ -188,7 +188,7 @@ void mainboard_memory_init_params(FSPM_UPD *mupd)
/* Since it's the first IPMI command, it's better to run get BMC
selftest result first */
- if (ipmi_kcs_premem_init(CONFIG_BMC_KCS_BASE, 0) == CB_SUCCESS) {
+ if (ipmi_premem_init(CONFIG_BMC_KCS_BASE, 0) == CB_SUCCESS) {
ipmi_set_post_start(CONFIG_BMC_KCS_BASE);
init_frb2_wdt();
}
diff --git a/src/mainboard/ocp/tiogapass/ipmi.c b/src/mainboard/ocp/tiogapass/ipmi.c
index 74f96fe36c58..e97341b2b678 100644
--- a/src/mainboard/ocp/tiogapass/ipmi.c
+++ b/src/mainboard/ocp/tiogapass/ipmi.c
@@ -1,7 +1,7 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <console/console.h>
-#include <drivers/ipmi/ipmi_kcs.h>
+#include <drivers/ipmi/ipmi_if.h>
#include <drivers/ipmi/ipmi_ops.h>
#include <drivers/ipmi/ocp/ipmi_ocp.h>
#include <drivers/vpd/vpd.h>
diff --git a/src/mainboard/ocp/tiogapass/romstage.c b/src/mainboard/ocp/tiogapass/romstage.c
index 20c74660ced1..842e977d3e1b 100644
--- a/src/mainboard/ocp/tiogapass/romstage.c
+++ b/src/mainboard/ocp/tiogapass/romstage.c
@@ -2,7 +2,7 @@
#include <fsp/api.h>
#include <FspmUpd.h>
-#include <drivers/ipmi/ipmi_kcs.h>
+#include <drivers/ipmi/ipmi_if.h>
#include <drivers/ipmi/ocp/ipmi_ocp.h>
#include <soc/romstage.h>
#include <string.h>
@@ -54,7 +54,7 @@ static void mainboard_config_iio(FSPM_UPD *mupd)
void mainboard_memory_init_params(FSPM_UPD *mupd)
{
/* It's better to run get BMC selftest result first */
- if (ipmi_kcs_premem_init(CONFIG_BMC_KCS_BASE, 0) == CB_SUCCESS) {
+ if (ipmi_premem_init(CONFIG_BMC_KCS_BASE, 0) == CB_SUCCESS) {
ipmi_set_post_start(CONFIG_BMC_KCS_BASE);
init_frb2_wdt();
}