mirror of
https://git.jff.email/cgit/dmidecode.git
synced 2026-08-07 15:50:51 +00:00
Merge branch 'release/debian/3.1-1'
This commit is contained in:
commit
6b606a764c
2
AUTHORS
2
AUTHORS
@ -19,6 +19,8 @@ Jarod Wilson <jarod@redhat.com>
|
||||
Anton Arapov <anton@redhat.com>
|
||||
Roy Franz <roy.franz@linaro.org>
|
||||
Tyler Bell <tyler.bell@hp.com>
|
||||
Xie XiuQi <xiexiuqi@huawei.com>
|
||||
Petr Oros <poros@redhat.com>
|
||||
|
||||
MANY THANKS TO (IN CHRONOLOGICAL ORDER)
|
||||
Werner Heuser
|
||||
|
||||
98
CHANGELOG
98
CHANGELOG
@ -1,3 +1,101 @@
|
||||
2015-09-03 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* version.h: Set version to 3.1.
|
||||
|
||||
2017-05-23 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* dmidecode.c, dmiopt.c: Add a new option to extract OEM strings, like
|
||||
we already have for many other strings.
|
||||
* dmidecode.8: Document the new option.
|
||||
|
||||
2017-04-27 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
Update to support SMBIOS specification version 3.1.1.
|
||||
|
||||
* dmidecode.c: Add support for 3-digit versions.
|
||||
* dmidecode.c: Add new enumerated values for processors (DMI type 4).
|
||||
|
||||
2017-04-27 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
Update to support SMBIOS specification version 3.1.0.
|
||||
|
||||
* dmidecode.c: Add support for extended BIOS ROM size (DMI type 0).
|
||||
* dmidecode.c: Add new enumerated values for chassis types
|
||||
(DMI type 3).
|
||||
* dmidecode.c: Add new enumerated values for processors (DMI type 4).
|
||||
* dmidecode.c: Don't assume 8-bit processor family in dmi_processor_id
|
||||
(DMI type 4).
|
||||
* dmidecode.c: Decode the MIDR register on ARM processors
|
||||
(DMI type 4).
|
||||
* dmidecode.c: Add support for large cache sizes (DMI type 7).
|
||||
* dmidecode.c: Add Mini PCIe system slot enumerated values
|
||||
(DMI type 9).
|
||||
* dmidecode.c: Clarify the memory speed unit (DMI type 17).
|
||||
* dmidecode.c: Add support for structure type 43 (TPM Device).
|
||||
|
||||
2017-04-11 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* util.c: Don't leak a file descriptor in function read_file.
|
||||
* util.c, util.c, dmidecode.c: Let callers pass an offset to function
|
||||
read_file.
|
||||
* dmidecode.c: Fix reading from SMBIOS 3 dump files using a 64-bit
|
||||
entry point.
|
||||
|
||||
2017-04-10 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* dmidecode.c: Decode the processor ID of the Intel Core M, AMD
|
||||
Athlon X4 and AMD Opteron X1000/X2000 processors (DMI type 4).
|
||||
* dmidecode.c: Display the IPMI interrupt number as a decimal
|
||||
number (DMI type 38).
|
||||
|
||||
2017-01-20 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* biosdecode.c: Decode the entry point defined in the Intel
|
||||
Multiprocessor specification.
|
||||
|
||||
2017-01-20 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* dmidecode.c: Only decode one DMI table.
|
||||
This fixes Savannah bug #50022:
|
||||
https://savannah.nongnu.org/bugs/?50022
|
||||
|
||||
2016-09-22 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* README: Explain that we can no longer support Cygwin.
|
||||
|
||||
2016-06-30 Petr Oros <poros@redhat.com>
|
||||
|
||||
* dmidecode.c: Unmask LRDIMM in memory type detail (DMI type 17).
|
||||
|
||||
2015-11-02 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* dmidecode.c, util.c, util.h: Let read_file return the actual data
|
||||
size.
|
||||
* dmidecode.c: Use read_file to read the DMI table from sysfs.
|
||||
This fixes Savannah bug #46176:
|
||||
https://savannah.nongnu.org/bugs/?46176
|
||||
* dmidecode.c: Check the sysfs entry point length.
|
||||
|
||||
2015-10-21 Xie XiuQi <xiexiuqi@huawei.com>
|
||||
|
||||
* dmidecode.c: Handle SMBIOS 3.0 entry points on EFI systems.
|
||||
|
||||
2015-10-20 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* dmidecode.c: Handle OEM-specific types in group associations
|
||||
(DMI type 14).
|
||||
|
||||
2015-10-14 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* util.c: Avoid SIGBUS on mmap failure.
|
||||
This fixes Savannah bug #46066:
|
||||
https://savannah.nongnu.org/bugs/?46066
|
||||
* util.c: Fix error paths in mem_chunk.
|
||||
|
||||
2015-10-01 Roy Franz <roy.franz@linaro.org>
|
||||
|
||||
* dmiopt.c: Add "--no-sysfs" option description to -h output.
|
||||
|
||||
2015-09-03 Jean Delvare <jdelvare@suse.de>
|
||||
|
||||
* version.h: Set version to 3.0.
|
||||
|
||||
7
README
7
README
@ -28,7 +28,7 @@ and other interesting material, such as a list of related projects and
|
||||
articles.
|
||||
|
||||
This program was first written for Linux, and has since been reported to work
|
||||
on FreeBSD, NetBSD, OpenBSD, BeOS, Cygwin and Solaris as well.
|
||||
on FreeBSD, NetBSD, OpenBSD, BeOS and Solaris as well.
|
||||
|
||||
There's no configure script, so simply run "make" to build dmidecode, and
|
||||
"make install" to install it. You also can use "make uninstall" to remove
|
||||
@ -83,9 +83,8 @@ successfully run.
|
||||
|
||||
CYGWIN
|
||||
|
||||
Dmidecode was reported to work under Cygwin. It seems that /dev/mem doesn't
|
||||
work properly before version 1.5.10 though, so you will need to use at least
|
||||
this version.
|
||||
Dmidecode used to work under Cygwin. However the /dev/mem interface was
|
||||
removed at some point in time so it no longer works.
|
||||
|
||||
|
||||
** MISCELLANEOUS TOOLS **
|
||||
|
||||
34
biosdecode.c
34
biosdecode.c
@ -2,7 +2,7 @@
|
||||
* BIOS Decode
|
||||
*
|
||||
* Copyright (C) 2000-2002 Alan Cox <alan@redhat.com>
|
||||
* Copyright (C) 2002-2015 Jean Delvare <jdelvare@suse.de>
|
||||
* Copyright (C) 2002-2017 Jean Delvare <jdelvare@suse.de>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
@ -52,6 +52,9 @@
|
||||
* - Fujitsu application panel technical details
|
||||
* As of July 23rd, 2004
|
||||
* http://apanel.sourceforge.net/tech.php
|
||||
* - Intel Multiprocessor Specification
|
||||
* Version 1.4
|
||||
* http://www.intel.com/design/archives/processors/pro/docs/242016.htm
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
@ -545,6 +548,34 @@ static int fjkeyinf_decode(const u8 *p, size_t len)
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* Intel Multiprocessor
|
||||
*/
|
||||
|
||||
static size_t mp_length(const u8 *p)
|
||||
{
|
||||
return 16 * p[8];
|
||||
}
|
||||
|
||||
static int mp_decode(const u8 *p, size_t len)
|
||||
{
|
||||
if (!checksum(p, len))
|
||||
return 0;
|
||||
|
||||
printf("Intel Multiprocessor present.\n");
|
||||
printf("\tSpecification Revision: %s\n",
|
||||
p[9] == 0x01 ? "1.1" : p[9] == 0x04 ? "1.4" : "Invalid");
|
||||
if (p[11])
|
||||
printf("\tDefault Configuration: #%d\n", p[11]);
|
||||
else
|
||||
printf("\tConfiguration Table Address: 0x%08X\n",
|
||||
DWORD(p + 4));
|
||||
printf("\tMode: %s\n", p[12] & (1 << 7) ?
|
||||
"IMCR and PIC" : "Virtual Wire");
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* Main
|
||||
*/
|
||||
@ -562,6 +593,7 @@ static struct bios_entry bios_entries[] = {
|
||||
{ "32OS", 0, 0xE0000, 0xFFFFF, compaq_length, compaq_decode },
|
||||
{ "\252\125VPD", 0, 0xF0000, 0xFFFFF, vpd_length, vpd_decode },
|
||||
{ "FJKEYINF", 0, 0xF0000, 0xFFFFF, fjkeyinf_length, fjkeyinf_decode },
|
||||
{ "_MP_", 0, 0xE0000, 0xFFFFF, mp_length, mp_decode },
|
||||
{ NULL, 0, 0, 0, NULL, NULL }
|
||||
};
|
||||
|
||||
|
||||
18
debian/README.source
vendored
Normal file
18
debian/README.source
vendored
Normal file
@ -0,0 +1,18 @@
|
||||
Hello,
|
||||
|
||||
now I use the branching model from Vincent Driessen[1].
|
||||
|
||||
I use the gitflow-avh[2]. with the Documentation[3].
|
||||
The Debian package can be found here[4].
|
||||
|
||||
Please upload unattended uploads use a branch feature/<your title>.
|
||||
|
||||
|
||||
Many thanks.
|
||||
|
||||
-- Jörg Frings-Fürst <debian@jff-webhosting.net> Fri, 02 Jun 2017 19:00:40 +0200
|
||||
|
||||
[1] http://nvie.com/posts/a-successful-git-branching-model/
|
||||
[2] https://github.com/petervanderdoes/gitflow-avh
|
||||
[3] https://github.com/petervanderdoes/gitflow-avh/wiki
|
||||
[4] https://tracker.debian.org/pkg/git-flow
|
||||
26
debian/changelog
vendored
26
debian/changelog
vendored
@ -1,3 +1,29 @@
|
||||
dmidecode (3.1-1) unstable; urgency=medium
|
||||
|
||||
* New upstream release (LP: #1688162) (Closes: #860897):
|
||||
- Remove applied patches:
|
||||
+ debian/patches/0110-nosysfs.patch
|
||||
+ debian/patches/0115-no_smbios_DMI_entry_point.patch
|
||||
+ debian/patches/0120-return_actual_data_size.patch
|
||||
+ debian/patches/0125-use_read_file_to_read_DMI_table_from_sysfs.patch
|
||||
+ debian/patches/0130-use_DWORD_for_table_max_size.patch
|
||||
+ debian/patches/0135-hide_fixup_msg.patch
|
||||
* debian/copyright:
|
||||
- Add year 2017.
|
||||
- Change upstream email address.
|
||||
* debian/control:
|
||||
- Change Homepage.
|
||||
* Migrate to debhelper 10:
|
||||
- Change debian/compat to 10.
|
||||
- Bump minimum debhelper version in debian/control to >= 10.
|
||||
* Use the automatic debug symbol packages:
|
||||
- Remove dmidecode-dbg section from debian/control.
|
||||
- Remove override_dh_strip from debian/rules.
|
||||
* New README.source to explain the branching model used.
|
||||
* Declare compliance with Debian Policy 4.0.0. (No changes needed).
|
||||
|
||||
-- Jörg Frings-Fürst <debian@jff-webhosting.net> Sat, 24 Jun 2017 23:21:09 +0200
|
||||
|
||||
dmidecode (3.0-4) unstable; urgency=medium
|
||||
|
||||
* debian/rules: Fix FTCBFS to pass suitable CC to make. (Closes: #835921).
|
||||
|
||||
2
debian/compat
vendored
2
debian/compat
vendored
@ -1 +1 @@
|
||||
9
|
||||
10
|
||||
|
||||
17
debian/control
vendored
17
debian/control
vendored
@ -2,11 +2,11 @@ Source: dmidecode
|
||||
Section: utils
|
||||
Priority: optional
|
||||
Maintainer: Jörg Frings-Fürst <debian@jff-webhosting.net>
|
||||
Build-Depends: debhelper (>= 9)
|
||||
Standards-Version: 3.9.8
|
||||
Build-Depends: debhelper (>= 10)
|
||||
Standards-Version: 4.0.0
|
||||
Vcs-Browser: https://anonscm.debian.org/cgit/collab-maint/dmidecode.git
|
||||
Vcs-Git: https://anonscm.debian.org/cgit/collab-maint/dmidecode.git
|
||||
Homepage: https://dmidecode.nongnu.org/
|
||||
Homepage: http://nongnu.org/dmidecode/
|
||||
|
||||
Package: dmidecode
|
||||
Priority: important
|
||||
@ -26,17 +26,6 @@ Description: SMBIOS/DMI table decoder
|
||||
Beware that DMI data have proven to be too unreliable to be blindly trusted.
|
||||
Dmidecode does not scan the hardware, it only reports what the BIOS told it to.
|
||||
|
||||
Package: dmidecode-dbg
|
||||
Section: debug
|
||||
Priority: extra
|
||||
Architecture: any-amd64 arm64 armhf ia64 any-i386
|
||||
Depends: ${misc:Depends}, dmidecode (= ${binary:Version})
|
||||
Description: SMBIOS/DMI table decoder (debug)
|
||||
Dmidecode reports information about the system's hardware as described in the
|
||||
system BIOS according to the SMBIOS/DMI standard.
|
||||
.
|
||||
This package contains the debugging symbols.
|
||||
|
||||
Package: dmidecode-udeb
|
||||
Section: debian-installer
|
||||
Architecture: any-amd64 arm64 armhf ia64 any-i386
|
||||
|
||||
4
debian/copyright
vendored
4
debian/copyright
vendored
@ -4,7 +4,7 @@ Upstream-Contact: dmidecode-devel@nongnu.org
|
||||
Source: http://download.savannah.gnu.org/releases/demidecode/
|
||||
|
||||
Files: *
|
||||
Copyright: 2002-2016 Jean Delvare <khali@linux-fr.org>
|
||||
Copyright: 2002-2017 Jean Delvare <jdelvare@suse.de>
|
||||
2002 Alan Cox <alan@redhat.com>
|
||||
2010 Anton Arapov <anton@redhat.com>
|
||||
2015 Xie XiuQi <xiexiuqi@huawei.com>
|
||||
@ -13,7 +13,7 @@ License: GPL-2+
|
||||
Files: debian/*
|
||||
Copyright: 2003-2007 Petter Reinholdtsen <pere@debian.org>
|
||||
2011-2012 Daniel Baumann <daniel.baumann@progress-technologies.net>
|
||||
2014-2016 Jörg Frings-Fürst <debian@jff-webhosting.net>
|
||||
2014-2017 Jörg Frings-Fürst <debian@jff-webhosting.net>
|
||||
License: GPL-2+
|
||||
|
||||
License: GPL-2+
|
||||
|
||||
1
debian/files
vendored
Normal file
1
debian/files
vendored
Normal file
@ -0,0 +1 @@
|
||||
dmidecode_3.1-1_source.buildinfo utils optional
|
||||
14
debian/patches/series
vendored
14
debian/patches/series
vendored
@ -1,10 +1,10 @@
|
||||
0100-ansi-c.patch
|
||||
0001-hurd.patch
|
||||
0005-build.patch
|
||||
0105-dmidecode-avoid-sigbus.patch
|
||||
0110-nosysfs.patch
|
||||
0115-no_smbios_DMI_entry_point.patch
|
||||
0120-return_actual_data_size.patch
|
||||
0125-use_read_file_to_read_DMI_table_from_sysfs.patch
|
||||
0130-use_DWORD_for_table_max_size.patch
|
||||
0135-hide_fixup_msg.patch
|
||||
#0105-dmidecode-avoid-sigbus.patch
|
||||
#0110-nosysfs.patch
|
||||
#0115-no_smbios_DMI_entry_point.patch
|
||||
#0120-return_actual_data_size.patch
|
||||
#0125-use_read_file_to_read_DMI_table_from_sysfs.patch
|
||||
#0130-use_DWORD_for_table_max_size.patch
|
||||
#0135-hide_fixup_msg.patch
|
||||
|
||||
3
debian/rules
vendored
3
debian/rules
vendored
@ -22,6 +22,3 @@ override_dh_auto_install:
|
||||
|
||||
override_dh_install:
|
||||
dh_install --fail-missing
|
||||
|
||||
override_dh_strip:
|
||||
dh_strip --dbg-package=dmidecode-dbg
|
||||
|
||||
412
dmidecode.c
412
dmidecode.c
@ -2,7 +2,7 @@
|
||||
* DMI Decode
|
||||
*
|
||||
* Copyright (C) 2000-2002 Alan Cox <alan@redhat.com>
|
||||
* Copyright (C) 2002-2015 Jean Delvare <jdelvare@suse.de>
|
||||
* Copyright (C) 2002-2017 Jean Delvare <jdelvare@suse.de>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
@ -25,7 +25,7 @@
|
||||
* are deemed to be part of the source code.
|
||||
*
|
||||
* Unless specified otherwise, all references are aimed at the "System
|
||||
* Management BIOS Reference Specification, Version 3.0.0" document,
|
||||
* Management BIOS Reference Specification, Version 3.1.1" document,
|
||||
* available from http://www.dmtf.org/standards/smbios.
|
||||
*
|
||||
* Note to contributors:
|
||||
@ -50,6 +50,12 @@
|
||||
* - DMTF DSP0239 version 1.1.0
|
||||
* "Management Component Transport Protocol (MCTP) IDs and Codes"
|
||||
* http://www.dmtf.org/standards/pmci
|
||||
* - "TPM Main, Part 2 TPM Structures"
|
||||
* Specification version 1.2, level 2, revision 116
|
||||
* https://trustedcomputinggroup.org/tpm-main-specification/
|
||||
* - "PC Client Platform TPM Profile (PTP) Specification"
|
||||
* Family "2.0", Level 00, Revision 00.43, January 26, 2015
|
||||
* https://trustedcomputinggroup.org/pc-client-platform-tpm-profile-ptp-specification/
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
@ -69,13 +75,14 @@
|
||||
#define out_of_spec "<OUT OF SPEC>"
|
||||
static const char *bad_index = "<BAD INDEX>";
|
||||
|
||||
#define SUPPORTED_SMBIOS_VER 0x0300
|
||||
#define SUPPORTED_SMBIOS_VER 0x030101
|
||||
|
||||
#define FLAG_NO_FILE_OFFSET (1 << 0)
|
||||
#define FLAG_STOP_AT_EOT (1 << 1)
|
||||
|
||||
#define SYS_ENTRY_FILE "/sys/firmware/dmi/tables/smbios_entry_point"
|
||||
#define SYS_TABLE_FILE "/sys/firmware/dmi/tables/DMI"
|
||||
#define SYS_FIRMWARE_DIR "/sys/firmware/dmi/tables"
|
||||
#define SYS_ENTRY_FILE SYS_FIRMWARE_DIR "/smbios_entry_point"
|
||||
#define SYS_TABLE_FILE SYS_FIRMWARE_DIR "/DMI"
|
||||
|
||||
/*
|
||||
* Type-independant Stuff
|
||||
@ -169,10 +176,13 @@ static const char *dmi_smbios_structure_type(u8 code)
|
||||
"Power Supply",
|
||||
"Additional Information",
|
||||
"Onboard Device",
|
||||
"Management Controller Host Interface", /* 42 */
|
||||
"Management Controller Host Interface",
|
||||
"TPM Device", /* 43 */
|
||||
};
|
||||
|
||||
if (code <= 42)
|
||||
if (code >= 128)
|
||||
return "OEM-specific";
|
||||
if (code <= 43)
|
||||
return type[code];
|
||||
return out_of_spec;
|
||||
}
|
||||
@ -292,6 +302,18 @@ static void dmi_bios_runtime_size(u32 code)
|
||||
printf(" %u kB", code >> 10);
|
||||
}
|
||||
|
||||
static void dmi_bios_rom_size(u8 code1, u16 code2)
|
||||
{
|
||||
static const char *unit[4] = {
|
||||
"MB", "GB", out_of_spec, out_of_spec
|
||||
};
|
||||
|
||||
if (code1 != 0xFF)
|
||||
printf(" %u kB", (code1 + 1) << 6);
|
||||
else
|
||||
printf(" %u %s", code2 & 0x3FFF, unit[code2 >> 14]);
|
||||
}
|
||||
|
||||
static void dmi_bios_characteristics(u64 code, const char *prefix)
|
||||
{
|
||||
/* 7.1.1 */
|
||||
@ -550,12 +572,16 @@ static const char *dmi_chassis_type(u8 code)
|
||||
"Blade Enclosing",
|
||||
"Tablet",
|
||||
"Convertible",
|
||||
"Detachable" /* 0x20 */
|
||||
"Detachable",
|
||||
"IoT Gateway",
|
||||
"Embedded PC",
|
||||
"Mini PC",
|
||||
"Stick PC" /* 0x24 */
|
||||
};
|
||||
|
||||
code &= 0x7F; /* bits 6:0 are chassis type, 7th bit is the lock bit */
|
||||
|
||||
if (code >= 0x01 && code <= 0x20)
|
||||
if (code >= 0x01 && code <= 0x24)
|
||||
return type[code - 0x01];
|
||||
return out_of_spec;
|
||||
}
|
||||
@ -717,7 +743,9 @@ static const char *dmi_processor_family(const struct dmi_header *h, u16 ver)
|
||||
{ 0x2A, "Core Solo Mobile" },
|
||||
{ 0x2B, "Atom" },
|
||||
{ 0x2C, "Core M" },
|
||||
|
||||
{ 0x2D, "Core m3" },
|
||||
{ 0x2E, "Core m5" },
|
||||
{ 0x2F, "Core m7" },
|
||||
{ 0x30, "Alpha" },
|
||||
{ 0x31, "Alpha 21064" },
|
||||
{ 0x32, "Alpha 21066" },
|
||||
@ -769,6 +797,9 @@ static const char *dmi_processor_family(const struct dmi_header *h, u16 ver)
|
||||
{ 0x66, "Athlon X4" },
|
||||
{ 0x67, "Opteron X1000" },
|
||||
{ 0x68, "Opteron X2000" },
|
||||
{ 0x69, "Opteron A-Series" },
|
||||
{ 0x6A, "Opteron X3000" },
|
||||
{ 0x6B, "Zen" },
|
||||
|
||||
{ 0x70, "Hobbit" },
|
||||
|
||||
@ -880,6 +911,8 @@ static const char *dmi_processor_family(const struct dmi_header *h, u16 ver)
|
||||
{ 0xFA, "i860" },
|
||||
{ 0xFB, "i960" },
|
||||
|
||||
{ 0x100, "ARMv7" },
|
||||
{ 0x101, "ARMv8" },
|
||||
{ 0x104, "SH-3" },
|
||||
{ 0x105, "SH-4" },
|
||||
{ 0x118, "ARM" },
|
||||
@ -891,6 +924,10 @@ static const char *dmi_processor_family(const struct dmi_header *h, u16 ver)
|
||||
{ 0x15E, "DSP" },
|
||||
{ 0x1F4, "Video Processor" },
|
||||
};
|
||||
/*
|
||||
* Note to developers: when adding entries to this list, check if
|
||||
* function dmi_processor_id below needs updating too.
|
||||
*/
|
||||
|
||||
/* Special case for ambiguous value 0x30 (SMBIOS 2.0 only) */
|
||||
if (ver == 0x0200 && data[0x06] == 0x30 && h->length >= 0x08)
|
||||
@ -943,7 +980,7 @@ static const char *dmi_processor_family(const struct dmi_header *h, u16 ver)
|
||||
}
|
||||
}
|
||||
|
||||
static void dmi_processor_id(u8 type, const u8 *p, const char *version, const char *prefix)
|
||||
static void dmi_processor_id(const struct dmi_header *h, const char *prefix)
|
||||
{
|
||||
/* Intel AP-485 revision 36, table 2-4 */
|
||||
static const char *flags[32] = {
|
||||
@ -980,13 +1017,14 @@ static void dmi_processor_id(u8 type, const u8 *p, const char *version, const ch
|
||||
NULL, /* 30 */
|
||||
"PBE (Pending break enabled)" /* 31 */
|
||||
};
|
||||
/*
|
||||
* Extra flags are now returned in the ECX register when one calls
|
||||
* the CPUID instruction. Their meaning is explained in table 3-5, but
|
||||
* DMI doesn't support this yet.
|
||||
*/
|
||||
const u8 *data = h->data;
|
||||
const u8 *p = data + 0x08;
|
||||
u32 eax, edx;
|
||||
int sig = 0;
|
||||
u16 type;
|
||||
|
||||
type = (data[0x06] == 0xFE && h->length >= 0x2A) ?
|
||||
WORD(data + 0x28) : data[0x06];
|
||||
|
||||
/*
|
||||
* This might help learn about new processors supporting the
|
||||
@ -1026,8 +1064,24 @@ static void dmi_processor_id(u8 type, const u8 *p, const char *version, const ch
|
||||
return;
|
||||
}
|
||||
}
|
||||
else if ((type >= 0x100 && type <= 0x101) /* ARM */
|
||||
|| (type >= 0x118 && type <= 0x119)) /* ARM */
|
||||
{
|
||||
u32 midr = DWORD(p);
|
||||
/*
|
||||
* The format of this field was not defined for ARM processors
|
||||
* before version 3.1.0 of the SMBIOS specification, so we
|
||||
* silently skip it if it reads all zeroes.
|
||||
*/
|
||||
if (midr == 0)
|
||||
return;
|
||||
printf("%sSignature: Implementor 0x%02x, Variant 0x%x, Architecture %u, Part 0x%03x, Revision %u\n",
|
||||
prefix, midr >> 24, (midr >> 20) & 0xF,
|
||||
(midr >> 16) & 0xF, (midr >> 4) & 0xFFF, midr & 0xF);
|
||||
return;
|
||||
}
|
||||
else if ((type >= 0x0B && type <= 0x15) /* Intel, Cyrix */
|
||||
|| (type >= 0x28 && type <= 0x2B) /* Intel */
|
||||
|| (type >= 0x28 && type <= 0x2F) /* Intel */
|
||||
|| (type >= 0xA1 && type <= 0xB3) /* Intel */
|
||||
|| type == 0xB5 /* Intel */
|
||||
|| (type >= 0xB9 && type <= 0xC7) /* Intel */
|
||||
@ -1039,12 +1093,14 @@ static void dmi_processor_id(u8 type, const u8 *p, const char *version, const ch
|
||||
|| type == 0x1F /* AMD */
|
||||
|| (type >= 0x38 && type <= 0x3F) /* AMD */
|
||||
|| (type >= 0x46 && type <= 0x4F) /* AMD */
|
||||
|| (type >= 0x66 && type <= 0x6B) /* AMD */
|
||||
|| (type >= 0x83 && type <= 0x8F) /* AMD */
|
||||
|| (type >= 0xB6 && type <= 0xB7) /* AMD */
|
||||
|| (type >= 0xE4 && type <= 0xEF)) /* AMD */
|
||||
sig = 2;
|
||||
else if (type == 0x01 || type == 0x02)
|
||||
{
|
||||
const char *version = dmi_string(h, data[0x10]);
|
||||
/*
|
||||
* Some X86-class CPU have family "Other" or "Unknown". In this case,
|
||||
* we use the version string to determine if they are known to
|
||||
@ -1062,9 +1118,14 @@ static void dmi_processor_id(u8 type, const u8 *p, const char *version, const ch
|
||||
else
|
||||
return;
|
||||
}
|
||||
else /* not X86-class */
|
||||
else /* neither X86 nor ARM */
|
||||
return;
|
||||
|
||||
/*
|
||||
* Extra flags are now returned in the ECX register when one calls
|
||||
* the CPUID instruction. Their meaning is explained in table 3-5, but
|
||||
* DMI doesn't support this yet.
|
||||
*/
|
||||
eax = DWORD(p);
|
||||
edx = DWORD(p + 4);
|
||||
switch (sig)
|
||||
@ -1200,10 +1261,18 @@ static const char *dmi_processor_upgrade(u8 code)
|
||||
"Socket LGA1150",
|
||||
"Socket BGA1168",
|
||||
"Socket BGA1234",
|
||||
"Socket BGA1364" /* 0x30 */
|
||||
"Socket BGA1364",
|
||||
"Socket AM4",
|
||||
"Socket LGA1151",
|
||||
"Socket BGA1356",
|
||||
"Socket BGA1440",
|
||||
"Socket BGA1515",
|
||||
"Socket LGA3647-1",
|
||||
"Socket SP3",
|
||||
"Socket SP3r2" /* 0x38 */
|
||||
};
|
||||
|
||||
if (code >= 0x01 && code <= 0x30)
|
||||
if (code >= 0x01 && code <= 0x38)
|
||||
return upgrade[code - 0x01];
|
||||
return out_of_spec;
|
||||
}
|
||||
@ -1476,6 +1545,21 @@ static void dmi_cache_size(u16 code)
|
||||
printf(" %u kB", code);
|
||||
}
|
||||
|
||||
static void dmi_cache_size_2(u32 code)
|
||||
{
|
||||
if (code & 0x80000000)
|
||||
{
|
||||
code &= 0x7FFFFFFFLU;
|
||||
/* Use a more convenient unit for large cache size */
|
||||
if (code >= 0x8000)
|
||||
printf(" %u MB", code >> 4);
|
||||
else
|
||||
printf(" %u kB", code << 6);
|
||||
}
|
||||
else
|
||||
printf(" %u kB", code);
|
||||
}
|
||||
|
||||
static void dmi_cache_types(u16 code, const char *sep)
|
||||
{
|
||||
/* 7.8.2 */
|
||||
@ -1712,7 +1796,10 @@ static const char *dmi_slot_type(u8 code)
|
||||
"MXM 3.0 Type A",
|
||||
"MXM 3.0 Type B",
|
||||
"PCI Express 2 SFF-8639",
|
||||
"PCI Express 3 SFF-8639" /* 0x20 */
|
||||
"PCI Express 3 SFF-8639",
|
||||
"PCI Express Mini 52-pin with bottom-side keep-outs",
|
||||
"PCI Express Mini 52-pin without bottom-side keep-outs",
|
||||
"PCI Express Mini 76-pin" /* 0x23 */
|
||||
};
|
||||
static const char *type_0xA0[] = {
|
||||
"PC-98/C20", /* 0xA0 */
|
||||
@ -1744,7 +1831,7 @@ static const char *dmi_slot_type(u8 code)
|
||||
* function dmi_slot_id below needs updating too.
|
||||
*/
|
||||
|
||||
if (code >= 0x01 && code <= 0x20)
|
||||
if (code >= 0x01 && code <= 0x23)
|
||||
return type[code - 0x01];
|
||||
if (code >= 0xA0 && code <= 0xB6)
|
||||
return type_0xA0[code - 0xA0];
|
||||
@ -1826,6 +1913,9 @@ static void dmi_slot_id(u8 code1, u8 code2, u8 type, const char *prefix)
|
||||
case 0x13: /* AGP */
|
||||
case 0x1F: /* PCI Express 2 */
|
||||
case 0x20: /* PCI Express 3 */
|
||||
case 0x21: /* PCI Express Mini */
|
||||
case 0x22: /* PCI Express Mini */
|
||||
case 0x23: /* PCI Express Mini */
|
||||
case 0xA5: /* PCI Express */
|
||||
case 0xA6: /* PCI Express */
|
||||
case 0xA7: /* PCI Express */
|
||||
@ -2274,10 +2364,13 @@ static void dmi_memory_device_extended_size(u32 code)
|
||||
{
|
||||
code &= 0x7FFFFFFFUL;
|
||||
|
||||
/* Use the most suitable unit depending on size */
|
||||
/*
|
||||
* Use the greatest unit for which the exact value can be displayed
|
||||
* as an integer without rounding
|
||||
*/
|
||||
if (code & 0x3FFUL)
|
||||
printf(" %lu MB", (unsigned long)code);
|
||||
else if (code & 0xFFFFFUL)
|
||||
else if (code & 0xFFC00UL)
|
||||
printf(" %lu GB", (unsigned long)code >> 10);
|
||||
else
|
||||
printf(" %lu TB", (unsigned long)code >> 20);
|
||||
@ -2389,7 +2482,7 @@ static void dmi_memory_device_type_detail(u16 code)
|
||||
"LRDIMM" /* 15 */
|
||||
};
|
||||
|
||||
if ((code & 0x7FFE) == 0)
|
||||
if ((code & 0xFFFE) == 0)
|
||||
printf(" None");
|
||||
else
|
||||
{
|
||||
@ -2406,7 +2499,7 @@ static void dmi_memory_device_speed(u16 code)
|
||||
if (code == 0)
|
||||
printf(" Unknown");
|
||||
else
|
||||
printf(" %u MHz", code);
|
||||
printf(" %u MT/s", code);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -2946,7 +3039,7 @@ static void dmi_64bit_memory_error_address(u64 code)
|
||||
* first 5 characters of the device name to be trimmed. It's easy to
|
||||
* check and fix, so do it, but warn.
|
||||
*/
|
||||
static void dmi_fixup_type_34(struct dmi_header *h)
|
||||
static void dmi_fixup_type_34(struct dmi_header *h, int display)
|
||||
{
|
||||
u8 *p = h->data;
|
||||
|
||||
@ -2954,7 +3047,10 @@ static void dmi_fixup_type_34(struct dmi_header *h)
|
||||
if (h->length == 0x10
|
||||
&& is_printable(p + 0x0B, 0x10 - 0x0B))
|
||||
{
|
||||
printf("Invalid entry length (%u). Fixed up to %u.\n", 0x10, 0x0B);
|
||||
if (!(opt.flags & FLAG_QUIET) && display)
|
||||
fprintf(stderr,
|
||||
"Invalid entry length (%u). Fixed up to %u.\n",
|
||||
0x10, 0x0B);
|
||||
h->length = 0x0B;
|
||||
}
|
||||
}
|
||||
@ -3222,6 +3318,57 @@ static const char *dmi_management_controller_host_type(u8 code)
|
||||
return out_of_spec;
|
||||
}
|
||||
|
||||
/*
|
||||
* 7.44 TPM Device (Type 43)
|
||||
*/
|
||||
|
||||
static void dmi_tpm_vendor_id(const u8 *p)
|
||||
{
|
||||
char vendor_id[5];
|
||||
int i;
|
||||
|
||||
/* ASCII filtering */
|
||||
for (i = 0; i < 4 && p[i] != 0; i++)
|
||||
{
|
||||
if (p[i] < 32 || p[i] >= 127)
|
||||
vendor_id[i] = '.';
|
||||
else
|
||||
vendor_id[i] = p[i];
|
||||
}
|
||||
|
||||
/* Terminate the string */
|
||||
vendor_id[i] = '\0';
|
||||
|
||||
printf(" %s", vendor_id);
|
||||
}
|
||||
|
||||
static void dmi_tpm_characteristics(u64 code, const char *prefix)
|
||||
{
|
||||
/* 7.1.1 */
|
||||
static const char *characteristics[] = {
|
||||
"TPM Device characteristics not supported", /* 2 */
|
||||
"Family configurable via firmware update",
|
||||
"Family configurable via platform software support",
|
||||
"Family configurable via OEM proprietary mechanism" /* 5 */
|
||||
};
|
||||
int i;
|
||||
|
||||
/*
|
||||
* This isn't very clear what this bit is supposed to mean
|
||||
*/
|
||||
if (code.l & (1 << 2))
|
||||
{
|
||||
printf("%s%s\n",
|
||||
prefix, characteristics[0]);
|
||||
return;
|
||||
}
|
||||
|
||||
for (i = 3; i <= 5; i++)
|
||||
if (code.l & (1 << i))
|
||||
printf("%s%s\n",
|
||||
prefix, characteristics[i - 2]);
|
||||
}
|
||||
|
||||
/*
|
||||
* Main
|
||||
*/
|
||||
@ -3257,8 +3404,9 @@ static void dmi_decode(const struct dmi_header *h, u16 ver)
|
||||
dmi_bios_runtime_size((0x10000 - WORD(data + 0x06)) << 4);
|
||||
printf("\n");
|
||||
}
|
||||
printf("\tROM Size: %u kB\n",
|
||||
(data[0x09] + 1) << 6);
|
||||
printf("\tROM Size:");
|
||||
dmi_bios_rom_size(data[0x09], h->length < 0x1A ? 16 : WORD(data + 0x18));
|
||||
printf("\n");
|
||||
printf("\tCharacteristics:\n");
|
||||
dmi_bios_characteristics(QWORD(data + 0x0A), "\t\t");
|
||||
if (h->length < 0x13) break;
|
||||
@ -3382,7 +3530,7 @@ static void dmi_decode(const struct dmi_header *h, u16 ver)
|
||||
dmi_processor_family(h, ver));
|
||||
printf("\tManufacturer: %s\n",
|
||||
dmi_string(h, data[0x07]));
|
||||
dmi_processor_id(data[0x06], data + 0x08, dmi_string(h, data[0x10]), "\t");
|
||||
dmi_processor_id(h, "\t");
|
||||
printf("\tVersion: %s\n",
|
||||
dmi_string(h, data[0x10]));
|
||||
printf("\tVoltage:");
|
||||
@ -3509,10 +3657,16 @@ static void dmi_decode(const struct dmi_header *h, u16 ver)
|
||||
printf("\tLocation: %s\n",
|
||||
dmi_cache_location((WORD(data + 0x05) >> 5) & 0x0003));
|
||||
printf("\tInstalled Size:");
|
||||
dmi_cache_size(WORD(data + 0x09));
|
||||
if (h->length >= 0x1B)
|
||||
dmi_cache_size_2(DWORD(data + 0x17));
|
||||
else
|
||||
dmi_cache_size(WORD(data + 0x09));
|
||||
printf("\n");
|
||||
printf("\tMaximum Size:");
|
||||
dmi_cache_size(WORD(data + 0x07));
|
||||
if (h->length >= 0x17)
|
||||
dmi_cache_size_2(DWORD(data + 0x13));
|
||||
else
|
||||
dmi_cache_size(WORD(data + 0x07));
|
||||
printf("\n");
|
||||
printf("\tSupported SRAM Types:");
|
||||
dmi_cache_types(WORD(data + 0x0B), "\n\t\t");
|
||||
@ -4234,7 +4388,7 @@ static void dmi_decode(const struct dmi_header *h, u16 ver)
|
||||
}
|
||||
if (data[0x11] != 0x00)
|
||||
{
|
||||
printf("\tInterrupt Number: %x\n",
|
||||
printf("\tInterrupt Number: %u\n",
|
||||
data[0x11]);
|
||||
}
|
||||
break;
|
||||
@ -4331,6 +4485,43 @@ static void dmi_decode(const struct dmi_header *h, u16 ver)
|
||||
}
|
||||
break;
|
||||
|
||||
case 43: /* 7.44 TPM Device */
|
||||
printf("TPM Device\n");
|
||||
if (h->length < 0x1B) break;
|
||||
printf("\tVendor ID:");
|
||||
dmi_tpm_vendor_id(data + 0x04);
|
||||
printf("\n");
|
||||
printf("\tSpecification Version: %d.%d", data[0x08], data[0x09]);
|
||||
switch (data[0x08])
|
||||
{
|
||||
case 0x01:
|
||||
/*
|
||||
* We skip the first 2 bytes, which are
|
||||
* redundant with the above, and uncoded
|
||||
* in a silly way.
|
||||
*/
|
||||
printf("\tFirmware Revision: %u.%u\n",
|
||||
data[0x0C], data[0x0D]);
|
||||
break;
|
||||
case 0x02:
|
||||
printf("\tFirmware Revision: %u.%u\n",
|
||||
DWORD(data + 0x0A) >> 16,
|
||||
DWORD(data + 0x0A) && 0xFF);
|
||||
/*
|
||||
* We skip the next 4 bytes, as their
|
||||
* format is not standardized and their
|
||||
* usefulness seems limited anyway.
|
||||
*/
|
||||
break;
|
||||
}
|
||||
printf("\tDescription: %s", dmi_string(h, data[0x12]));
|
||||
printf("\tCharacteristics:\n");
|
||||
dmi_tpm_characteristics(QWORD(data + 0x13), "\t\t");
|
||||
if (h->length < 0x1F) break;
|
||||
printf("\tOEM-specific Information: 0x%08X\n",
|
||||
DWORD(data + 0x1B));
|
||||
break;
|
||||
|
||||
case 126: /* 7.44 Inactive */
|
||||
printf("Inactive\n");
|
||||
break;
|
||||
@ -4364,6 +4555,21 @@ static void dmi_table_string(const struct dmi_header *h, const u8 *data, u16 ver
|
||||
int key;
|
||||
u8 offset = opt.string->offset;
|
||||
|
||||
if (opt.string->type == 11) /* OEM strings */
|
||||
{
|
||||
if (h->length < 5 || offset > data[4])
|
||||
{
|
||||
fprintf(stderr, "No OEM string number %u\n", offset);
|
||||
return;
|
||||
}
|
||||
|
||||
if (offset)
|
||||
printf("%s\n", dmi_string(h, offset));
|
||||
else
|
||||
printf("%u\n", data[4]); /* count */
|
||||
return;
|
||||
}
|
||||
|
||||
if (offset >= h->length)
|
||||
return;
|
||||
|
||||
@ -4422,9 +4628,14 @@ static void dmi_table_decode(u8 *buf, u32 len, u16 num, u16 ver, u32 flags)
|
||||
*/
|
||||
if (h.length < 4)
|
||||
{
|
||||
printf("Invalid entry length (%u). DMI table is "
|
||||
"broken! Stop.\n\n", (unsigned int)h.length);
|
||||
opt.flags |= FLAG_QUIET;
|
||||
if (!(opt.flags & FLAG_QUIET))
|
||||
{
|
||||
fprintf(stderr,
|
||||
"Invalid entry length (%u). DMI table "
|
||||
"is broken! Stop.\n\n",
|
||||
(unsigned int)h.length);
|
||||
opt.flags |= FLAG_QUIET;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
@ -4443,7 +4654,7 @@ static void dmi_table_decode(u8 *buf, u32 len, u16 num, u16 ver, u32 flags)
|
||||
|
||||
/* Fixup a common mistake */
|
||||
if (h.type == 34)
|
||||
dmi_fixup_type_34(&h);
|
||||
dmi_fixup_type_34(&h, display);
|
||||
|
||||
/* look for the next handle */
|
||||
next = data + h.length;
|
||||
@ -4485,26 +4696,28 @@ static void dmi_table_decode(u8 *buf, u32 len, u16 num, u16 ver, u32 flags)
|
||||
if (!(opt.flags & FLAG_QUIET))
|
||||
{
|
||||
if (num && i != num)
|
||||
printf("Wrong DMI structures count: %d announced, "
|
||||
fprintf(stderr, "Wrong DMI structures count: %d announced, "
|
||||
"only %d decoded.\n", num, i);
|
||||
if ((unsigned long)(data - buf) > len
|
||||
|| (num && (unsigned long)(data - buf) < len))
|
||||
printf("Wrong DMI structures length: %u bytes "
|
||||
fprintf(stderr, "Wrong DMI structures length: %u bytes "
|
||||
"announced, structures occupy %lu bytes.\n",
|
||||
len, (unsigned long)(data - buf));
|
||||
}
|
||||
}
|
||||
|
||||
static void dmi_table(off_t base, u32 len, u16 num, u16 ver, const char *devmem,
|
||||
static void dmi_table(off_t base, u32 len, u16 num, u32 ver, const char *devmem,
|
||||
u32 flags)
|
||||
{
|
||||
u8 *buf;
|
||||
|
||||
if (ver > SUPPORTED_SMBIOS_VER && !(opt.flags & FLAG_QUIET))
|
||||
{
|
||||
printf("# SMBIOS implementations newer than version %u.%u are not\n"
|
||||
printf("# SMBIOS implementations newer than version %u.%u.%u are not\n"
|
||||
"# fully supported by this version of dmidecode.\n",
|
||||
SUPPORTED_SMBIOS_VER >> 8, SUPPORTED_SMBIOS_VER & 0xFF);
|
||||
SUPPORTED_SMBIOS_VER >> 16,
|
||||
(SUPPORTED_SMBIOS_VER >> 8) & 0xFF,
|
||||
SUPPORTED_SMBIOS_VER & 0xFF);
|
||||
}
|
||||
|
||||
if (!(opt.flags & FLAG_QUIET))
|
||||
@ -4521,29 +4734,45 @@ static void dmi_table(off_t base, u32 len, u16 num, u16 ver, const char *devmem,
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
/*
|
||||
* When we are reading the DMI table from sysfs, we want to print
|
||||
* the address of the table (done above), but the offset of the
|
||||
* data in the file is 0. When reading from /dev/mem, the offset
|
||||
* in the file is the address.
|
||||
*/
|
||||
if (flags & FLAG_NO_FILE_OFFSET)
|
||||
base = 0;
|
||||
|
||||
if ((buf = mem_chunk(base, len, devmem)) == NULL)
|
||||
if ((flags & FLAG_NO_FILE_OFFSET) || (opt.flags & FLAG_FROM_DUMP))
|
||||
{
|
||||
fprintf(stderr, "Table is unreachable, sorry."
|
||||
/*
|
||||
* When reading from sysfs or from a dump file, the file may be
|
||||
* shorter than announced. For SMBIOS v3 this is expcted, as we
|
||||
* only know the maximum table size, not the actual table size.
|
||||
* For older implementations (and for SMBIOS v3 too), this
|
||||
* would be the result of the kernel truncating the table on
|
||||
* parse error.
|
||||
*/
|
||||
size_t size = len;
|
||||
buf = read_file(flags & FLAG_NO_FILE_OFFSET ? 0 : base,
|
||||
&size, devmem);
|
||||
if (!(opt.flags & FLAG_QUIET) && num && size != (size_t)len)
|
||||
{
|
||||
fprintf(stderr, "Wrong DMI structures length: %u bytes "
|
||||
"announced, only %lu bytes available.\n",
|
||||
len, (unsigned long)size);
|
||||
}
|
||||
len = size;
|
||||
}
|
||||
else
|
||||
buf = mem_chunk(base, len, devmem);
|
||||
|
||||
if (buf == NULL)
|
||||
{
|
||||
fprintf(stderr, "Failed to read table, sorry.\n");
|
||||
#ifndef USE_MMAP
|
||||
" Try compiling dmidecode with -DUSE_MMAP."
|
||||
if (!(flags & FLAG_NO_FILE_OFFSET))
|
||||
fprintf(stderr,
|
||||
"Try compiling dmidecode with -DUSE_MMAP.\n");
|
||||
#endif
|
||||
"\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (opt.flags & FLAG_DUMP_BIN)
|
||||
dmi_table_dump(buf, len);
|
||||
else
|
||||
dmi_table_decode(buf, len, num, ver, flags);
|
||||
dmi_table_decode(buf, len, num, ver >> 8, flags);
|
||||
|
||||
free(buf);
|
||||
}
|
||||
@ -4580,13 +4809,13 @@ static void overwrite_smbios3_address(u8 *buf)
|
||||
|
||||
static int smbios3_decode(u8 *buf, const char *devmem, u32 flags)
|
||||
{
|
||||
u16 ver;
|
||||
u32 ver;
|
||||
u64 offset;
|
||||
|
||||
if (!checksum(buf, buf[0x06]))
|
||||
return 0;
|
||||
|
||||
ver = (buf[0x07] << 8) + buf[0x08];
|
||||
ver = (buf[0x07] << 16) + (buf[0x08] << 8) + buf[0x09];
|
||||
if (!(opt.flags & FLAG_QUIET))
|
||||
printf("SMBIOS %u.%u.%u present.\n",
|
||||
buf[0x07], buf[0x08], buf[0x09]);
|
||||
@ -4599,7 +4828,7 @@ static int smbios3_decode(u8 *buf, const char *devmem, u32 flags)
|
||||
}
|
||||
|
||||
dmi_table(((off_t)offset.h << 32) | offset.l,
|
||||
WORD(buf + 0x0C), 0, ver, devmem, flags | FLAG_STOP_AT_EOT);
|
||||
DWORD(buf + 0x0C), 0, ver, devmem, flags | FLAG_STOP_AT_EOT);
|
||||
|
||||
if (opt.flags & FLAG_DUMP_BIN)
|
||||
{
|
||||
@ -4633,14 +4862,16 @@ static int smbios_decode(u8 *buf, const char *devmem, u32 flags)
|
||||
case 0x021F:
|
||||
case 0x0221:
|
||||
if (!(opt.flags & FLAG_QUIET))
|
||||
printf("SMBIOS version fixup (2.%d -> 2.%d).\n",
|
||||
ver & 0xFF, 3);
|
||||
fprintf(stderr,
|
||||
"SMBIOS version fixup (2.%d -> 2.%d).\n",
|
||||
ver & 0xFF, 3);
|
||||
ver = 0x0203;
|
||||
break;
|
||||
case 0x0233:
|
||||
if (!(opt.flags & FLAG_QUIET))
|
||||
printf("SMBIOS version fixup (2.%d -> 2.%d).\n",
|
||||
51, 6);
|
||||
fprintf(stderr,
|
||||
"SMBIOS version fixup (2.%d -> 2.%d).\n",
|
||||
51, 6);
|
||||
ver = 0x0206;
|
||||
break;
|
||||
}
|
||||
@ -4649,7 +4880,7 @@ static int smbios_decode(u8 *buf, const char *devmem, u32 flags)
|
||||
ver >> 8, ver & 0xFF);
|
||||
|
||||
dmi_table(DWORD(buf + 0x18), WORD(buf + 0x16), WORD(buf + 0x1C),
|
||||
ver, devmem, flags);
|
||||
ver << 8, devmem, flags);
|
||||
|
||||
if (opt.flags & FLAG_DUMP_BIN)
|
||||
{
|
||||
@ -4677,7 +4908,8 @@ static int legacy_decode(u8 *buf, const char *devmem, u32 flags)
|
||||
buf[0x0E] >> 4, buf[0x0E] & 0x0F);
|
||||
|
||||
dmi_table(DWORD(buf + 0x08), WORD(buf + 0x06), WORD(buf + 0x0C),
|
||||
((buf[0x0E] & 0xF0) << 4) + (buf[0x0E] & 0x0F), devmem, flags);
|
||||
((buf[0x0E] & 0xF0) << 12) + ((buf[0x0E] & 0x0F) << 8),
|
||||
devmem, flags);
|
||||
|
||||
if (opt.flags & FLAG_DUMP_BIN)
|
||||
{
|
||||
@ -4748,9 +4980,17 @@ int main(int argc, char * const argv[])
|
||||
int ret = 0; /* Returned value */
|
||||
int found = 0;
|
||||
off_t fp;
|
||||
size_t size;
|
||||
int efi;
|
||||
u8 *buf;
|
||||
|
||||
/*
|
||||
* We don't want stdout and stderr to be mixed up if both are
|
||||
* redirected to the same file.
|
||||
*/
|
||||
setlinebuf(stdout);
|
||||
setlinebuf(stderr);
|
||||
|
||||
if (sizeof(u8) != 1 || sizeof(u16) != 2 || sizeof(u32) != 4 || '\0' != 0)
|
||||
{
|
||||
fprintf(stderr, "%s: compiler incompatibility\n", argv[0]);
|
||||
@ -4817,22 +5057,23 @@ int main(int argc, char * const argv[])
|
||||
* contain one of several types of entry points, so read enough for
|
||||
* the largest one, then determine what type it contains.
|
||||
*/
|
||||
size = 0x20;
|
||||
if (!(opt.flags & FLAG_NO_SYSFS)
|
||||
&& (buf = read_file(0x20, SYS_ENTRY_FILE)) != NULL)
|
||||
&& (buf = read_file(0, &size, SYS_ENTRY_FILE)) != NULL)
|
||||
{
|
||||
if (!(opt.flags & FLAG_QUIET))
|
||||
printf("Getting SMBIOS data from sysfs.\n");
|
||||
if (memcmp(buf, "_SM3_", 5) == 0)
|
||||
if (size >= 24 && memcmp(buf, "_SM3_", 5) == 0)
|
||||
{
|
||||
if (smbios3_decode(buf, SYS_TABLE_FILE, FLAG_NO_FILE_OFFSET))
|
||||
found++;
|
||||
}
|
||||
else if (memcmp(buf, "_SM_", 4) == 0)
|
||||
else if (size >= 31 && memcmp(buf, "_SM_", 4) == 0)
|
||||
{
|
||||
if (smbios_decode(buf, SYS_TABLE_FILE, FLAG_NO_FILE_OFFSET))
|
||||
found++;
|
||||
}
|
||||
else if (memcmp(buf, "_DMI_", 5) == 0)
|
||||
else if (size >= 15 && memcmp(buf, "_DMI_", 5) == 0)
|
||||
{
|
||||
if (legacy_decode(buf, SYS_TABLE_FILE, FLAG_NO_FILE_OFFSET))
|
||||
found++;
|
||||
@ -4864,8 +5105,16 @@ int main(int argc, char * const argv[])
|
||||
goto exit_free;
|
||||
}
|
||||
|
||||
if (smbios_decode(buf, opt.devmem, 0))
|
||||
found++;
|
||||
if (memcmp(buf, "_SM3_", 5) == 0)
|
||||
{
|
||||
if (smbios3_decode(buf, opt.devmem, 0))
|
||||
found++;
|
||||
}
|
||||
else if (memcmp(buf, "_SM_", 4) == 0)
|
||||
{
|
||||
if (smbios_decode(buf, opt.devmem, 0))
|
||||
found++;
|
||||
}
|
||||
goto done;
|
||||
|
||||
memory_scan:
|
||||
@ -4878,28 +5127,37 @@ memory_scan:
|
||||
goto exit_free;
|
||||
}
|
||||
|
||||
for (fp = 0; fp <= 0xFFF0; fp += 16)
|
||||
/* Look for a 64-bit entry point first */
|
||||
for (fp = 0; fp <= 0xFFE0; fp += 16)
|
||||
{
|
||||
if (memcmp(buf + fp, "_SM3_", 5) == 0 && fp <= 0xFFE0)
|
||||
if (memcmp(buf + fp, "_SM3_", 5) == 0)
|
||||
{
|
||||
if (smbios3_decode(buf + fp, opt.devmem, 0))
|
||||
{
|
||||
found++;
|
||||
fp += 16;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
else if (memcmp(buf + fp, "_SM_", 4) == 0 && fp <= 0xFFE0)
|
||||
}
|
||||
|
||||
/* If none found, look for a 32-bit entry point */
|
||||
for (fp = 0; fp <= 0xFFF0; fp += 16)
|
||||
{
|
||||
if (memcmp(buf + fp, "_SM_", 4) == 0 && fp <= 0xFFE0)
|
||||
{
|
||||
if (smbios_decode(buf + fp, opt.devmem, 0))
|
||||
{
|
||||
found++;
|
||||
fp += 16;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
else if (memcmp(buf + fp, "_DMI_", 5) == 0)
|
||||
{
|
||||
if (legacy_decode(buf + fp, opt.devmem, 0))
|
||||
{
|
||||
found++;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
41
dmiopt.c
41
dmiopt.c
@ -20,6 +20,7 @@
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <strings.h>
|
||||
#include <stdlib.h>
|
||||
#include <getopt.h>
|
||||
@ -171,6 +172,10 @@ static const struct string_keyword opt_string_keyword[] = {
|
||||
{ "processor-frequency", 4, 0x16 }, /* dmi_processor_frequency() */
|
||||
};
|
||||
|
||||
/* This is a template, 3rd field is set at runtime. */
|
||||
static struct string_keyword opt_oem_string_keyword =
|
||||
{ NULL, 11, 0x00 };
|
||||
|
||||
static void print_opt_string_list(void)
|
||||
{
|
||||
unsigned int i;
|
||||
@ -206,6 +211,34 @@ static int parse_opt_string(const char *arg)
|
||||
return -1;
|
||||
}
|
||||
|
||||
static int parse_opt_oem_string(const char *arg)
|
||||
{
|
||||
unsigned long val;
|
||||
char *next;
|
||||
|
||||
if (opt.string)
|
||||
{
|
||||
fprintf(stderr, "Only one string can be specified\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Return the number of OEM strings */
|
||||
if (strcmp(arg, "count") == 0)
|
||||
goto done;
|
||||
|
||||
val = strtoul(arg, &next, 10);
|
||||
if (next == arg || val == 0x00 || val > 0xff)
|
||||
{
|
||||
fprintf(stderr, "Invalid OEM string number: %s\n", arg);
|
||||
return -1;
|
||||
}
|
||||
|
||||
opt_oem_string_keyword.offset = val;
|
||||
done:
|
||||
opt.string = &opt_oem_string_keyword;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Command line options handling
|
||||
@ -225,6 +258,7 @@ int parse_command_line(int argc, char * const argv[])
|
||||
{ "dump", no_argument, NULL, 'u' },
|
||||
{ "dump-bin", required_argument, NULL, 'B' },
|
||||
{ "from-dump", required_argument, NULL, 'F' },
|
||||
{ "oem-string", required_argument, NULL, 'O' },
|
||||
{ "no-sysfs", no_argument, NULL, 'S' },
|
||||
{ "version", no_argument, NULL, 'V' },
|
||||
{ NULL, 0, NULL, 0 }
|
||||
@ -255,6 +289,11 @@ int parse_command_line(int argc, char * const argv[])
|
||||
return -1;
|
||||
opt.flags |= FLAG_QUIET;
|
||||
break;
|
||||
case 'O':
|
||||
if (parse_opt_oem_string(optarg) < 0)
|
||||
return -1;
|
||||
opt.flags |= FLAG_QUIET;
|
||||
break;
|
||||
case 't':
|
||||
opt.type = parse_opt_type(opt.type, optarg);
|
||||
if (opt.type == NULL)
|
||||
@ -314,6 +353,8 @@ void print_help(void)
|
||||
" -u, --dump Do not decode the entries\n"
|
||||
" --dump-bin FILE Dump the DMI data to a binary file\n"
|
||||
" --from-dump FILE Read the DMI data from a binary file\n"
|
||||
" --no-sysfs Do not attempt to read DMI data from sysfs files\n"
|
||||
" --oem-string N Only display the value of the given OEM string\n"
|
||||
" -V, --version Display the version and exit\n";
|
||||
|
||||
printf("%s", help);
|
||||
|
||||
@ -134,13 +134,18 @@ Read the DMI data from a binary file previously generated using
|
||||
Do not attempt to read DMI data from sysfs files. This is mainly useful for
|
||||
debugging.
|
||||
.TP
|
||||
.BR " " " " "--oem-string N"
|
||||
Only display the value of the \s-1OEM\s0 string number \fBN\fR. The first
|
||||
\s-1OEM\s0 string has number 1. With special value "count", return the
|
||||
number of OEM strings instead.
|
||||
.TP
|
||||
.BR "-h" ", " "--help"
|
||||
Display usage information and exit
|
||||
.TP
|
||||
.BR "-V" ", " "--version"
|
||||
Display the version and exit
|
||||
.P
|
||||
Options --string, --type and --dump-bin
|
||||
Options --string, --type, --dump-bin and --oem-string
|
||||
determine the output format and are mutually exclusive.
|
||||
.P
|
||||
Please note in case of
|
||||
|
||||
69
util.c
69
util.c
@ -2,7 +2,7 @@
|
||||
* Common "util" functions
|
||||
* This file is part of the dmidecode project.
|
||||
*
|
||||
* Copyright (C) 2002-2015 Jean Delvare <jdelvare@suse.de>
|
||||
* Copyright (C) 2002-2017 Jean Delvare <jdelvare@suse.de>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
@ -89,15 +89,16 @@ int checksum(const u8 *buf, size_t len)
|
||||
}
|
||||
|
||||
/*
|
||||
* Reads all of file, up to max_len bytes.
|
||||
* Reads all of file from given offset, up to max_len bytes.
|
||||
* A buffer of max_len bytes is allocated by this function, and
|
||||
* needs to be freed by the caller.
|
||||
* This provides a similar usage model to mem_chunk()
|
||||
*
|
||||
* Returns pointer to buffer of max_len bytes, or NULL on error
|
||||
* Returns pointer to buffer of max_len bytes, or NULL on error, and
|
||||
* sets max_len to the length actually read.
|
||||
*
|
||||
*/
|
||||
void *read_file(size_t max_len, const char *filename)
|
||||
void *read_file(off_t base, size_t *max_len, const char *filename)
|
||||
{
|
||||
int fd;
|
||||
size_t r2 = 0;
|
||||
@ -112,26 +113,34 @@ void *read_file(size_t max_len, const char *filename)
|
||||
{
|
||||
if (errno != ENOENT)
|
||||
perror(filename);
|
||||
return(NULL);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if ((p = malloc(max_len)) == NULL)
|
||||
if (lseek(fd, base, SEEK_SET) == -1)
|
||||
{
|
||||
fprintf(stderr, "%s: ", filename);
|
||||
perror("lseek");
|
||||
p = NULL;
|
||||
goto out;
|
||||
}
|
||||
|
||||
if ((p = malloc(*max_len)) == NULL)
|
||||
{
|
||||
perror("malloc");
|
||||
return NULL;
|
||||
goto out;
|
||||
}
|
||||
|
||||
do
|
||||
{
|
||||
r = read(fd, p + r2, max_len - r2);
|
||||
r = read(fd, p + r2, *max_len - r2);
|
||||
if (r == -1)
|
||||
{
|
||||
if (errno != EINTR)
|
||||
{
|
||||
close(fd);
|
||||
perror(filename);
|
||||
free(p);
|
||||
return NULL;
|
||||
p = NULL;
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
else
|
||||
@ -139,7 +148,10 @@ void *read_file(size_t max_len, const char *filename)
|
||||
}
|
||||
while (r != 0);
|
||||
|
||||
*max_len = r2;
|
||||
out:
|
||||
close(fd);
|
||||
|
||||
return p;
|
||||
}
|
||||
|
||||
@ -152,6 +164,7 @@ void *mem_chunk(off_t base, size_t len, const char *devmem)
|
||||
void *p;
|
||||
int fd;
|
||||
#ifdef USE_MMAP
|
||||
struct stat statbuf;
|
||||
off_t mmoffset;
|
||||
void *mmp;
|
||||
#endif
|
||||
@ -165,10 +178,28 @@ void *mem_chunk(off_t base, size_t len, const char *devmem)
|
||||
if ((p = malloc(len)) == NULL)
|
||||
{
|
||||
perror("malloc");
|
||||
return NULL;
|
||||
goto out;
|
||||
}
|
||||
|
||||
#ifdef USE_MMAP
|
||||
if (fstat(fd, &statbuf) == -1)
|
||||
{
|
||||
fprintf(stderr, "%s: ", devmem);
|
||||
perror("stat");
|
||||
goto err_free;
|
||||
}
|
||||
|
||||
/*
|
||||
* mmap() will fail with SIGBUS if trying to map beyond the end of
|
||||
* the file.
|
||||
*/
|
||||
if (S_ISREG(statbuf.st_mode) && base + (off_t)len > statbuf.st_size)
|
||||
{
|
||||
fprintf(stderr, "mmap: Can't map beyond end of file %s\n",
|
||||
devmem);
|
||||
goto err_free;
|
||||
}
|
||||
|
||||
#ifdef _SC_PAGESIZE
|
||||
mmoffset = base % sysconf(_SC_PAGESIZE);
|
||||
#else
|
||||
@ -199,19 +230,17 @@ try_read:
|
||||
{
|
||||
fprintf(stderr, "%s: ", devmem);
|
||||
perror("lseek");
|
||||
free(p);
|
||||
return NULL;
|
||||
goto err_free;
|
||||
}
|
||||
|
||||
if (myread(fd, p, len, devmem) == -1)
|
||||
{
|
||||
free(p);
|
||||
return NULL;
|
||||
}
|
||||
if (myread(fd, p, len, devmem) == 0)
|
||||
goto out;
|
||||
|
||||
err_free:
|
||||
free(p);
|
||||
p = NULL;
|
||||
|
||||
#ifdef USE_MMAP
|
||||
out:
|
||||
#endif
|
||||
if (close(fd) == -1)
|
||||
perror(devmem);
|
||||
|
||||
|
||||
4
util.h
4
util.h
@ -1,7 +1,7 @@
|
||||
/*
|
||||
* This file is part of the dmidecode project.
|
||||
*
|
||||
* Copyright (C) 2003-2015 Jean Delvare <jdelvare@suse.de>
|
||||
* Copyright (C) 2003-2017 Jean Delvare <jdelvare@suse.de>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
@ -25,7 +25,7 @@
|
||||
#define ARRAY_SIZE(x) (sizeof(x)/sizeof((x)[0]))
|
||||
|
||||
int checksum(const u8 *buf, size_t len);
|
||||
void *read_file(size_t len, const char *filename);
|
||||
void *read_file(off_t base, size_t *len, const char *filename);
|
||||
void *mem_chunk(off_t base, size_t len, const char *devmem);
|
||||
int write_dump(size_t base, size_t len, const void *data, const char *dumpfile, int add);
|
||||
u64 u64_range(u64 start, u64 end);
|
||||
|
||||
Loading…
Reference in New Issue
Block a user