Module Name: src Committed By: jmcneill Date: Wed Jul 21 23:26:15 UTC 2021
Modified Files: src/sys/arch/x86/conf: files.x86 Added Files: src/sys/dev: smbios_platform.c Removed Files: src/sys/arch/x86/x86: platform.c Log Message: x86's platform.c no longer has any x86 specific code in it, so move it to dev/smbios_platform.c to let other ports use it To generate a diff of this commit: cvs rdiff -u -r1.121 -r1.122 src/sys/arch/x86/conf/files.x86 cvs rdiff -u -r1.17 -r0 src/sys/arch/x86/x86/platform.c cvs rdiff -u -r0 -r1.1 src/sys/dev/smbios_platform.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/arch/x86/conf/files.x86 diff -u src/sys/arch/x86/conf/files.x86:1.121 src/sys/arch/x86/conf/files.x86:1.122 --- src/sys/arch/x86/conf/files.x86:1.121 Wed Jul 21 23:16:08 2021 +++ src/sys/arch/x86/conf/files.x86 Wed Jul 21 23:26:15 2021 @@ -1,4 +1,4 @@ -# $NetBSD: files.x86,v 1.121 2021/07/21 23:16:08 jmcneill Exp $ +# $NetBSD: files.x86,v 1.122 2021/07/21 23:26:15 jmcneill Exp $ # options for MP configuration through the MP spec defflag opt_mpbios.h MPBIOS MPDEBUG MPBIOS_SCANPCI @@ -103,7 +103,7 @@ file arch/x86/x86/idt.c machdep file arch/x86/x86/ipi.c machdep & !xenpv file arch/x86/x86/mtrr_i686.c mtrr & !xenpv file arch/x86/x86/patch.c machdep & !xenpv -file arch/x86/x86/platform.c machdep +file dev/smbios_platform.c machdep file arch/x86/x86/pmap.c machdep file arch/x86/x86/x86_tlb.c machdep file arch/x86/x86/procfs_machdep.c procfs Added files: Index: src/sys/dev/smbios_platform.c diff -u /dev/null src/sys/dev/smbios_platform.c:1.1 --- /dev/null Wed Jul 21 23:26:15 2021 +++ src/sys/dev/smbios_platform.c Wed Jul 21 23:26:15 2021 @@ -0,0 +1,321 @@ +/* $NetBSD: smbios_platform.c,v 1.1 2021/07/21 23:26:15 jmcneill Exp $ */ + +/*- + * Copyright (c) 2007 Jared D. McNeill <jmcne...@invisible.ca> + * 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 NETBSD FOUNDATION, INC. 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 FOUNDATION 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. + */ + +#include "isa.h" + +#include <sys/cdefs.h> +__KERNEL_RCSID(0, "$NetBSD: smbios_platform.c,v 1.1 2021/07/21 23:26:15 jmcneill Exp $"); + +#include <sys/types.h> +#include <sys/param.h> +#include <sys/kernel.h> +#include <sys/sysctl.h> +#include <sys/uuid.h> +#include <sys/pmf.h> + +#if NISA > 0 +#include <dev/isa/isavar.h> +#endif + +#include <dev/smbiosvar.h> + +static int platform_dminode = CTL_EOL; + +void platform_init(void); /* XXX */ +static void platform_add(struct smbtable *, const char *, int); +static void platform_add_word(struct smbtable *, const char *, uint16_t, + const char *); +static void platform_add_date(struct smbtable *, const char *, int); +static void platform_add_uuid(struct smbtable *, const char *, + const uint8_t *); +static int platform_dmi_sysctl(SYSCTLFN_PROTO); + +/* list of private DMI sysctl nodes */ +static const char *platform_private_nodes[] = { + "chassis-serial", + "board-serial", + "system-serial", + "system-uuid", + NULL +}; + +void +platform_init(void) +{ + struct smbtable smbios; + struct smbios_sys *psys; + struct smbios_struct_bios *pbios; + struct smbios_board *pboard; + struct smbios_chassis *pchassis; + struct smbios_processor *pproc; + struct smbios_slot *pslot; + int nisa, nother; + + smbios.cookie = 0; + if (smbios_find_table(SMBIOS_TYPE_SYSTEM, &smbios)) { + psys = smbios.tblhdr; + + platform_add(&smbios, "system-vendor", psys->vendor); + platform_add(&smbios, "system-product", psys->product); + platform_add(&smbios, "system-version", psys->version); + platform_add(&smbios, "system-serial", psys->serial); + platform_add_uuid(&smbios, "system-uuid", psys->uuid); + } + + smbios.cookie = 0; + if (smbios_find_table(SMBIOS_TYPE_BIOS, &smbios)) { + pbios = smbios.tblhdr; + + platform_add(&smbios, "bios-vendor", pbios->vendor); + platform_add(&smbios, "bios-version", pbios->version); + platform_add_date(&smbios, "bios-date", pbios->release); + } + + smbios.cookie = 0; + if (smbios_find_table(SMBIOS_TYPE_BASEBOARD, &smbios)) { + pboard = smbios.tblhdr; + + platform_add(&smbios, "board-vendor", pboard->vendor); + platform_add(&smbios, "board-product", pboard->product); + platform_add(&smbios, "board-version", pboard->version); + platform_add(&smbios, "board-serial", pboard->serial); + platform_add(&smbios, "board-asset-tag", pboard->asset); + } + + smbios.cookie = 0; + if (smbios_find_table(SMBIOS_TYPE_ENCLOSURE, &smbios)) { + pchassis = smbios.tblhdr; + + platform_add(&smbios, "chassis-vendor", pchassis->vendor); + platform_add(&smbios, "chassis-type", pchassis->shape); + platform_add(&smbios, "chassis-version", pchassis->version); + platform_add(&smbios, "chassis-serial", pchassis->serial); + platform_add(&smbios, "chassis-asset-tag", pchassis->asset); + } + + smbios.cookie = 0; + if (smbios_find_table(SMBIOS_TYPE_PROCESSOR, &smbios)) { + pproc = smbios.tblhdr; + + platform_add(&smbios, "processor-vendor", pproc->vendor); + platform_add(&smbios, "processor-version", pproc->version); + platform_add_word(&smbios, "processor-frequency", + pproc->curspeed, " MHz"); + } + + smbios.cookie = 0; + nisa = 0; + nother = 0; + while (smbios_find_table(SMBIOS_TYPE_SLOTS, &smbios)) { + pslot = smbios.tblhdr; + switch (pslot->type) { + case SMBIOS_SLOT_ISA: + case SMBIOS_SLOT_EISA: + nisa++; + break; + default: + nother++; + break; + } + } + +#if NISA > 0 + if ((nother | nisa) != 0) { + /* Only if there seems to be good expansion slot info. */ + isa_set_slotcount(nisa); + } +#endif +} + +static bool +platform_sysctl_is_private(const char *key) +{ + unsigned int n; + + for (n = 0; platform_private_nodes[n] != NULL; n++) { + if (strcmp(key, platform_private_nodes[n]) == 0) { + return true; + } + } + + return false; +} + +static void +platform_create_sysctl(const char *key) +{ + int flags = 0, err; + + if (pmf_get_platform(key) == NULL) + return; + + /* If the key is marked private, set CTLFLAG_PRIVATE flag */ + if (platform_sysctl_is_private(key)) + flags |= CTLFLAG_PRIVATE; + + err = sysctl_createv(NULL, 0, NULL, NULL, + CTLFLAG_READONLY | flags, CTLTYPE_STRING, + key, NULL, platform_dmi_sysctl, 0, NULL, 0, + CTL_MACHDEP, platform_dminode, CTL_CREATE, CTL_EOL); + if (err != 0) + printf("platform: sysctl_createv " + "(machdep.dmi.%s) failed, err = %d\n", + key, err); +} + +static void +platform_add(struct smbtable *tbl, const char *key, int idx) +{ + char tmpbuf[128]; /* XXX is this long enough? */ + + if (smbios_get_string(tbl, idx, tmpbuf, 128) != NULL) { + /* add to platform dictionary */ + pmf_set_platform(key, tmpbuf); + + /* create sysctl node */ + platform_create_sysctl(key); + } +} + +static void +platform_add_word(struct smbtable *tbl, const char *key, uint16_t val, + const char *suf) +{ + char tmpbuf[128]; /* XXX is this long enough? */ + + if (snprintf(tmpbuf, sizeof(tmpbuf), "%u%s", val, suf)) { + /* add to platform dictionary */ + pmf_set_platform(key, tmpbuf); + + /* create sysctl node */ + platform_create_sysctl(key); + } +} + +static int +platform_scan_date(char *buf, unsigned int *month, unsigned int *day, + unsigned int *year) +{ + char *p, *s; + + s = buf; + p = strchr(s, '/'); + if (p) *p = '\0'; + *month = strtoul(s, NULL, 10); + if (!p) return 1; + + s = p + 1; + p = strchr(s, '/'); + if (p) *p = '\0'; + *day = strtoul(s, NULL, 10); + if (!p) return 2; + + s = p + 1; + *year = strtoul(s, NULL, 10); + return 3; +} + +static void +platform_add_date(struct smbtable *tbl, const char *key, int idx) +{ + unsigned int month, day, year; + char tmpbuf[128], datestr[9]; + + if (smbios_get_string(tbl, idx, tmpbuf, 128) == NULL) + return; + if (platform_scan_date(tmpbuf, &month, &day, &year) != 3) + return; + if (month == 0 || month > 12 || day == 0 || day > 31) + return; + if (year > 9999) + return; + if (year < 70) + year += 2000; + else if (year < 100) + year += 1900; + snprintf(datestr, sizeof(datestr), "%04u%02u%02u", year, month, day); + pmf_set_platform(key, datestr); + platform_create_sysctl(key); +} + +static void +platform_add_uuid(struct smbtable *tbl, const char *key, const uint8_t *buf) +{ + struct uuid uuid; + char tmpbuf[UUID_STR_LEN]; + + uuid_dec_le(buf, &uuid); + uuid_snprintf(tmpbuf, sizeof(tmpbuf), &uuid); + + pmf_set_platform(key, tmpbuf); + platform_create_sysctl(key); +} + +static int +platform_dmi_sysctl(SYSCTLFN_ARGS) +{ + struct sysctlnode node; + const char *v; + int err = 0; + + node = *rnode; + + v = pmf_get_platform(node.sysctl_name); + if (v == NULL) + return ENOENT; + + node.sysctl_data = __UNCONST(v); + err = sysctl_lookup(SYSCTLFN_CALL(&node)); + if (err || newp == NULL) + return err; + + return 0; +} + +SYSCTL_SETUP(sysctl_dmi_setup, "sysctl machdep.dmi subtree setup") +{ + const struct sysctlnode *rnode; + int err; + + err = sysctl_createv(clog, 0, NULL, &rnode, + CTLFLAG_PERMANENT, CTLTYPE_NODE, "machdep", + NULL, NULL, 0, NULL, 0, + CTL_MACHDEP, CTL_EOL); + if (err) + return; + + err = sysctl_createv(clog, 0, &rnode, &rnode, + CTLFLAG_PERMANENT, CTLTYPE_NODE, "dmi", + SYSCTL_DESCR("DMI table information"), + NULL, 0, NULL, 0, + CTL_CREATE, CTL_EOL); + if (err) + return; + + platform_dminode = rnode->sysctl_num; +}