Module Name:    src
Committed By:   jmcneill
Date:           Sat Jul 24 11:39:19 UTC 2021

Modified Files:
        src/etc: MAKEDEV.tmpl
        src/etc/etc.aarch64: MAKEDEV.conf
        src/etc/etc.amd64: MAKEDEV.conf
        src/etc/etc.i386: MAKEDEV.conf
        src/sys/arch/arm/fdt: acpi_fdt.c
        src/sys/arch/x86/x86: bios32.c
        src/sys/conf: majors
        src/sys/dev: smbios.c smbiosvar.h

Log Message:
smbios: Add character device for accessing SMBIOS tables

The /dev/smbios character device gives an aperture into physical memory
that allows read-only access to the SMBIOS header and tables.


To generate a diff of this commit:
cvs rdiff -u -r1.223 -r1.224 src/etc/MAKEDEV.tmpl
cvs rdiff -u -r1.8 -r1.9 src/etc/etc.aarch64/MAKEDEV.conf
cvs rdiff -u -r1.32 -r1.33 src/etc/etc.amd64/MAKEDEV.conf
cvs rdiff -u -r1.33 -r1.34 src/etc/etc.i386/MAKEDEV.conf
cvs rdiff -u -r1.21 -r1.22 src/sys/arch/arm/fdt/acpi_fdt.c
cvs rdiff -u -r1.5 -r1.6 src/sys/arch/x86/x86/bios32.c
cvs rdiff -u -r1.97 -r1.98 src/sys/conf/majors
cvs rdiff -u -r1.1 -r1.2 src/sys/dev/smbios.c src/sys/dev/smbiosvar.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/etc/MAKEDEV.tmpl
diff -u src/etc/MAKEDEV.tmpl:1.223 src/etc/MAKEDEV.tmpl:1.224
--- src/etc/MAKEDEV.tmpl:1.223	Tue Jun 29 10:22:33 2021
+++ src/etc/MAKEDEV.tmpl	Sat Jul 24 11:39:18 2021
@@ -1,5 +1,5 @@
 #!/bin/sh -
-#	$NetBSD: MAKEDEV.tmpl,v 1.223 2021/06/29 10:22:33 nia Exp $
+#	$NetBSD: MAKEDEV.tmpl,v 1.224 2021/07/24 11:39:18 jmcneill Exp $
 #
 # Copyright (c) 2003,2007,2008 The NetBSD Foundation, Inc.
 # All rights reserved.
@@ -2240,6 +2240,10 @@ acpi)
 	mkdev acpi c %acpi_chr% 0
 	;;
 
+smbios)
+	mkdev smbios c %smbios_chr% 0
+	;;
+
 midevend)
 %MI_DEVICES_END%
 local)

Index: src/etc/etc.aarch64/MAKEDEV.conf
diff -u src/etc/etc.aarch64/MAKEDEV.conf:1.8 src/etc/etc.aarch64/MAKEDEV.conf:1.9
--- src/etc/etc.aarch64/MAKEDEV.conf:1.8	Sun Dec  6 02:57:30 2020
+++ src/etc/etc.aarch64/MAKEDEV.conf	Sat Jul 24 11:39:18 2021
@@ -1,4 +1,4 @@
-# $NetBSD: MAKEDEV.conf,v 1.8 2020/12/06 02:57:30 jmcneill Exp $
+# $NetBSD: MAKEDEV.conf,v 1.9 2021/07/24 11:39:18 jmcneill Exp $
 
 all_md)
 	makedev wscons fd0 fd1 wd0 wd1 wd2 wd3 sd0 sd1 sd2 sd3
@@ -21,6 +21,7 @@ all_md)
 	makedev bpf
 	makedev openfirm
 	makedev acpi
+	makedev smbios
 	;;
 
 ramdisk|floppy)

