]> git.proxmox.com Git - mirror_edk2.git/blob - OvmfPkg/Library/SmbiosVersionLib/DetectSmbiosVersionLib.c
UefiCpuPkg: Move AsmRelocateApLoopStart from Mpfuncs.nasm to AmdSev.nasm
[mirror_edk2.git] / OvmfPkg / Library / SmbiosVersionLib / DetectSmbiosVersionLib.c
1 /** @file
2
3 A hook-in library for MdeModulePkg/Universal/SmbiosDxe, in order to set
4 gEfiMdeModulePkgTokenSpaceGuid.PcdSmbiosVersion (and possibly other PCDs)
5 just before SmbiosDxe consumes them.
6
7 Copyright (C) 2013, 2015, Red Hat, Inc.
8 Copyright (c) 2008 - 2012, Intel Corporation. All rights reserved.<BR>
9
10 SPDX-License-Identifier: BSD-2-Clause-Patent
11
12 **/
13
14 #include <IndustryStandard/SmBios.h>
15
16 #include <Base.h>
17 #include <Library/BaseMemoryLib.h>
18 #include <Library/DebugLib.h>
19 #include <Library/PcdLib.h>
20 #include <Library/QemuFwCfgLib.h>
21
22 typedef union {
23 SMBIOS_TABLE_ENTRY_POINT V2;
24 SMBIOS_TABLE_3_0_ENTRY_POINT V3;
25 } QEMU_SMBIOS_ANCHOR;
26
27 RETURN_STATUS
28 EFIAPI
29 DetectSmbiosVersion (
30 VOID
31 )
32 {
33 FIRMWARE_CONFIG_ITEM Anchor, Tables;
34 UINTN AnchorSize, TablesSize;
35 QEMU_SMBIOS_ANCHOR QemuAnchor;
36 UINT16 SmbiosVersion;
37 RETURN_STATUS PcdStatus;
38
39 if (PcdGetBool (PcdQemuSmbiosValidated)) {
40 //
41 // Some other module, linked against this library, has already performed
42 // the task at hand. This should never happen, but it's easy to handle;
43 // just exit early.
44 //
45 return RETURN_SUCCESS;
46 }
47
48 if (RETURN_ERROR (
49 QemuFwCfgFindFile (
50 "etc/smbios/smbios-anchor",
51 &Anchor,
52 &AnchorSize
53 )
54 ) ||
55 RETURN_ERROR (
56 QemuFwCfgFindFile (
57 "etc/smbios/smbios-tables",
58 &Tables,
59 &TablesSize
60 )
61 ) ||
62 (TablesSize == 0))
63 {
64 return RETURN_SUCCESS;
65 }
66
67 QemuFwCfgSelectItem (Anchor);
68
69 switch (AnchorSize) {
70 case sizeof QemuAnchor.V2:
71 QemuFwCfgReadBytes (AnchorSize, &QemuAnchor);
72
73 if ((QemuAnchor.V2.MajorVersion != 2) ||
74 (QemuAnchor.V2.TableLength != TablesSize) ||
75 (CompareMem (QemuAnchor.V2.AnchorString, "_SM_", 4) != 0) ||
76 (CompareMem (QemuAnchor.V2.IntermediateAnchorString, "_DMI_", 5) != 0))
77 {
78 return RETURN_SUCCESS;
79 }
80
81 SmbiosVersion = (UINT16)(QemuAnchor.V2.MajorVersion << 8 |
82 QemuAnchor.V2.MinorVersion);
83 break;
84
85 case sizeof QemuAnchor.V3:
86 QemuFwCfgReadBytes (AnchorSize, &QemuAnchor);
87
88 if ((QemuAnchor.V3.MajorVersion != 3) ||
89 (QemuAnchor.V3.TableMaximumSize != TablesSize) ||
90 (CompareMem (QemuAnchor.V3.AnchorString, "_SM3_", 5) != 0))
91 {
92 return RETURN_SUCCESS;
93 }
94
95 SmbiosVersion = (UINT16)(QemuAnchor.V3.MajorVersion << 8 |
96 QemuAnchor.V3.MinorVersion);
97
98 DEBUG ((
99 DEBUG_INFO,
100 "%a: SMBIOS 3.x DocRev from QEMU: 0x%02x\n",
101 __FUNCTION__,
102 QemuAnchor.V3.DocRev
103 ));
104 PcdStatus = PcdSet8S (PcdSmbiosDocRev, QemuAnchor.V3.DocRev);
105 ASSERT_RETURN_ERROR (PcdStatus);
106 break;
107
108 default:
109 return RETURN_SUCCESS;
110 }
111
112 DEBUG ((
113 DEBUG_INFO,
114 "%a: SMBIOS version from QEMU: 0x%04x\n",
115 __FUNCTION__,
116 SmbiosVersion
117 ));
118 PcdStatus = PcdSet16S (PcdSmbiosVersion, SmbiosVersion);
119 ASSERT_RETURN_ERROR (PcdStatus);
120
121 //
122 // SMBIOS platform drivers can now fetch and install
123 // "etc/smbios/smbios-tables" from QEMU.
124 //
125 PcdStatus = PcdSetBoolS (PcdQemuSmbiosValidated, TRUE);
126 ASSERT_RETURN_ERROR (PcdStatus);
127 return RETURN_SUCCESS;
128 }