git: a7b187860cb7 - stable/13 - ipmi: support getting address from EFI

From: Eric van Gyzen <vangyzen_at_FreeBSD.org>
Date: Thu, 03 Mar 2022 14:20:41 UTC
The branch stable/13 has been updated by vangyzen:

URL: https://cgit.FreeBSD.org/src/commit/?id=a7b187860cb784fb76bd9142f6ae6c53ec5d7f42

commit a7b187860cb784fb76bd9142f6ae6c53ec5d7f42
Author:     Yinlong Lu <yinlong.lu@dell.com>
AuthorDate: 2021-04-29 10:04:36 +0000
Commit:     Eric van Gyzen <vangyzen@FreeBSD.org>
CommitDate: 2022-03-03 14:20:07 +0000

    ipmi: support getting address from EFI
    
    The original implementation only supports getting the address from legacy
    BIOS (by searching for the SMBIOS_SIG pattern in a fixed address space).
    
    Try to get the SMBIOS table from EFI through efirt (EFI Runtime Services)
    firstly.  Continue to search in the legacy BIOS if a NULL address is
    returned from EFI.
    
    By this way the ipmi function supports both legacy BIOS and UEFI systems.
    
    Reviewed by:    dab, vangyzen
    MFC after:      1 week
    Sponsored by:   Dell EMC Isilon
    Differential Revision: https://reviews.freebsd.org/D30007
    
    (cherry picked from commit ee8b757a949a9575c7355ea01f0475e0c526b9e5)
---
 sys/dev/ipmi/ipmi_isa.c    |  4 ++++
 sys/dev/ipmi/ipmi_pci.c    |  4 ++++
 sys/dev/ipmi/ipmi_smbios.c | 19 ++++++++++++++++---
 sys/dev/ipmi/ipmi_smbus.c  |  4 ++++
 4 files changed, 28 insertions(+), 3 deletions(-)

diff --git a/sys/dev/ipmi/ipmi_isa.c b/sys/dev/ipmi/ipmi_isa.c
index cdff305b07ec..1123f2849905 100644
--- a/sys/dev/ipmi/ipmi_isa.c
+++ b/sys/dev/ipmi/ipmi_isa.c
@@ -38,6 +38,7 @@ __FBSDID("$FreeBSD$");
 #include <sys/module.h>
 #include <sys/rman.h>
 #include <sys/selinfo.h>
+#include <sys/efi.h>
 
 #include <machine/pci_cfgreg.h>
 #include <dev/pci/pcireg.h>
@@ -286,3 +287,6 @@ static driver_t ipmi_isa_driver = {
 };
 
 DRIVER_MODULE(ipmi_isa, isa, ipmi_isa_driver, ipmi_devclass, 0, 0);
+#ifdef ARCH_MAY_USE_EFI
+MODULE_DEPEND(ipmi_isa, efirt, 1, 1, 1);
+#endif
diff --git a/sys/dev/ipmi/ipmi_pci.c b/sys/dev/ipmi/ipmi_pci.c
index d4598f9db873..13ac4f4b5ede 100644
--- a/sys/dev/ipmi/ipmi_pci.c
+++ b/sys/dev/ipmi/ipmi_pci.c
@@ -38,6 +38,7 @@ __FBSDID("$FreeBSD$");
 #include <sys/module.h>
 #include <sys/rman.h>
 #include <sys/selinfo.h>
+#include <sys/efi.h>
 
 #include <dev/pci/pcireg.h>
 #include <dev/pci/pcivar.h>
@@ -292,3 +293,6 @@ static driver_t ipmi2_pci_driver = {
 };
 
 DRIVER_MODULE(ipmi2_pci, pci, ipmi2_pci_driver, ipmi_devclass, 0, 0);
+#ifdef ARCH_MAY_USE_EFI
+MODULE_DEPEND(ipmi2_pci, efirt, 1, 1, 1);
+#endif
diff --git a/sys/dev/ipmi/ipmi_smbios.c b/sys/dev/ipmi/ipmi_smbios.c
index a1b953365d7c..e26b6f2956ad 100644
--- a/sys/dev/ipmi/ipmi_smbios.c
+++ b/sys/dev/ipmi/ipmi_smbios.c
@@ -36,6 +36,7 @@ __FBSDID("$FreeBSD$");
 #include <sys/eventhandler.h>
 #include <sys/kernel.h>
 #include <sys/selinfo.h>
+#include <sys/efi.h>
 
 #include <vm/vm.h>
 #include <vm/pmap.h>
@@ -150,15 +151,27 @@ smbios_ipmi_info(struct smbios_structure_header *h, void *arg)
 static void
 ipmi_smbios_probe(struct ipmi_get_info *info)
 {
+#ifdef ARCH_MAY_USE_EFI
+	struct uuid efi_smbios;
+	void *addr_efi;
+#endif
 	struct smbios_eps *header;
 	void *table;
 	u_int32_t addr;
 
+	addr = 0;
 	bzero(info, sizeof(struct ipmi_get_info));
 
-	/* Find the SMBIOS table header. */
-	addr = bios_sigsearch(SMBIOS_START, SMBIOS_SIG, SMBIOS_LEN,
-			      SMBIOS_STEP, SMBIOS_OFF);
+#ifdef ARCH_MAY_USE_EFI
+	efi_smbios = (struct uuid)EFI_TABLE_SMBIOS;
+	if (!efi_get_table(&efi_smbios, &addr_efi))
+		addr = (vm_paddr_t)addr_efi;
+#endif
+
+	if (addr == 0)
+		/* Find the SMBIOS table header. */
+		addr = bios_sigsearch(SMBIOS_START, SMBIOS_SIG, SMBIOS_LEN,
+			SMBIOS_STEP, SMBIOS_OFF);
 	if (addr == 0)
 		return;
 
diff --git a/sys/dev/ipmi/ipmi_smbus.c b/sys/dev/ipmi/ipmi_smbus.c
index 212248f0217e..652e0ea6e665 100644
--- a/sys/dev/ipmi/ipmi_smbus.c
+++ b/sys/dev/ipmi/ipmi_smbus.c
@@ -38,6 +38,7 @@ __FBSDID("$FreeBSD$");
 #include <sys/module.h>
 #include <sys/rman.h>
 #include <sys/selinfo.h>
+#include <sys/efi.h>
 
 #include <dev/smbus/smbconf.h>
 #include <dev/smbus/smbus.h>
@@ -131,3 +132,6 @@ static driver_t ipmi_smbus_driver = {
 
 DRIVER_MODULE(ipmi_smbus, smbus, ipmi_smbus_driver, ipmi_devclass, 0, 0);
 MODULE_DEPEND(ipmi_smbus, smbus, SMBUS_MINVER, SMBUS_PREFVER, SMBUS_MAXVER);
+#ifdef ARCH_MAY_USE_EFI
+MODULE_DEPEND(ipmi_smbus, efirt, 1, 1, 1);
+#endif