Index: src/etc/etc.amd64/MAKEDEV.conf
diff -u src/etc/etc.amd64/MAKEDEV.conf:1.32 src/etc/etc.amd64/MAKEDEV.conf:1.33
--- src/etc/etc.amd64/MAKEDEV.conf:1.32	Sun Dec  6 02:57:30 2020
+++ src/etc/etc.amd64/MAKEDEV.conf	Sat Jul 24 11:39:18 2021
@@ -1,4 +1,4 @@
-# $NetBSD: MAKEDEV.conf,v 1.32 2020/12/06 02:57:30 jmcneill Exp $
+# $NetBSD: MAKEDEV.conf,v 1.33 2021/07/24 11:39:18 jmcneill Exp $
 
 # As of 2003-04-17, the "init" case must not create more than 890 entries.
 all_md)
@@ -46,6 +46,7 @@ all_md)
 	makedev bio
 	makedev xmm0
 	makedev acpi
+	makedev smbios
 	;;
 
 xen)

Index: src/etc/etc.i386/MAKEDEV.conf
diff -u src/etc/etc.i386/MAKEDEV.conf:1.33 src/etc/etc.i386/MAKEDEV.conf:1.34
--- src/etc/etc.i386/MAKEDEV.conf:1.33	Sun Dec  6 02:57:30 2020
+++ src/etc/etc.i386/MAKEDEV.conf	Sat Jul 24 11:39:19 2021
@@ -1,4 +1,4 @@
-# $NetBSD: MAKEDEV.conf,v 1.33 2020/12/06 02:57:30 jmcneill Exp $
+# $NetBSD: MAKEDEV.conf,v 1.34 2021/07/24 11:39:19 jmcneill Exp $
 
 # As of 2005-03-15, the "init" case must not create more than 1024 entries.
 all_md)
@@ -50,6 +50,7 @@ all_md)
 	makedev bio
 	makedev cfs
 	makedev acpi
+	makedev smbios
 	;;
 
 xen)

