summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMark Kettenis <kettenis@cvs.openbsd.org>2021-01-23 12:10:09 +0000
committerMark Kettenis <kettenis@cvs.openbsd.org>2021-01-23 12:10:09 +0000
commit510654c0ebd38535b730b1fa4bf738daa3101e6a (patch)
tree4d528ada5dcf148fbdda55fd91ea8c38c104535b
parent63391001a741154e73ae4f055cf6fbe6041019d7 (diff)
OPAL implements firmware calls that abstract communicating with the BMC over
IPMI. Use these calls to add support for impi(4) on PowerNV systems. ok dlg@
-rw-r--r--sys/arch/powerpc64/conf/GENERIC3
-rw-r--r--sys/arch/powerpc64/conf/files.powerpc645
-rw-r--r--sys/arch/powerpc64/dev/ipmi_opal.c173
-rw-r--r--sys/arch/powerpc64/dev/opal.c7
-rw-r--r--sys/arch/powerpc64/include/opal.h19
-rw-r--r--sys/arch/powerpc64/include/smbiosvar.h278
-rw-r--r--sys/arch/powerpc64/powerpc64/locore.S4
-rw-r--r--sys/dev/ipmi.c6
-rw-r--r--sys/dev/ipmivar.h5
9 files changed, 489 insertions, 11 deletions
diff --git a/sys/arch/powerpc64/conf/GENERIC b/sys/arch/powerpc64/conf/GENERIC
index 75e26260d84..cba5f59f2cf 100644
--- a/sys/arch/powerpc64/conf/GENERIC
+++ b/sys/arch/powerpc64/conf/GENERIC
@@ -1,4 +1,4 @@
-# $OpenBSD: GENERIC,v 1.23 2021/01/23 05:08:36 thfr Exp $
+# $OpenBSD: GENERIC,v 1.24 2021/01/23 12:10:08 kettenis Exp $
#
# For further information on compiling OpenBSD kernels, see the config(8)
# man page.
@@ -21,6 +21,7 @@ config bsd swap generic
mainbus0 at root
cpu0 at mainbus?
+ipmi0 at fdt?
opal0 at fdt?
opalcons* at fdt?
opalsens* at fdt?
diff --git a/sys/arch/powerpc64/conf/files.powerpc64 b/sys/arch/powerpc64/conf/files.powerpc64
index 9f4fb64fbef..d4bc2b3e349 100644
--- a/sys/arch/powerpc64/conf/files.powerpc64
+++ b/sys/arch/powerpc64/conf/files.powerpc64
@@ -1,4 +1,4 @@
-# $OpenBSD: files.powerpc64,v 1.25 2020/10/26 21:13:56 kettenis Exp $
+# $OpenBSD: files.powerpc64,v 1.26 2021/01/23 12:10:08 kettenis Exp $
maxpartitions 16
maxusers 2 8 128
@@ -86,6 +86,9 @@ device opalsens
attach opalsens at fdt
file arch/powerpc64/dev/opalsens.c opalsens
+attach ipmi at fdt with ipmi_opal
+file arch/powerpc64/dev/ipmi_opal.c ipmi_opal
+
device phb: pcibus
attach phb at fdt
file arch/powerpc64/dev/phb.c phb
diff --git a/sys/arch/powerpc64/dev/ipmi_opal.c b/sys/arch/powerpc64/dev/ipmi_opal.c
new file mode 100644
index 00000000000..3532a90add9
--- /dev/null
+++ b/sys/arch/powerpc64/dev/ipmi_opal.c
@@ -0,0 +1,173 @@
+/* $OpenBSD: ipmi_opal.c,v 1.1 2021/01/23 12:10:08 kettenis Exp $ */
+/*
+ * Copyright (c) 2020 Mark Kettenis <kettenis@openbsd.org>
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <sys/param.h>
+#include <sys/device.h>
+#include <sys/systm.h>
+
+#include <machine/fdt.h>
+#include <machine/opal.h>
+
+#include <dev/ofw/openfirm.h>
+#include <dev/ofw/fdt.h>
+
+#include <dev/ipmivar.h>
+
+struct ipmi_opal_softc {
+ struct ipmi_softc sc;
+ int sc_id;
+};
+
+void ipmi_opal_buildmsg(struct ipmi_cmd *);
+int ipmi_opal_sendmsg(struct ipmi_cmd *);
+int ipmi_opal_recvmsg(struct ipmi_cmd *);
+int ipmi_opal_reset(struct ipmi_softc *);
+int ipmi_opal_probe(struct ipmi_softc *);
+
+#define IPMI_OPALMSG_VERSION 0
+#define IPMI_OPALMSG_NFLN 1
+#define IPMI_OPALMSG_CMD 2
+#define IPMI_OPALMSG_CCODE 3
+#define IPMI_OPALMSG_DATASND 3
+#define IPMI_OPALMSG_DATARCV 4
+
+struct ipmi_if opal_if = {
+ "OPAL",
+ 0,
+ ipmi_opal_buildmsg,
+ ipmi_opal_sendmsg,
+ ipmi_opal_recvmsg,
+ ipmi_opal_reset,
+ ipmi_opal_probe,
+ IPMI_OPALMSG_DATASND,
+ IPMI_OPALMSG_DATARCV
+};
+
+int ipmi_opal_match(struct device *, void *, void *);
+void ipmi_opal_attach(struct device *, struct device *, void *);
+
+struct cfattach ipmi_opal_ca = {
+ sizeof (struct ipmi_opal_softc), ipmi_opal_match, ipmi_opal_attach
+};
+
+int
+ipmi_opal_match(struct device *parent, void *match, void *aux)
+{
+ struct fdt_attach_args *faa = aux;
+
+ return OF_is_compatible(faa->fa_node, "ibm,opal-ipmi");
+}
+
+void
+ipmi_opal_attach(struct device *parent, struct device *self, void *aux)
+{
+ struct ipmi_opal_softc *sc = (struct ipmi_opal_softc *)self;
+ struct fdt_attach_args *faa = aux;
+ struct ipmi_attach_args iaa;
+ uint64_t size;
+ int64_t error;
+
+ sc->sc.sc_if = &opal_if;
+ sc->sc_id = OF_getpropint(faa->fa_node, "ibm,ipmi-interface-id", 0);
+
+ /* Clear IPMI message queue. */
+ do {
+ size = sizeof(sc->sc.sc_buf);
+ error = opal_ipmi_recv(sc->sc_id,
+ opal_phys(sc->sc.sc_buf), opal_phys(&size));
+ } while (error == OPAL_SUCCESS);
+
+ memset(&iaa, 0, sizeof(iaa));
+ iaa.iaa_if_type = IPMI_IF_SSIF;
+ iaa.iaa_if_rev = 0x20;
+ iaa.iaa_if_irq = -1;
+ ipmi_attach_common(&sc->sc, &iaa);
+}
+
+#define RSSA_MASK 0xff
+#define LUN_MASK 0x3
+#define NETFN_LUN(nf,ln) (((nf) << 2) | ((ln) & LUN_MASK))
+
+void
+ipmi_opal_buildmsg(struct ipmi_cmd *c)
+{
+ struct ipmi_softc *sc = c->c_sc;
+ struct opal_ipmi_msg *msg = (struct opal_ipmi_msg *)sc->sc_buf;
+
+ msg->version = OPAL_IPMI_MSG_FORMAT_VERSION_1;
+ msg->netfn = NETFN_LUN(c->c_netfn, c->c_rslun);;
+ msg->cmd = c->c_cmd;
+ if (c->c_txlen && c->c_data)
+ memcpy(msg->data, c->c_data, c->c_txlen);
+}
+
+int
+ipmi_opal_sendmsg(struct ipmi_cmd *c)
+{
+ struct ipmi_opal_softc *sc = (struct ipmi_opal_softc *)c->c_sc;
+ int64_t error;
+
+ error = opal_ipmi_send(sc->sc_id,
+ opal_phys(sc->sc.sc_buf), c->c_txlen);
+
+ return (error == OPAL_SUCCESS ? 0 : -1);
+}
+
+int
+ipmi_opal_recvmsg(struct ipmi_cmd *c)
+{
+ struct ipmi_opal_softc *sc = (struct ipmi_opal_softc *)c->c_sc;
+ struct opal_ipmi_msg *msg = (struct opal_ipmi_msg *)sc->sc.sc_buf;
+ uint64_t size = sizeof(sc->sc.sc_buf);
+ int64_t error;
+ int timo;
+
+ msg->version = OPAL_IPMI_MSG_FORMAT_VERSION_1;
+ for (timo = 1000; timo > 0; timo--) {
+ error = opal_ipmi_recv(sc->sc_id,
+ opal_phys(sc->sc.sc_buf), opal_phys(&size));
+ if (error != OPAL_EMPTY)
+ break;
+
+ tsleep_nsec(sc, PWAIT, "ipmi", MSEC_TO_NSEC(1));
+ opal_poll_events(NULL);
+ }
+
+ if (error == OPAL_SUCCESS) {
+ if (msg->version != OPAL_IPMI_MSG_FORMAT_VERSION_1)
+ return -1;
+
+ sc->sc.sc_buf[IPMI_MSG_NFLN] = msg->netfn;
+ sc->sc.sc_buf[IPMI_MSG_CMD] = msg->cmd;
+ sc->sc.sc_buf[IPMI_MSG_CCODE] = msg->data[0];
+ c->c_rxlen = MIN(size, c->c_maxrxlen);
+ }
+
+ return (error == OPAL_SUCCESS ? 0 : -1);
+}
+
+int
+ipmi_opal_reset(struct ipmi_softc *sc)
+{
+ return -1;
+}
+
+int
+ipmi_opal_probe(struct ipmi_softc *sc)
+{
+ return 0;
+}
diff --git a/sys/arch/powerpc64/dev/opal.c b/sys/arch/powerpc64/dev/opal.c
index 096412b778f..78c636407c8 100644
--- a/sys/arch/powerpc64/dev/opal.c
+++ b/sys/arch/powerpc64/dev/opal.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: opal.c,v 1.11 2020/12/30 06:06:30 gkoehler Exp $ */
+/* $OpenBSD: opal.c,v 1.12 2021/01/23 12:10:08 kettenis Exp $ */
/*
* Copyright (c) 2020 Mark Kettenis <kettenis@openbsd.org>
*
@@ -165,6 +165,11 @@ opal_attach(struct device *parent, struct device *self, void *aux)
for (node = OF_child(node); node; node = OF_peer(node))
opal_attach_node(sc, node);
}
+
+ for (node = OF_child(faa->fa_node); node; node = OF_peer(node)) {
+ if (OF_is_compatible(node, "ibm,opal-ipmi"))
+ opal_attach_node(sc, node);
+ }
}
int
diff --git a/sys/arch/powerpc64/include/opal.h b/sys/arch/powerpc64/include/opal.h
index b94e5f0a94b..fc375727537 100644
--- a/sys/arch/powerpc64/include/opal.h
+++ b/sys/arch/powerpc64/include/opal.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: opal.h,v 1.18 2020/10/19 18:54:58 kettenis Exp $ */
+/* $OpenBSD: opal.h,v 1.19 2021/01/23 12:10:08 kettenis Exp $ */
/*
* Copyright (c) 2020 Mark Kettenis <kettenis@openbsd.org>
@@ -49,6 +49,8 @@
#define OPAL_REINIT_CPUS 70
#define OPAL_CHECK_TOKEN 80
#define OPAL_SENSOR_READ 88
+#define OPAL_IPMI_SEND 107
+#define OPAL_IPMI_RECV 108
#define OPAL_CONSOLE_FLUSH 117
#define OPAL_XIVE_RESET 128
#define OPAL_XIVE_GET_IRQ_INFO 129
@@ -78,6 +80,7 @@
#define OPAL_HARDWARE_FROZEN -13
#define OPAL_WRONG_STATE -14
#define OPAL_ASYNC_COMPLETION -15
+#define OPAL_EMPTY -16
/* OPAL_POLL_EVENT */
#define OPAL_EVENT_CONSOLE_OUTPUT 0x00000008
@@ -126,6 +129,18 @@
#define OPAL_TOKEN_ABSENT 0
#define OPAL_TOKEN_PRESENT 1
+/* OPAL_IPMI_SEND/RECV */
+#define OPAL_IPMI_MSG_FORMAT_VERSION_1 1
+
+#ifndef _LOCORE
+struct opal_ipmi_msg {
+ uint8_t version;
+ uint8_t netfn;
+ uint8_t cmd;
+ uint8_t data[0];
+};
+#endif
+
/* OPAL_XIVE_RESET */
#define OPAL_XIVE_MODE_EMU 0
#define OPAL_XIVE_MODE_EXPL 1
@@ -196,6 +211,8 @@ int64_t opal_pci_reset(uint64_t, uint8_t, uint8_t);
int64_t opal_reinit_cpus(uint64_t);
int64_t opal_check_token(uint64_t);
int64_t opal_sensor_read(uint32_t, int, uint32_t *);
+int64_t opal_ipmi_send(uint64_t, struct opal_ipmi_msg *, uint64_t);
+int64_t opal_ipmi_recv(uint64_t, struct opal_ipmi_msg *, uint64_t *);
int64_t opal_console_flush(uint64_t);
int64_t opal_xive_reset(uint64_t);
int64_t opal_xive_get_irq_info(uint32_t, uint64_t *, uint64_t *,
diff --git a/sys/arch/powerpc64/include/smbiosvar.h b/sys/arch/powerpc64/include/smbiosvar.h
new file mode 100644
index 00000000000..7876cebc831
--- /dev/null
+++ b/sys/arch/powerpc64/include/smbiosvar.h
@@ -0,0 +1,278 @@
+/* $OpenBSD: smbiosvar.h,v 1.1 2021/01/23 12:10:08 kettenis Exp $ */
+/*
+ * Copyright (c) 2006 Gordon Willem Klok <gklok@cogeco.ca>
+ * Copyright (c) 2005 Jordan Hargrave
+ * 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 AUTHORS 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 AUTHORS 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 _MACHINE_SMBIOSVAR_
+#define _MACHINE_SMBIOSVAR_
+
+#define SMBIOS_UUID_NPRESENT 0x1
+#define SMBIOS_UUID_NSET 0x2
+
+/*
+ * Section 3.5 of "UUIDs and GUIDs" found at
+ * http://www.opengroup.org/dce/info/draft-leach-uuids-guids-01.txt
+ * specifies the string repersentation of a UUID.
+ */
+#define SMBIOS_UUID_REP "%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x"
+#define SMBIOS_UUID_REPLEN 37 /* 16 zero padded values, 4 hyphens, 1 null */
+
+struct smbios_entry {
+ uint8_t mjr;
+ uint8_t min;
+ uint8_t *addr;
+ uint16_t len;
+ uint16_t count;
+};
+
+struct smbhdr {
+ uint32_t sig; /* "_SM_" */
+ uint8_t checksum; /* Entry point checksum */
+ uint8_t len; /* Entry point structure length */
+ uint8_t majrev; /* Specification major revision */
+ uint8_t minrev; /* Specification minor revision */
+ uint16_t mss; /* Maximum Structure Size */
+ uint8_t epr; /* Entry Point Revision */
+ uint8_t fa[5]; /* value determined by EPR */
+ uint8_t sasig[5]; /* Secondary Anchor "_DMI_" */
+ uint8_t sachecksum; /* Secondary Checksum */
+ uint16_t size; /* Length of structure table in bytes */
+ uint32_t addr; /* Structure table address */
+ uint16_t count; /* Number of SMBIOS structures */
+ uint8_t rev; /* BCD revision */
+} __packed;
+
+struct smb3hdr {
+ uint8_t sig[5]; /* "_SM3_" */
+ uint8_t checksum; /* Entry point structure checksum */
+ uint8_t len; /* Entry point length */
+ uint8_t majrev; /* SMBIOS major version */
+ uint8_t minrev; /* SMBIOS minor version */
+ uint8_t docrev; /* SMBIOS docrev */
+ uint8_t epr; /* Entry point revision */
+ uint8_t reserved; /* Reserved */
+ uint32_t size; /* Structure table maximum size */
+ uint64_t addr; /* Structure table address */
+} __packed;
+
+struct smbtblhdr {
+ uint8_t type;
+ uint8_t size;
+ uint16_t handle;
+} __packed;
+
+struct smbtable {
+ struct smbtblhdr *hdr;
+ void *tblhdr;
+ uint32_t cookie;
+};
+
+#define SMBIOS_TYPE_BIOS 0
+#define SMBIOS_TYPE_SYSTEM 1
+#define SMBIOS_TYPE_BASEBOARD 2
+#define SMBIOS_TYPE_ENCLOSURE 3
+#define SMBIOS_TYPE_PROCESSOR 4
+#define SMBIOS_TYPE_MEMCTRL 5
+#define SMBIOS_TYPE_MEMMOD 6
+#define SMBIOS_TYPE_CACHE 7
+#define SMBIOS_TYPE_PORT 8
+#define SMBIOS_TYPE_SLOTS 9
+#define SMBIOS_TYPE_OBD 10
+#define SMBIOS_TYPE_OEM 11
+#define SMBIOS_TYPE_SYSCONFOPT 12
+#define SMBIOS_TYPE_BIOSLANG 13
+#define SMBIOS_TYPE_GROUPASSOC 14
+#define SMBIOS_TYPE_SYSEVENTLOG 15
+#define SMBIOS_TYPE_PHYMEM 16
+#define SMBIOS_TYPE_MEMDEV 17
+#define SMBIOS_TYPE_ECCINFO32 18
+#define SMBIOS_TYPE_MEMMAPARRAYADDR 19
+#define SMBIOS_TYPE_MEMMAPDEVADDR 20
+#define SMBIOS_TYPE_INBUILTPOINT 21
+#define SMBIOS_TYPE_PORTBATT 22
+#define SMBIOS_TYPE_SYSRESET 23
+#define SMBIOS_TYPE_HWSECUIRTY 24
+#define SMBIOS_TYPE_PWRCTRL 25
+#define SMBIOS_TYPE_VOLTPROBE 26
+#define SMBIOS_TYPE_COOLING 27
+#define SMBIOS_TYPE_TEMPPROBE 28
+#define SMBIOS_TYPE_CURRENTPROBE 29
+#define SMBIOS_TYPE_OOB_REMOTEACCESS 30
+#define SMBIOS_TYPE_BIS 31
+#define SMBIOS_TYPE_SBI 32
+#define SMBIOS_TYPE_ECCINFO64 33
+#define SMBIOS_TYPE_MGMTDEV 34
+#define SMBIOS_TYPE_MGTDEVCOMP 35
+#define SMBIOS_TYPE_MGTDEVTHRESH 36
+#define SMBIOS_TYPE_MEMCHANNEL 37
+#define SMBIOS_TYPE_IPMIDEV 38
+#define SMBIOS_TYPE_SPS 39
+#define SMBIOS_TYPE_INACTIVE 126
+#define SMBIOS_TYPE_EOT 127
+
+/*
+ * SMBIOS Structure Type 0 "BIOS Information"
+ * DMTF Specification DSP0134 Section: 3.3.1 p.g. 34
+ */
+struct smbios_struct_bios {
+ uint8_t vendor; /* string */
+ uint8_t version; /* string */
+ uint16_t startaddr;
+ uint8_t release; /* string */
+ uint8_t romsize;
+ uint64_t characteristics;
+ uint32_t charext;
+ uint8_t major_rel;
+ uint8_t minor_rel;
+ uint8_t ecf_mjr_rel; /* embedded controller firmware */
+ uint8_t ecf_min_rel; /* embedded controller firmware */
+} __packed;
+
+/*
+ * SMBIOS Structure Type 1 "System Information"
+ * DMTF Specification DSP0134 Section 3.3.2 p.g. 35
+ */
+
+struct smbios_sys {
+/* SMBIOS spec 2.0+ */
+ uint8_t vendor; /* string */
+ uint8_t product; /* string */
+ uint8_t version; /* string */
+ uint8_t serial; /* string */
+/* SMBIOS spec 2.1+ */
+ uint8_t uuid[16];
+ uint8_t wakeup;
+/* SMBIOS spec 2.4+ */
+ uint8_t sku; /* string */
+ uint8_t family; /* string */
+} __packed;
+
+/*
+ * SMBIOS Structure Type 2 "Base Board (Module) Information"
+ * DMTF Specification DSP0134 Section 3.3.3 p.g. 37
+ */
+struct smbios_board {
+ uint8_t vendor; /* string */
+ uint8_t product; /* string */
+ uint8_t version; /* string */
+ uint8_t serial; /* string */
+ uint8_t asset; /* string */
+ uint8_t feature; /* feature flags */
+ uint8_t location; /* location in chassis */
+ uint16_t handle; /* chassis handle */
+ uint8_t type; /* board type */
+ uint8_t noc; /* number of contained objects */
+} __packed;
+
+/*
+ * SMBIOS Structure Type 3 "System Wnclosure or Chassis"
+ * DMTF Specification DSP0134
+ */
+struct smbios_enclosure {
+ /* SMBIOS spec 2.0+ */
+ uint8_t vendor; /* string */
+ uint8_t type;
+ uint8_t version; /* string */
+ uint8_t serial; /* string */
+ uint8_t asset_tag; /* string */
+ /* SMBIOS spec 2.1+ */
+ uint8_t boot_state;
+ uint8_t psu_state;
+ uint8_t thermal_state;
+ uint8_t security_status;
+ /* SMBIOS spec 2.3+ */
+ uint16_t oem_defined;
+ uint8_t height;
+ uint8_t no_power_cords;
+ uint8_t no_contained_element;
+ uint8_t reclen_contained_element;
+ uint8_t contained_elements;
+ /* SMBIOS spec 2.7+ */
+ uint8_t sku; /* string */
+} __packed;
+
+/*
+ * SMBIOS Structure Type 4 "processor Information"
+ * DMTF Specification DSP0134 v2.5 Section 3.3.5 p.g. 24
+ */
+struct smbios_cpu {
+ uint8_t cpu_socket_designation; /* string */
+ uint8_t cpu_type;
+ uint8_t cpu_family;
+ uint8_t cpu_mfg; /* string */
+ uint32_t cpu_id_eax;
+ uint32_t cpu_id_edx;
+ uint8_t cpu_version; /* string */
+ uint8_t cpu_voltage;
+ uint16_t cpu_clock;
+ uint16_t cpu_max_speed;
+ uint16_t cpu_current_speed;
+ uint8_t cpu_status;
+#define SMBIOS_CPUST_POPULATED (1<<6)
+#define SMBIOS_CPUST_STATUSMASK (0x07)
+ uint8_t cpu_upgrade;
+ uint16_t cpu_l1_handle;
+ uint16_t cpu_l2_handle;
+ uint16_t cpu_l3_handle;
+ uint8_t cpu_serial; /* string */
+ uint8_t cpu_asset_tag; /* string */
+ uint8_t cpu_part_nr; /* string */
+ /* following fields were added in smbios 2.5 */
+ uint8_t cpu_core_count;
+ uint8_t cpu_core_enabled;
+ uint8_t cpu_thread_count;
+ uint16_t cpu_characteristics;
+} __packed;
+
+/*
+ * SMBIOS Structure Type 38 "IPMI Information"
+ * DMTF Specification DSP0134 Section 3.3.39 p.g. 91
+ */
+struct smbios_ipmi {
+ uint8_t smipmi_if_type; /* IPMI Interface Type */
+ uint8_t smipmi_if_rev; /* BCD IPMI Revision */
+ uint8_t smipmi_i2c_address; /* I2C address of BMC */
+ uint8_t smipmi_nvram_address; /* I2C address of NVRAM
+ * storage */
+ uint64_t smipmi_base_address; /* Base address of BMC (BAR
+ * format */
+ uint8_t smipmi_base_flags; /* Flags field:
+ * bit 7:6 : register spacing
+ * 00 = byte
+ * 01 = dword
+ * 02 = word
+ * bit 4 : Lower bit BAR
+ * bit 3 : IRQ valid
+ * bit 2 : N/A
+ * bit 1 : Interrupt polarity
+ * bit 0 : Interrupt trigger */
+ uint8_t smipmi_irq; /* IRQ if applicable */
+} __packed;
+
+int smbios_find_table(uint8_t, struct smbtable *);
+char *smbios_get_string(struct smbtable *, uint8_t, char *, size_t);
+
+#endif
diff --git a/sys/arch/powerpc64/powerpc64/locore.S b/sys/arch/powerpc64/powerpc64/locore.S
index 5d83bb28000..10a5cd16707 100644
--- a/sys/arch/powerpc64/powerpc64/locore.S
+++ b/sys/arch/powerpc64/powerpc64/locore.S
@@ -1,4 +1,4 @@
-/* $OpenBSD: locore.S,v 1.42 2020/12/30 06:06:30 gkoehler Exp $ */
+/* $OpenBSD: locore.S,v 1.43 2021/01/23 12:10:08 kettenis Exp $ */
/*
* Copyright (c) 2020 Mark Kettenis <kettenis@openbsd.org>
@@ -440,6 +440,8 @@ OPAL_CALL(OPAL_PCI_RESET, opal_pci_reset)
OPAL_CALL(OPAL_REINIT_CPUS, opal_reinit_cpus)
OPAL_CALL(OPAL_CHECK_TOKEN, opal_check_token)
OPAL_CALL(OPAL_SENSOR_READ, opal_sensor_read)
+OPAL_CALL(OPAL_IPMI_SEND, opal_ipmi_send)
+OPAL_CALL(OPAL_IPMI_RECV, opal_ipmi_recv)
OPAL_CALL(OPAL_CONSOLE_FLUSH, opal_console_flush)
OPAL_CALL(OPAL_XIVE_RESET, opal_xive_reset)
OPAL_CALL(OPAL_XIVE_GET_IRQ_INFO, opal_xive_get_irq_info)
diff --git a/sys/dev/ipmi.c b/sys/dev/ipmi.c
index cb99a063deb..5ea5b45aed2 100644
--- a/sys/dev/ipmi.c
+++ b/sys/dev/ipmi.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ipmi.c,v 1.114 2020/12/11 19:48:58 cheloha Exp $ */
+/* $OpenBSD: ipmi.c,v 1.115 2021/01/23 12:10:08 kettenis Exp $ */
/*
* Copyright (c) 2015 Masao Uebayashi
@@ -67,10 +67,6 @@ int ipmi_enabled = 0;
#define IPMI_BTMSG_DATASND 4
#define IPMI_BTMSG_DATARCV 5
-#define IPMI_MSG_NFLN 0
-#define IPMI_MSG_CMD 1
-#define IPMI_MSG_CCODE 2
-
#define IPMI_SENSOR_TYPE_TEMP 0x0101
#define IPMI_SENSOR_TYPE_VOLT 0x0102
#define IPMI_SENSOR_TYPE_FAN 0x0104
diff --git a/sys/dev/ipmivar.h b/sys/dev/ipmivar.h
index 1bed74a5a6d..60a57073f0d 100644
--- a/sys/dev/ipmivar.h
+++ b/sys/dev/ipmivar.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: ipmivar.h,v 1.33 2020/03/29 09:31:10 kettenis Exp $ */
+/* $OpenBSD: ipmivar.h,v 1.34 2021/01/23 12:10:08 kettenis Exp $ */
/*
* Copyright (c) 2005 Jordan Hargrave
@@ -175,6 +175,9 @@ int ipmi_activate(struct device *, int);
int ipmi_sendcmd(struct ipmi_cmd *);
int ipmi_recvcmd(struct ipmi_cmd *);
+#define IPMI_MSG_NFLN 0
+#define IPMI_MSG_CMD 1
+#define IPMI_MSG_CCODE 2
#define IPMI_MSG_DATASND 2
#define IPMI_MSG_DATARCV 3