1 | /*␊ |
2 | * A very simple SMBIOS Table decoder, part of the Chameleon Boot Loader Project␊ |
3 | *␊ |
4 | * Copyright 2010 by Islam M. Ahmed Zaid. All rights reserved.␊ |
5 | *␊ |
6 | */␊ |
7 | ␊ |
8 | #include "libsaio.h"␊ |
9 | #include "smbios.h"␊ |
10 | // Bungo:␊ |
11 | #include "boot.h"␊ |
12 | #include "bootstruct.h"␊ |
13 | ␊ |
14 | #ifndef DEBUG_SMBIOS␊ |
15 | #define DEBUG_SMBIOS 0␊ |
16 | #endif␊ |
17 | ␊ |
18 | #if DEBUG_SMBIOS␊ |
19 | #define DBG(x...)␉printf(x)␊ |
20 | #else␊ |
21 | #define DBG(x...)␉msglog(x)␊ |
22 | #endif␊ |
23 | ␊ |
24 | extern char *getSMBStringForField(SMBStructHeader *structHeader, uint8_t field);␊ |
25 | // Bungo:␊ |
26 | #define NotSpecifiedStr "Not Specified" // no string␊ |
27 | #define OutOfSpecStr "<OUT OF SPEC>" // value out of smbios spec. range␊ |
28 | #define PrivateStr "** PRIVATE **" // masking private data␊ |
29 | #define neverMask false␊ |
30 | ␊ |
31 | static bool privateData = true;␊ |
32 | static SMBByte minorVersion; // SMBIOS rev. minor␊ |
33 | static SMBByte majorVersion; // SMBIOS rev. major␊ |
34 | static SMBByte bcdRevisionLo; // DMI rev. minor␊ |
35 | static SMBByte bcdRevisionHi; // DMI rev. major␊ |
36 | ␊ |
37 | /*====␊ |
38 | 7.2.2␊ |
39 | ===*/␊ |
40 | static const char *SMBWakeUpTypes[] = // Bungo: strings for wake-up type (Table Type 1 - System Information)␊ |
41 | {␊ |
42 | ␉"Reserved", /* 00h */␊ |
43 | ␉"Other", /* 01h */␊ |
44 | ␉"Unknown", /* 02h */␊ |
45 | ␉"APM Timer", /* 03h */␊ |
46 | ␉"Modem Ring", /* 04h */␊ |
47 | ␉"LAN Remote", /* 05h */␊ |
48 | ␉"Power Switch", /* 06h */␊ |
49 | ␉"PCI PME#", /* 07h */␊ |
50 | ␉"AC Power Restored" /* 08h */␊ |
51 | };␊ |
52 | ␊ |
53 | /*====␊ |
54 | 7.3.2␊ |
55 | ===*/␊ |
56 | static const char *SMBBaseBoardTypes[] = // Bungo: strings for base board type (Table Type 2 - Base Board Information)␊ |
57 | {␊ |
58 | ␉"Unknown", /* 01h */␊ |
59 | ␉"Other", /* 02h */␊ |
60 | ␉"Server Blade", /* 03h */␊ |
61 | ␉"Connectivity Switch", /* 04h */␊ |
62 | ␉"System Management Module", /* 05h */␊ |
63 | ␉"Processor Module", /* 06h */␊ |
64 | ␉"I/O Module", /* 07h */␊ |
65 | ␉"Memory Module", /* 08h */␊ |
66 | ␉"Daughter Board", /* 09h */␊ |
67 | ␉"Motherboard", /* 0Ah */␊ |
68 | ␉"Processor+Memory Module", /* 0Bh */␊ |
69 | ␉"Processor+I/O Module", /* 0Ch */␊ |
70 | ␉"Interconnect Board" /* 0Dh */␊ |
71 | };␊ |
72 | ␊ |
73 | /*===␊ |
74 | 7.4.1␊ |
75 | ===*/␊ |
76 | static const char *SMBChassisTypes[] = // Bungo: strings for chassis type (Table Type 3 - Chassis Information)␊ |
77 | {␊ |
78 | ␉"Other", /* 01h */␊ |
79 | ␉"Unknown", /* 02h */␊ |
80 | ␉"Desktop", /* 03h */␊ |
81 | ␉"Low Profile Desktop", /* 04h */␊ |
82 | ␉"Pizza Box", /* 05h */␊ |
83 | ␉"Mini Tower", /* 06h */␊ |
84 | ␉"Tower", /* 07h */␊ |
85 | ␉"Portable", /* 08h */␊ |
86 | ␉"Laptop", /* 09h */␊ |
87 | ␉"Notebook", /* 0Ah */␊ |
88 | ␉"Hand Held", /* 0Bh */␊ |
89 | ␉"Docking Station", /* 0Ch */␊ |
90 | ␉"All in One", /* 0Dh */␊ |
91 | ␉"Sub Notebook", /* 0Eh */␊ |
92 | ␉"Space-saving", /* 0Fh */␊ |
93 | ␉"Lunch Box", /* 10h */␊ |
94 | ␉"Main Server Chassis", /* 11h */␊ |
95 | ␉"Expansion Chassis", /* 12h */␊ |
96 | ␉"SubChassis", /* 13h */␊ |
97 | ␉"Bus Expansion Chassis", /* 14h */␊ |
98 | ␉"Peripheral Chassis", /* 15h */␊ |
99 | ␉"RAID Chassis", /* 16h */␊ |
100 | ␉"Rack Mount Chassis", /* 17h */␊ |
101 | ␉"Sealed-case PC", /* 18h */␊ |
102 | ␉"Multi-system Chassis", /* 19h */␊ |
103 | ␉"Compact PCI", /* 1Ah */␊ |
104 | ␉"Advanced TCA", /* 1Bh */␊ |
105 | ␉"Blade", /* 1Ch */ // An SMBIOS implementation for a Blade would contain a Type 3 Chassis structure␊ |
106 | ␉"Blade Enclosing"␉/* 1Dh */ // A Blade Enclosure is a specialized chassis that contains a set of Blades.␊ |
107 | };␊ |
108 | ␊ |
109 | /*====␊ |
110 | 7.5.1␊ |
111 | ===*/␊ |
112 | static const char *SMBProcessorTypes[] = // Bungo: strings for processor type (Table Type 4 - Processor Information)␊ |
113 | {␊ |
114 | ␉"Other", /* 01h */␊ |
115 | ␉"Unknown", /* 02h */␊ |
116 | ␉"Central Processor", /* 03h */␊ |
117 | ␉"Math Processor", /* 04h */␊ |
118 | ␉"DSP Processor", /* 05h */␊ |
119 | ␉"Video Processor" /* 06h */␊ |
120 | };␊ |
121 | ␊ |
122 | /*====␊ |
123 | 7.5.5␊ |
124 | ===*/␊ |
125 | static const char *SMBProcessorUpgrades[] = // ErmaC: strings for processor upgrade (Table Type 4 - Processor Information)␊ |
126 | {␊ |
127 | ␉"Other", /* 01h */␊ |
128 | "Unknown",␊ |
129 | "Daughter Board",␊ |
130 | "ZIF Socket",␊ |
131 | "Replaceable Piggy Back",␊ |
132 | "None",␊ |
133 | "LIF Socket",␊ |
134 | "Slot 1",␊ |
135 | "Slot 2",␊ |
136 | "370-pin Socket",␊ |
137 | "Slot A",␊ |
138 | "Slot M",␊ |
139 | "Socket 423",␊ |
140 | "Socket A (Socket 462)",␊ |
141 | "Socket 478",␊ |
142 | "Socket 754",␊ |
143 | "Socket 940",␊ |
144 | "Socket 939",␊ |
145 | "Socket mPGA604",␊ |
146 | "Socket LGA771",␊ |
147 | "Socket LGA775",␊ |
148 | "Socket S1",␊ |
149 | "Socket AM2",␊ |
150 | "Socket F (1207)",␊ |
151 | "Socket LGA1366",␊ |
152 | "Socket G34",␊ |
153 | "Socket AM3",␊ |
154 | "Socket C32",␊ |
155 | "Socket LGA1156",␊ |
156 | "Socket LGA1567",␊ |
157 | "Socket PGA988A",␊ |
158 | "Socket BGA1288",␊ |
159 | "Socket rPGA988B",␊ |
160 | "Socket BGA1023",␊ |
161 | "Socket BGA1224",␊ |
162 | "Socket BGA1155",␊ |
163 | "Socket LGA1356",␊ |
164 | "Socket LGA2011",␊ |
165 | "Socket FS1",␊ |
166 | "Socket FS2",␊ |
167 | "Socket FM1",␊ |
168 | "Socket FM2",␊ |
169 | "Socket LGA2011-3",␊ |
170 | "Socket LGA1356-3" /* 2Ch */␊ |
171 | };␊ |
172 | ␊ |
173 | /*=====␊ |
174 | 7.18.2␊ |
175 | ====*/␊ |
176 | static const char *␊ |
177 | SMBMemoryDeviceTypes[] =␊ |
178 | {␊ |
179 | ␉"RAM", /* 00h Undefined */␊ |
180 | ␉"RAM", /* 01h Other */␊ |
181 | ␉"RAM", /* 02h Unknown */␊ |
182 | ␉"DRAM", /* 03h DRAM */␊ |
183 | ␉"EDRAM", /* 04h EDRAM */␊ |
184 | ␉"VRAM", /* 05h VRAM */␊ |
185 | ␉"SRAM", /* 06h SRAM */␊ |
186 | ␉"RAM", /* 07h RAM */␊ |
187 | ␉"ROM", /* 08h ROM */␊ |
188 | ␉"FLASH", /* 09h FLASH */␊ |
189 | ␉"EEPROM", /* 0Ah EEPROM */␊ |
190 | ␉"FEPROM", /* 0Bh FEPROM */␊ |
191 | ␉"EPROM", /* 0Ch EPROM */␊ |
192 | ␉"CDRAM", /* 0Dh CDRAM */␊ |
193 | ␉"3DRAM", /* 0Eh 3DRAM */␊ |
194 | ␉"SDRAM", /* 0Fh SDRAM */␊ |
195 | ␉"SGRAM", /* 10h SGRAM */␊ |
196 | ␉"RDRAM", /* 11h RDRAM */␊ |
197 | ␉"DDR SDRAM", /* 12h DDR */␊ |
198 | ␉"DDR2 SDRAM", /* 13h DDR2 */␊ |
199 | ␉"DDR2 FB-DIMM", /* 14h DDR2 FB-DIMM */␊ |
200 | ␉"RAM", /* 15h unused */␊ |
201 | ␉"RAM", /* 16h unused */␊ |
202 | ␉"RAM", /* 17h unused */␊ |
203 | ␉"DDR3", /* 18h DDR3, chosen in [5776134] */␊ |
204 | ␉"FBD2" /* 19h FBD2 */␊ |
205 | };␊ |
206 | ␊ |
207 | static const int kSMBMemoryDeviceTypeCount = sizeof(SMBMemoryDeviceTypes) /␊ |
208 | sizeof(SMBMemoryDeviceTypes[0]);␊ |
209 | ␊ |
210 | // Bungo: fixes random string readout if null in smbios to "Not Specified" as dmidecode displays␊ |
211 | char *SMBStringForField(SMBStructHeader *structHeader, uint8_t field, const bool mask)␊ |
212 | {␊ |
213 | ␉char *str = NULL;␊ |
214 | ␉str = getSMBStringForField(structHeader, field);␊ |
215 | ␉if (!field) {␊ |
216 | ␉␉str = NotSpecifiedStr;␊ |
217 | ␉}␊ |
218 | else if (mask) {␊ |
219 | ␉␉str = PrivateStr;␊ |
220 | ␉}␊ |
221 | ␊ |
222 | return str;␊ |
223 | };␊ |
224 | ␊ |
225 | void printHeader(SMBStructHeader *structHeader)␊ |
226 | {␊ |
227 | DBG("Type: %d, Length: %d, Handle: 0x%04x\n", structHeader->type, structHeader->length, structHeader->handle);␊ |
228 | }␊ |
229 | ␊ |
230 | //-------------------------------------------------------------------------------------------------------------------------␊ |
231 | // BIOS Information (Type 0)␊ |
232 | //-------------------------------------------------------------------------------------------------------------------------␊ |
233 | void decodeBIOSInformation(SMBStructHeader *structHeader)␊ |
234 | {␊ |
235 | printHeader(structHeader);␊ |
236 | ␉DBG("BIOS Information:\n");␊ |
237 | ␉DBG("\tVendor: %s\n", SMBStringForField(structHeader, ((SMBBIOSInformation *)structHeader)->vendor, neverMask));␊ |
238 | ␉DBG("\tVersion: %s\n", SMBStringForField(structHeader, ((SMBBIOSInformation *)structHeader)->version, neverMask));␊ |
239 | ␉// Address Segment␊ |
240 | ␉DBG("\tRelease Date: %s\n", SMBStringForField(structHeader, ((SMBBIOSInformation *)structHeader)->releaseDate, neverMask));␊ |
241 | ␉DBG("\tBIOS Revision: %d.%d\n", ((SMBBIOSInformation *)structHeader)->releaseMajor, ((SMBBIOSInformation *)structHeader)->releaseMinor);␊ |
242 | ␉// ROM Size␊ |
243 | ␉// DBG("\tSupported BIOS functions: (0x%llX) %s\n", ((SMBBIOSInformation *)structHeader)->characteristics, SMBBIOSInfoChar0[((SMBBIOSInformation *)structHeader)->characteristics]);␊ |
244 | ␉// Firmware Major Release␊ |
245 | ␉// Firmware Minor Release␊ |
246 | ␉// SMBByte characteristicsExt1;␊ |
247 | ␉// SMBByte characteristicsExt2;␊ |
248 | ␉DBG("\n");␊ |
249 | }␊ |
250 | ␊ |
251 | //-------------------------------------------------------------------------------------------------------------------------␊ |
252 | // System Information (Type 1)␊ |
253 | //-------------------------------------------------------------------------------------------------------------------------␊ |
254 | void decodeSystemInformation(SMBStructHeader *structHeader)␊ |
255 | {␊ |
256 | printHeader(structHeader);␊ |
257 | ␉DBG("System Information:\n");␊ |
258 | ␉DBG("\tManufacturer: %s\n", SMBStringForField(structHeader, ((SMBSystemInformation *)structHeader)->manufacturer, neverMask));␊ |
259 | ␉DBG("\tProduct Name: %s\n", SMBStringForField(structHeader, ((SMBSystemInformation *)structHeader)->productName, neverMask));␊ |
260 | ␉DBG("\tVersion: %s\n", SMBStringForField(structHeader, ((SMBSystemInformation *)structHeader)->version, neverMask));␊ |
261 | ␉DBG("\tSerial Number: %s\n", SMBStringForField(structHeader, ((SMBSystemInformation *)structHeader)->serialNumber, privateData));␊ |
262 | ␉uint8_t *uuid = ((SMBSystemInformation *)structHeader)->uuid;␊ |
263 | ␉if (privateData) {␊ |
264 | ␉␉DBG("\tUUID: %s\n", PrivateStr);␊ |
265 | ␉} else {␊ |
266 | ␉␉DBG("\tUUID: %02X%02X%02X%02X-%02X%02X-%02X%02X-%02x%02X-%02X%02X%02X%02X%02X%02X\n",␊ |
267 | ␉␉␉uuid[0], uuid[1], uuid[2], uuid[3], uuid[4], uuid[5], uuid[6], uuid[7],␊ |
268 | ␉␉␉uuid[8], uuid[9], uuid[10], uuid[11], uuid[12], uuid[13], uuid[14], uuid[15]);␊ |
269 | ␉ }␊ |
270 | ␉if (((SMBSystemInformation *)structHeader)->wakeupReason > 8) {␊ |
271 | ␉␉DBG("\tWake-up Type: %s\n", OutOfSpecStr);␊ |
272 | ␉} else {␊ |
273 | ␉␉DBG("\tWake-up Type: %s\n", SMBWakeUpTypes[((SMBSystemInformation *)structHeader)->wakeupReason]);␊ |
274 | ␉ }␊ |
275 | ␉DBG("\tSKU Number: %s\n", SMBStringForField(structHeader, ((SMBSystemInformation *)structHeader)->skuNumber, neverMask)); // System SKU#␊ |
276 | ␉DBG("\tFamily: %s\n", SMBStringForField(structHeader, ((SMBSystemInformation *)structHeader)->family, neverMask));␊ |
277 | ␉DBG("\n");␊ |
278 | }␊ |
279 | ␊ |
280 | //-------------------------------------------------------------------------------------------------------------------------␊ |
281 | // Base Board (or Module) Information (Type 2)␊ |
282 | //-------------------------------------------------------------------------------------------------------------------------␊ |
283 | void decodeBaseBoard(SMBStructHeader *structHeader)␊ |
284 | {␊ |
285 | printHeader(structHeader);␊ |
286 | ␉DBG("Base Board Information:\n");␊ |
287 | ␉DBG("\tManufacturer: %s\n", SMBStringForField(structHeader, ((SMBBaseBoard *)structHeader)->manufacturer, neverMask));␊ |
288 | ␉DBG("\tProduct Name: %s\n", SMBStringForField(structHeader, ((SMBBaseBoard *)structHeader)->product, neverMask));␊ |
289 | ␉DBG("\tVersion: %s\n", SMBStringForField(structHeader, ((SMBBaseBoard *)structHeader)->version, neverMask));␊ |
290 | ␉DBG("\tSerial Number: %s\n", SMBStringForField(structHeader, ((SMBBaseBoard *)structHeader)->serialNumber, privateData));␊ |
291 | ␉DBG("\tAsset Tag: %s\n", SMBStringForField(structHeader, ((SMBBaseBoard *)structHeader)->assetTag, neverMask));␊ |
292 | ␉// Feature Flags (BYTE)␊ |
293 | ␉DBG("\tLocation In Chassis: %s\n", SMBStringForField(structHeader, ((SMBBaseBoard *)structHeader)->locationInChassis, neverMask)); // Part Component␊ |
294 | ␉// Chassis Handle (WORD)␊ |
295 | ␉if ((((SMBBaseBoard *)structHeader)->boardType < kSMBBaseBoardUnknown) || (((SMBBaseBoard *)structHeader)->boardType > kSMBBaseBoardInterconnect)) {␊ |
296 | ␉␉DBG("\tType: %s\n", OutOfSpecStr);␊ |
297 | ␉} else {␊ |
298 | ␉␉DBG("\tType: %s\n", SMBBaseBoardTypes[(((SMBBaseBoard *)structHeader)->boardType - 1)]);␊ |
299 | ␉ }␊ |
300 | ␉// Number of Contained Object Handles (n) (BYTE)␊ |
301 | ␉// Contained Object Handles n(WORDs)␊ |
302 | ␉DBG("\n");␊ |
303 | }␊ |
304 | ␊ |
305 | //-------------------------------------------------------------------------------------------------------------------------␊ |
306 | // System Enclosure or Chassis (Type 3)␊ |
307 | //-------------------------------------------------------------------------------------------------------------------------␊ |
308 | void decodeSystemEnclosure(SMBStructHeader *structHeader)␊ |
309 | {␊ |
310 | printHeader(structHeader);␊ |
311 | ␉DBG("Chassis Information:\n");␊ |
312 | ␉DBG("\tManufacturer: %s\n", SMBStringForField(structHeader, ((SMBSystemEnclosure *)structHeader)->manufacturer, neverMask));␊ |
313 | ␉if ((((SMBSystemEnclosure *)structHeader)->chassisType < kSMBchassisOther) || (((SMBSystemEnclosure *)structHeader)->chassisType > kSMBchassisBladeEnclosing)) {␊ |
314 | ␉␉DBG("\tType: %s\n", OutOfSpecStr);␊ |
315 | ␉} else {␊ |
316 | ␉␉DBG("\tType: %s\n", SMBChassisTypes[(((SMBSystemEnclosure *)structHeader)->chassisType - 1)]);␊ |
317 | ␉ }␊ |
318 | ␉DBG("\tVersion: %s\n", SMBStringForField(structHeader, ((SMBSystemEnclosure *)structHeader)->version, neverMask));␊ |
319 | ␉DBG("\tSerial Number: %s\n", SMBStringForField(structHeader, ((SMBSystemEnclosure *)structHeader)->serialNumber, privateData));␊ |
320 | ␉DBG("\tAsset Tag: %s\n", SMBStringForField(structHeader, ((SMBSystemEnclosure *)structHeader)->assetTag, neverMask));␊ |
321 | ␉// Boot-up State:␊ |
322 | ␉// Power Supply State␊ |
323 | ␉// Thermal State␊ |
324 | ␉// Security Status:␊ |
325 | ␉// OEM Information:␊ |
326 | ␉// Height;␊ |
327 | ␉// Cords;␊ |
328 | ␉// ElementsCount;␊ |
329 | ␉// ElementLen;␊ |
330 | ␉// Elements[1]; // open array of ElementsCount*ElementLen BYTEs␊ |
331 | ␉DBG("\n");␊ |
332 | }␊ |
333 | ␊ |
334 | //-------------------------------------------------------------------------------------------------------------------------␊ |
335 | // Processor Information (Type 4)␊ |
336 | //-------------------------------------------------------------------------------------------------------------------------␊ |
337 | void decodeProcessorInformation(SMBStructHeader *structHeader)␊ |
338 | {␊ |
339 | printHeader(structHeader);␊ |
340 | ␉DBG("Processor Information:\n");␊ |
341 | ␉DBG("\tSocket Designation: %s\n", SMBStringForField(structHeader, ((SMBProcessorInformation *)structHeader)->socketDesignation, neverMask));␊ |
342 | if ((((SMBProcessorInformation *)structHeader)->processorType < kSMBprocessorTypeOther) || (((SMBProcessorInformation *)structHeader)->processorType > kSMBprocessorTypeGPU)) {␊ |
343 | ␉␉DBG("\tType: %s\n", OutOfSpecStr);␊ |
344 | ␉} else {␊ |
345 | ␉␉DBG("\tType: %s\n", SMBProcessorTypes[((SMBProcessorInformation *)structHeader)->processorType - 1]);␊ |
346 | ␉ }␊ |
347 | ␉DBG("\tFamily: 0x%X\n", ((SMBProcessorInformation *)structHeader)->processorFamily);␊ |
348 | ␉DBG("\tManufacturer: %s\n", SMBStringForField(structHeader, ((SMBProcessorInformation *)structHeader)->manufacturer, neverMask));␊ |
349 | ␉DBG("\tID: 0x%llX\n", ((SMBProcessorInformation *)structHeader)->processorID);␊ |
350 | ␉DBG("\tProcessor Version: %s\n", SMBStringForField(structHeader, ((SMBProcessorInformation *)structHeader)->processorVersion, neverMask));␊ |
351 | //␉DBG("\tVoltage: 0.%xV\n", ((SMBProcessorInformation *)structHeader)->voltage);␊ |
352 | ␉DBG("\tExternal Clock: %dMHz\n", ((SMBProcessorInformation *)structHeader)->externalClock);␊ |
353 | ␉DBG("\tMaximal Clock: %dMHz\n", ((SMBProcessorInformation *)structHeader)->maximumClock);␊ |
354 | ␉DBG("\tCurrent Clock: %dMHz\n", ((SMBProcessorInformation *)structHeader)->currentClock);␊ |
355 | if ((((SMBProcessorInformation *)structHeader)->processorUpgrade < 1) || (((SMBProcessorInformation *)structHeader)->processorUpgrade > 0x2C)) {␊ |
356 | ␉␉DBG("\tUpgrade: %s\n", OutOfSpecStr);␊ |
357 | ␉} else {␊ |
358 | ␉␉DBG("\tUpgrade: %s\n", SMBProcessorUpgrades[((SMBProcessorInformation *)structHeader)->processorUpgrade - 1]);␊ |
359 | ␉ }␊ |
360 | ␉DBG("\tSerial Number: %s\n", SMBStringForField(structHeader, ((SMBProcessorInformation *)structHeader)->serialNumber, privateData));␊ |
361 | ␉DBG("\tAsset Tag: %s\n", SMBStringForField(structHeader, ((SMBProcessorInformation *)structHeader)->assetTag, neverMask));␊ |
362 | ␉DBG("\tPart Number: %s\n", SMBStringForField(structHeader, ((SMBProcessorInformation *)structHeader)->partNumber, neverMask));␊ |
363 | //␉DBG("\tProcessor Family 2: %d\n", ((SMBProcessorInformation *)structHeader)->processorFamily2);␊ |
364 | ␉DBG("\n");␊ |
365 | }␊ |
366 | ␊ |
367 | //-------------------------------------------------------------------------------------------------------------------------␊ |
368 | // OEM Strings (Type 11)␊ |
369 | //-------------------------------------------------------------------------------------------------------------------------␊ |
370 | void decodeSMBOEMStrings(SMBStructHeader *structHeader)␊ |
371 | {␊ |
372 | char *stringPtr = (char *)structHeader + structHeader->length;␊ |
373 | printHeader(structHeader);␊ |
374 | ␉DBG("OEM Strings:\n");␊ |
375 | SMBByte i;␊ |
376 | for (i = 1; i <= ((SMBOEMStrings *)structHeader)->count; i++) {␊ |
377 | DBG("\tString %d: %s\n", i, stringPtr);␊ |
378 | stringPtr = stringPtr + strlen(stringPtr) + 1;␊ |
379 | }␊ |
380 | ␉DBG("\n");␊ |
381 | }␊ |
382 | ␊ |
383 | //-------------------------------------------------------------------------------------------------------------------------␊ |
384 | // MemoryDevice (Type 17)␊ |
385 | //-------------------------------------------------------------------------------------------------------------------------␊ |
386 | void decodeMemoryDevice(SMBStructHeader *structHeader)␊ |
387 | {␊ |
388 | printHeader(structHeader);␊ |
389 | ␉DBG("Memory Device:\n");␊ |
390 | ␉DBG("\tDevice Locator: %s\n", SMBStringForField(structHeader, ((SMBMemoryDevice *)structHeader)->deviceLocator, neverMask));␊ |
391 | ␉DBG("\tBank Locator: %s\n", SMBStringForField(structHeader, ((SMBMemoryDevice *)structHeader)->bankLocator, neverMask));␊ |
392 | ␉DBG("\tMemory Type: %s\n", SMBMemoryDeviceTypes[((SMBMemoryDevice *)structHeader)->memoryType]);␊ |
393 | ␉DBG("\tSpeed: %d MHz\n", ((SMBMemoryDevice *)structHeader)->memorySpeed);␊ |
394 | ␉DBG("\tError Handle: %x\n", ((SMBMemoryDevice *)structHeader)->errorHandle);␊ |
395 | ␉DBG("\tManufacturer: %s\n", SMBStringForField(structHeader, ((SMBMemoryDevice *)structHeader)->manufacturer, neverMask));␊ |
396 | ␉DBG("\tSerial Number: %s\n", SMBStringForField(structHeader, ((SMBMemoryDevice *)structHeader)->serialNumber, privateData));␊ |
397 | ␉DBG("\tAsset Tag: %s\n", SMBStringForField(structHeader, ((SMBMemoryDevice *)structHeader)->assetTag, neverMask));␊ |
398 | ␉DBG("\tPart Number: %s\n", SMBStringForField(structHeader, ((SMBMemoryDevice *)structHeader)->partNumber, neverMask));␊ |
399 | ␉DBG("\n");␊ |
400 | }␊ |
401 | ␊ |
402 | //-------------------------------------------------------------------------------------------------------------------------␊ |
403 | // Apple Specific␊ |
404 | //-------------------------------------------------------------------------------------------------------------------------␊ |
405 | void decodeOemProcessorType(SMBStructHeader *structHeader)␊ |
406 | {␊ |
407 | printHeader(structHeader);␊ |
408 | DBG("Apple specific Processor Type:\n");␊ |
409 | ␉DBG("\tcpu=0x%x\n", ((SMBOemProcessorType *)structHeader)->ProcessorType);␊ |
410 | ␉DBG("\n");␊ |
411 | }␊ |
412 | ␊ |
413 | void decodeOemProcessorBusSpeed(SMBStructHeader *structHeader)␊ |
414 | {␊ |
415 | printHeader(structHeader);␊ |
416 | DBG("Apple specific Processor Interconnect Speed:\n");␊ |
417 | DBG("\tqpi=%d MT/s\n", ((SMBOemProcessorBusSpeed *)structHeader)->ProcessorBusSpeed);␊ |
418 | ␉DBG("\n");␊ |
419 | }␊ |
420 | //-------------------------------------------------------------------------------------------------------------------------␊ |
421 | ␊ |
422 | ␊ |
423 | void decodeSMBIOSTable(SMBEntryPoint *eps)␊ |
424 | {␊ |
425 | ␉uint8_t *ptr = (uint8_t *)eps->dmi.tableAddress;␊ |
426 | ␉SMBStructHeader *structHeader = (SMBStructHeader *)ptr;␊ |
427 | ␊ |
428 | ␉minorVersion = eps->minorVersion;␊ |
429 | ␉majorVersion = eps->majorVersion;␊ |
430 | ␉bcdRevisionHi = eps->dmi.bcdRevision >> 4;␊ |
431 | ␉bcdRevisionLo = eps->dmi.bcdRevision & 0x0F;␊ |
432 | ␊ |
433 | ␉getBoolForKey(kPrivateData, &privateData, &bootInfo->chameleonConfig); // Bungo: chek if mask some data␊ |
434 | ␊ |
435 | DBG("\n");␊ |
436 | ␉DBG("SMBIOS rev.: %d.%d, DMI rev.: %d.%d\n", majorVersion, minorVersion, bcdRevisionHi, bcdRevisionLo);␊ |
437 | DBG("\n");␊ |
438 | ␉for (;((eps->dmi.tableAddress + eps->dmi.tableLength) > ((uint32_t)(uint8_t *)structHeader + sizeof(SMBStructHeader)));)␊ |
439 | ␉{␊ |
440 | ␉␉switch (structHeader->type)␊ |
441 | ␉␉{␊ |
442 | ␉␉␉case kSMBTypeBIOSInformation: // Type 0␊ |
443 | ␉␉␉␉decodeBIOSInformation(structHeader);␊ |
444 | ␉␉␉␉break;␊ |
445 | ␊ |
446 | ␉␉␉case kSMBTypeSystemInformation: // Type 1␊ |
447 | ␉␉␉␉decodeSystemInformation(structHeader);␊ |
448 | ␉␉␉␉break;␊ |
449 | ␊ |
450 | ␉␉␉case kSMBTypeBaseBoard: // Type 2␊ |
451 | ␉␉␉␉decodeBaseBoard(structHeader);␊ |
452 | ␉␉␉␉break;␊ |
453 | ␊ |
454 | ␉␉␉case kSMBTypeSystemEnclosure: // Type 3␊ |
455 | ␉␉␉␉decodeSystemEnclosure(structHeader);␊ |
456 | ␉␉␉␉break;␊ |
457 | ␊ |
458 | ␉␉␉case kSMBTypeProcessorInformation: // Type 4␊ |
459 | ␉␉␉␉decodeProcessorInformation(structHeader);␊ |
460 | ␉␉␉␉break;␊ |
461 | ␊ |
462 | ␉␉␉//case 6: // kSMBTypeMemoryModule: // Type 6␊ |
463 | ␉␉␉//␉decodeMemoryModule(structHeader);␊ |
464 | ␉␉␉//␉break;␊ |
465 | ␊ |
466 | ␉␉␉case kSMBOEMStrings: // Type 11␊ |
467 | ␉␉␉␉decodeSMBOEMStrings(structHeader);␊ |
468 | ␉␉␉␉break;␊ |
469 | ␊ |
470 | ␉␉␉case kSMBTypeMemoryDevice: // Type 17␊ |
471 | ␉␉␉␉decodeMemoryDevice(structHeader);␊ |
472 | ␉␉␉␉break;␊ |
473 | ␊ |
474 | ␉␉␉// kSMBTypeMemoryArrayMappedAddress: // Type 19␊ |
475 | ␊ |
476 | ␉␉␉/* Skip all Apple Specific Structures */␊ |
477 | ␉␉␉// case kSMBTypeFirmwareVolume: // Type 128␊ |
478 | ␉␉␉// case kSMBTypeMemorySPD: // Type 130␊ |
479 | ␉␉␉// ␉break;␊ |
480 | ␊ |
481 | ␉␉␉case kSMBTypeOemProcessorType: // Type 131␊ |
482 | ␉␉␉␉decodeOemProcessorType(structHeader);␊ |
483 | ␉␉␉␉break;␊ |
484 | ␊ |
485 | ␉␉␉case kSMBTypeOemProcessorBusSpeed: // Type 132␊ |
486 | ␉␉␉␉decodeOemProcessorBusSpeed(structHeader);␊ |
487 | ␉␉␉␉break;␊ |
488 | ␊ |
489 | ␉␉␉//kSMBTypeOemPlatformFeature: // Type 133␊ |
490 | ␊ |
491 | ␉␉␉case kSMBTypeEndOfTable: // Type 127␊ |
492 | DBG("Type: %d, Length: %d, Handle: 0x%04x\n", structHeader->type, structHeader->length, structHeader->handle);␊ |
493 | DBG("End of Table\n");␊ |
494 | ␉␉␉␉break;␊ |
495 | ␊ |
496 | ␉␉␉default:␊ |
497 | ␉␉␉␉break;␊ |
498 | ␉␉}␊ |
499 | ␊ |
500 | ␉␉ptr = (uint8_t *)((uint32_t)structHeader + structHeader->length);␊ |
501 | ␉␉for (; ((uint16_t *)ptr)[0] != 0; ptr++);␊ |
502 | ␊ |
503 | ␉␉if (((uint16_t *)ptr)[0] == 0) {␊ |
504 | ␉␉␉ptr += 2;␊ |
505 | ␉␉}␊ |
506 | ␊ |
507 | ␉␉structHeader = (SMBStructHeader *)ptr;␊ |
508 | ␉}␊ |
509 | ␉DBG("\n");␊ |
510 | }␊ |
511 | ␊ |
512 | |