Index: src/sys/arch/arm/fdt/acpi_fdt.c
diff -u src/sys/arch/arm/fdt/acpi_fdt.c:1.21 src/sys/arch/arm/fdt/acpi_fdt.c:1.22
--- src/sys/arch/arm/fdt/acpi_fdt.c:1.21	Fri Jul 23 21:33:35 2021
+++ src/sys/arch/arm/fdt/acpi_fdt.c	Sat Jul 24 11:39:19 2021
@@ -1,4 +1,4 @@
-/* $NetBSD: acpi_fdt.c,v 1.21 2021/07/23 21:33:35 jmcneill Exp $ */
+/* $NetBSD: acpi_fdt.c,v 1.22 2021/07/24 11:39:19 jmcneill Exp $ */
 
 /*-
  * Copyright (c) 2015-2017 Jared McNeill <[email protected]>
@@ -30,7 +30,7 @@
 #include "opt_efi.h"
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: acpi_fdt.c,v 1.21 2021/07/23 21:33:35 jmcneill Exp $");
+__KERNEL_RCSID(0, "$NetBSD: acpi_fdt.c,v 1.22 2021/07/24 11:39:19 jmcneill Exp $");
 
 #include <sys/param.h>
 #include <sys/bus.h>
@@ -179,6 +179,8 @@ acpi_fdt_smbios_init(device_t dev)
 		return;
 	}
 
+	smbios_entry.hdrphys = smbios_table;
+
 	smbver = acpi_fdt_smbios_version();
 	if (smbver == 3) {
 		struct smb3hdr *sh = AcpiOsMapMemory(smbios_table, sizeof(*sh));
@@ -188,6 +190,7 @@ acpi_fdt_smbios_init(device_t dev)
 
 		ptr = AcpiOsMapMemory(sh->addr, sh->size);
 		if (ptr != NULL) {
+			smbios_entry.tabphys = sh->addr;
 			smbios_entry.addr = ptr;
 			smbios_entry.len = sh->size;
 			smbios_entry.rev = sh->eprev;
@@ -208,6 +211,7 @@ acpi_fdt_smbios_init(device_t dev)
 
 		ptr = AcpiOsMapMemory(sh->addr, sh->size);
 		if (ptr != NULL) {
+			smbios_entry.tabphys = sh->addr;
 			smbios_entry.addr = ptr;
 			smbios_entry.len = sh->size;
 			smbios_entry.rev = 0;

Index: src/sys/arch/x86/x86/bios32.c
diff -u src/sys/arch/x86/x86/bios32.c:1.5 src/sys/arch/x86/x86/bios32.c:1.6
--- src/sys/arch/x86/x86/bios32.c:1.5	Wed Jul 21 23:16:09 2021
+++ src/sys/arch/x86/x86/bios32.c	Sat Jul 24 11:39:19 2021
@@ -1,4 +1,4 @@
-/*	$NetBSD: bios32.c,v 1.5 2021/07/21 23:16:09 jmcneill Exp $	*/
+/*	$NetBSD: bios32.c,v 1.6 2021/07/24 11:39:19 jmcneill Exp $	*/
 
 /*
  * Copyright (c) 1999 The NetBSD Foundation, Inc.
@@ -86,7 +86,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: bios32.c,v 1.5 2021/07/21 23:16:09 jmcneill Exp $");
+__KERNEL_RCSID(0, "$NetBSD: bios32.c,v 1.6 2021/07/24 11:39:19 jmcneill Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -252,6 +252,8 @@ smbios2_map_kva(const uint8_t *p)
 	if (eva == 0)
 		return;
 
+	smbios_entry.hdrphys = vtophys(p);
+	smbios_entry.tabphys = sh->addr;
 	smbios_entry.addr = (uint8_t *)(eva + (sh->addr & PGOFSET));
 	smbios_entry.len = sh->size;
 	smbios_entry.rev = 0;
@@ -285,6 +287,8 @@ smbios3_map_kva(const uint8_t *p)
 	if (eva == 0)
 		return;
 
+	smbios_entry.hdrphys = vtophys(p);
+	smbios_entry.tabphys = sh->addr;
 	smbios_entry.addr = (uint8_t *)(eva + ((vaddr_t)sh->addr & PGOFSET));
 	smbios_entry.len = sh->size;
 	smbios_entry.rev = sh->eprev;

Index: src/sys/conf/majors
diff -u src/sys/conf/majors:1.97 src/sys/conf/majors:1.98
--- src/sys/conf/majors:1.97	Sun Dec  6 02:57:30 2020
+++ src/sys/conf/majors	Sat Jul 24 11:39:19 2021
@@ -1,4 +1,4 @@
-# $NetBSD: majors,v 1.97 2020/12/06 02:57:30 jmcneill Exp $
+# $NetBSD: majors,v 1.98 2021/07/24 11:39:19 jmcneill Exp $
 #
 # Device majors for Machine-Independent drivers.
 #
@@ -91,3 +91,4 @@ device-major vio9p     char 356		   vio9
 device-major fault     char 357		   fault
 device-major wwanc     char 358	           wwanc
 device-major acpi      char 359            acpi
+device-major smbios    char 360            smbios

Index: src/sys/dev/smbios.c
diff -u src/sys/dev/smbios.c:1.1 src/sys/dev/smbios.c:1.2
--- src/sys/dev/smbios.c:1.1	Wed Jul 21 23:16:09 2021
+++ src/sys/dev/smbios.c	Sat Jul 24 11:39:19 2021
@@ -1,4 +1,4 @@
-/*	$NetBSD: smbios.c,v 1.1 2021/07/21 23:16:09 jmcneill Exp $	*/
+/*	$NetBSD: smbios.c,v 1.2 2021/07/24 11:39:19 jmcneill Exp $	*/
 
 /*
  * Copyright (c) 1999 The NetBSD Foundation, Inc.
@@ -86,12 +86,15 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: smbios.c,v 1.1 2021/07/21 23:16:09 jmcneill Exp $");
+__KERNEL_RCSID(0, "$NetBSD: smbios.c,v 1.2 2021/07/24 11:39:19 jmcneill Exp $");
 
 #include <sys/param.h>
+#include <sys/conf.h>
 #include <sys/systm.h>
 #include <sys/device.h>
 
+#include <uvm/uvm_extern.h>
+
 #include <dev/smbiosvar.h>
 
 #define	SMBIOS_MAKESIG(a, b, c, d)	\
@@ -99,6 +102,104 @@ __KERNEL_RCSID(0, "$NetBSD: smbios.c,v 1
 
 struct smbios_entry smbios_entry;
 
+static dev_type_read(smbios_read);
+
+const struct cdevsw smbios_cdevsw = {
+	.d_open		= nullopen,
+	.d_close	= nullclose,
+	.d_read		= smbios_read,
+	.d_write	= nowrite,
+	.d_ioctl	= noioctl,
+	.d_stop		= nostop,
+	.d_tty		= notty,
+	.d_poll		= nopoll,
+	.d_mmap		= nommap,
+	.d_kqfilter	= nokqfilter,
+	.d_discard	= nodiscard,
+	.d_flag		= D_OTHER | D_MPSAFE,
+};
+
+static void *
+smbios_map_memory(paddr_t pa, size_t size)
+{
+	paddr_t spa, epa, curpa;
+	vaddr_t va, curva;
+
+	spa = trunc_page(pa);
+	epa = round_page(pa + size);
+
+	va = uvm_km_alloc(kernel_map, epa - spa, 0, UVM_KMF_VAONLY);
+	if (va == 0) {
+		return NULL;
+	}
+
+	for (curpa = spa, curva = va; curpa < epa; curpa += PAGE_SIZE, curva += PAGE_SIZE) {
+		pmap_kenter_pa(curva, curpa, VM_PROT_READ, PMAP_WRITE_BACK);
+	}
+	pmap_update(pmap_kernel());
+
+	return (void *)(va + (pa - spa));
+}
+
+static void
+smbios_unmap_memory(void *va, size_t size)
+{
+	vaddr_t ova;
+	vsize_t osz;
+
+	ova = trunc_page((vaddr_t)va);
+	osz = round_page((vaddr_t)va + size) - ova;
+
+	pmap_kremove(ova, osz);
+	pmap_update(pmap_kernel());
+	uvm_km_free(kernel_map, ova, osz, UVM_KMF_VAONLY);
+}
+
+/*
+ * smbios_read --
+ *
+ *	Read data from an SMBIOS table that resides in physical memory.
+ */
+static int
+smbios_read(dev_t dev, struct uio *uio, int flag)
+{
+	paddr_t pa;
+	uint8_t *data;
+	size_t len;
+	int error;
+
+	if (smbios_entry.addr == NULL) {
+		return EIO;
+	}
+	if (uio->uio_rw != UIO_READ) {
+		return EPERM;
+	}
+
+	pa = uio->uio_offset;
+	if (pa == smbios_entry.hdrphys) {
+		/* SMBIOS header */
+		len = uimin(0x20, uio->uio_resid);
+
+	} else {
+		/* Table data */
+		if (pa < smbios_entry.tabphys ||
+		    pa >= smbios_entry.tabphys + smbios_entry.len) {
+			return EFAULT;
+		}
+		len = uimin(smbios_entry.len - (pa - smbios_entry.tabphys),
+			    uio->uio_resid);
+	}
+
+	data = smbios_map_memory(pa, len);
+	if (data == NULL) {
+		return ENOMEM;
+	}
+	error = uiomove(data, len, uio);
+	smbios_unmap_memory(data, len);
+
+	return error;
+}
+
 int
 smbios2_check_header(const uint8_t *p)
 {
Index: src/sys/dev/smbiosvar.h
diff -u src/sys/dev/smbiosvar.h:1.1 src/sys/dev/smbiosvar.h:1.2
--- src/sys/dev/smbiosvar.h:1.1	Wed Jul 21 23:16:09 2021
+++ src/sys/dev/smbiosvar.h	Sat Jul 24 11:39:19 2021
@@ -1,4 +1,4 @@
-/*	$NetBSD: smbiosvar.h,v 1.1 2021/07/21 23:16:09 jmcneill Exp $ */
+/*	$NetBSD: smbiosvar.h,v 1.2 2021/07/24 11:39:19 jmcneill Exp $ */
 /*
  * Copyright (c) 2006 Gordon Willem Klok <[email protected]>
  * Copyright (c) 2005 Jordan Hargrave
@@ -41,6 +41,8 @@
 #define SMBIOS_UUID_REPLEN 37 /* 16 zero padded values, 4 hyphens, 1 null */
 
 struct smbios_entry {
+	paddr_t		hdrphys;
+	paddr_t		tabphys;
 	uint8_t 	rev;
 	uint8_t 	mjr;
 	uint8_t 	min;

Reply via email to