Chameleon

Chameleon Svn Source Tree

Root/branches/slice/trunkM/i386/libsaio/smbios.c

1/*
2 * SMBIOS Table Patcher, part of the Chameleon Boot Loader Project
3 *
4 * Copyright 2010 by Islam M. Ahmed Zaid. All rights reserved.
5 *
6 */
7
8
9#include "boot.h"
10#include "bootstruct.h"
11#include "smbios_getters.h"
12
13#ifndef DEBUG_SMBIOS
14#define DEBUG_SMBIOS 0
15#endif
16
17#if DEBUG_SMBIOS
18#define DBG(x...)printf(x)
19#else
20#define DBG(x...)msglog(x)
21#endif
22
23#define SMBPlist&bootInfo->smbiosConfig
24/* ASSUMPTION: 16KB should be enough for the whole thing */
25#define SMB_ALLOC_SIZE16384
26
27
28//-------------------------------------------------------------------------------------------------------------------------
29// SMBIOS Plist Keys
30//-------------------------------------------------------------------------------------------------------------------------
31/* BIOS Information */
32#define kSMBBIOSInformationVendorKey"SMbiosvendor"
33#define kSMBBIOSInformationVersionKey"SMbiosversion"
34#define kSMBBIOSInformationReleaseDateKey"SMbiosdate"
35
36/* System Information */
37#define kSMBSystemInformationManufacturerKey"SMmanufacturer"
38#define kSMBSystemInformationProductNameKey"SMproductname"
39#define kSMBSystemInformationVersionKey"SMsystemversion"
40#define kSMBSystemInformationSerialNumberKey"SMserial"
41#define kSMBSystemInformationFamilyKey"SMfamily"
42
43/* Base Board */
44#define kSMBBaseBoardManufacturerKey"SMboardmanufacturer"
45#define kSMBBaseBoardProductKey"SMboardproduct"
46
47/* Processor Information */
48#define kSMBProcessorInformationExternalClockKey"SMexternalclock"
49#define kSMBProcessorInformationMaximumClockKey"SMmaximalclock"
50
51/* Memory Device */
52#define kSMBMemoryDeviceDeviceLocatorKey"SMmemdevloc"
53#define kSMBMemoryDeviceBankLocatorKey"SMmembankloc"
54#define kSMBMemoryDeviceMemoryTypeKey"SMmemtype"
55#define kSMBMemoryDeviceMemorySpeedKey"SMmemspeed"
56#define kSMBMemoryDeviceManufacturerKey"SMmemmanufacturer"
57#define kSMBMemoryDeviceSerialNumberKey"SMmemserial"
58#define kSMBMemoryDevicePartNumberKey"SMmempart"
59
60/* Apple Specific */
61#define kSMBOemProcessorTypeKey"SMcputype"
62#define kSMBOemProcessorBusSpeedKey"SMbusspeed"
63
64//-------------------------------------------------------------------------------------------------------------------------
65// Default SMBIOS Data
66//-------------------------------------------------------------------------------------------------------------------------
67/* Rewrite: use a struct */
68
69#define kDefaultVendorManufacturer"Apple Inc."
70#define kDefaultBIOSReleaseDate"11/06/2009"
71#define kDefaultSerialNumber"SOMESRLNMBR"
72#define kDefaultBoardProduct"Mac-F4208DC8"
73#define kDefaultSystemVersion"1.0"
74
75// defaults for a Mac mini
76#define kDefaultMacminiFamily"Macmini"
77#define kDefaultMacmini"Macmini1,1"
78#define kDefaultMacminiBIOSVersion" MM21.88Z.009A.B00.0903051113"
79
80// defaults for a MacBook
81#define kDefaultMacBookFamily"MacBook"
82#define kDefaultMacBook"MacBook4,1"
83#define kDefaultMacBookBIOSVersion" MB41.88Z.0073.B00.0903051113"
84
85// defaults for a MacBook Pro
86#define kDefaultMacBookProFamily"MacBookPro"
87#define kDefaultMacBookPro"MacBookPro4,1"
88#define kDefaultMacBookProBIOSVersion" MBP41.88Z.0073.B00.0903051113"
89
90// defaults for an iMac
91#define kDefaultiMacFamily"iMac"
92#define kDefaultiMac"iMac8,1"
93#define kDefaultiMacBIOSVersion" IM81.88Z.00C1.B00.0903051113"
94// defaults for an iMac11,1 core i3/i5/i7
95#define kDefaultiMacNehalem"iMac11,1"
96#define kDefaultiMacNehalemBIOSVersion" IM111.88Z.0034.B00.0903051113"
97// defaults for an iMac12,1
98#define kDefaultiMacSandy"iMac12,1"
99#define kDefaultiMacSandyBIOSVersion" IM121.88Z.0047.B00.1102091756"
100
101// defaults for a Mac Pro
102#define kDefaultMacProFamily"MacPro"
103#define kDefaultMacPro"MacPro3,1"
104#define kDefaultMacProBIOSVersion" MP31.88Z.006C.B05.0903051113"
105// defaults for a Mac Pro 4,1 core i7/Xeon
106#define kDefaultMacProNehalem"MacPro4,1"
107#define kDefaultMacProNehalemBIOSVersion" MP41.88Z.0081.B04.0903051113"
108// defaults for a Mac Pro 5,1 core i7/Xeon
109#define kDefaultMacProWestmere"MacPro5,1"
110#define kDefaultMacProWestmereBIOSVersion" MP51.88Z.007F.B00.1008031144"
111#define kDefaulMacProWestmereBIOSReleaseDate"08/03/10"
112//-------------------------------------------------------------------------------------------------------------------------
113#define MAX_DMI_TABLES 96
114typedef struct DmiNumAssocTag {
115 SMBStructHeader* dmi;
116 uint8_t type;
117} DmiNumAssoc;
118
119static DmiNumAssoc DmiTablePair[MAX_DMI_TABLES];
120static int DmiTablePairCount = 0;
121static int current_pos=0;
122static bool ftTablePairInit = true; //use twice first run and after
123
124#define getFieldOffset(struct, field)((uint8_t)(uint32_t)&(((struct *)0)->field))
125
126typedef struct {
127SMBStructHeader *orig;
128SMBStructHeader *new;
129} SMBStructPtrs;
130
131struct {
132char *vendor;
133char *version;
134char *releaseDate;
135} defaultBIOSInfo;
136
137struct {
138char *manufacturer;
139char *productName;
140char *version;
141char *serialNumber;
142char *family;
143} defaultSystemInfo;
144
145struct {
146char *manufacturer;
147char *product;
148} defaultBaseBoard;
149
150
151typedef struct {
152uint8_ttype;
153SMBValueTypevalueType;
154uint8_tfieldOffset;
155char*keyString;
156bool(*getSMBValue)(returnType *);
157char**defaultValue;
158} SMBValueSetter;
159
160SMBValueSetter SMBSetters[] =
161{
162//-------------------------------------------------------------------------------------------------------------------------
163// BIOSInformation
164//-------------------------------------------------------------------------------------------------------------------------
165{kSMBTypeBIOSInformation,kSMBString,getFieldOffset(SMBBIOSInformation, vendor),kSMBBIOSInformationVendorKey,
166NULL,&defaultBIOSInfo.vendor},
167
168{kSMBTypeBIOSInformation,kSMBString,getFieldOffset(SMBBIOSInformation, version),kSMBBIOSInformationVersionKey,
169NULL,&defaultBIOSInfo.version},
170
171{kSMBTypeBIOSInformation,kSMBString,getFieldOffset(SMBBIOSInformation, releaseDate),kSMBBIOSInformationReleaseDateKey,
172NULL,&defaultBIOSInfo.releaseDate},
173
174//-------------------------------------------------------------------------------------------------------------------------
175// SystemInformation
176//-------------------------------------------------------------------------------------------------------------------------
177{kSMBTypeSystemInformation,kSMBString,getFieldOffset(SMBSystemInformation, manufacturer),kSMBSystemInformationManufacturerKey,
178NULL,&defaultSystemInfo.manufacturer},
179
180{kSMBTypeSystemInformation,kSMBString,getFieldOffset(SMBSystemInformation, productName),kSMBSystemInformationProductNameKey,
181NULL,&defaultSystemInfo.productName},
182
183{kSMBTypeSystemInformation,kSMBString,getFieldOffset(SMBSystemInformation, version),kSMBSystemInformationVersionKey,
184NULL,&defaultSystemInfo.version},
185
186{kSMBTypeSystemInformation,kSMBString,getFieldOffset(SMBSystemInformation, serialNumber),kSMBSystemInformationSerialNumberKey,
187NULL,&defaultSystemInfo.serialNumber},
188
189{kSMBTypeSystemInformation,kSMBString,getFieldOffset(SMBSystemInformation, skuNumber),NULL,
190NULL,NULL},
191
192{kSMBTypeSystemInformation,kSMBString,getFieldOffset(SMBSystemInformation, family),kSMBSystemInformationFamilyKey,
193NULL,&defaultSystemInfo.family},
194
195
196//-------------------------------------------------------------------------------------------------------------------------
197// BaseBoard
198//-------------------------------------------------------------------------------------------------------------------------
199{kSMBTypeBaseBoard,kSMBString,getFieldOffset(SMBBaseBoard, manufacturer),kSMBBaseBoardManufacturerKey,
200NULL,&defaultBaseBoard.manufacturer},
201
202{kSMBTypeBaseBoard,kSMBString,getFieldOffset(SMBBaseBoard, product),kSMBBaseBoardProductKey,
203NULL,&defaultBaseBoard.product},
204
205{kSMBTypeBaseBoard,kSMBString,getFieldOffset(SMBBaseBoard, version),NULL,NULL,NULL},
206
207{kSMBTypeBaseBoard,kSMBString,getFieldOffset(SMBBaseBoard, serialNumber),NULL,NULL,NULL},
208
209{kSMBTypeBaseBoard,kSMBString,getFieldOffset(SMBBaseBoard, assetTagNumber),NULL,NULL,NULL},
210
211{kSMBTypeBaseBoard,kSMBString,getFieldOffset(SMBBaseBoard, locationInChassis),NULL,NULL,NULL},
212
213
214//-------------------------------------------------------------------------------------------------------------------------
215// ProcessorInformation
216//-------------------------------------------------------------------------------------------------------------------------
217{kSMBTypeProcessorInformation,kSMBString,getFieldOffset(SMBProcessorInformation, socketDesignation),NULL,NULL,NULL},
218
219{kSMBTypeProcessorInformation,kSMBString,getFieldOffset(SMBProcessorInformation, manufacturer),NULL,NULL,NULL},
220
221{kSMBTypeProcessorInformation,kSMBString,getFieldOffset(SMBProcessorInformation, processorVersion),NULL,NULL,NULL},
222
223{kSMBTypeProcessorInformation,kSMBWord,getFieldOffset(SMBProcessorInformation, externalClock),kSMBProcessorInformationExternalClockKey,
224getProcessorInformationExternalClock,NULL},
225
226{kSMBTypeProcessorInformation,kSMBWord,getFieldOffset(SMBProcessorInformation, maximumClock),kSMBProcessorInformationMaximumClockKey,
227getProcessorInformationMaximumClock,NULL},
228
229{kSMBTypeProcessorInformation,kSMBString,getFieldOffset(SMBProcessorInformation, serialNumber),NULL,NULL,NULL},
230
231{kSMBTypeProcessorInformation,kSMBString,getFieldOffset(SMBProcessorInformation, assetTag),NULL,NULL,NULL},
232
233{kSMBTypeProcessorInformation,kSMBString,getFieldOffset(SMBProcessorInformation, partNumber),NULL,NULL,NULL},
234
235//-------------------------------------------------------------------------------------------------------------------------
236// Memory Device
237//-------------------------------------------------------------------------------------------------------------------------
238{kSMBTypeMemoryDevice,kSMBString,getFieldOffset(SMBMemoryDevice, deviceLocator),kSMBMemoryDeviceDeviceLocatorKey,
239NULL,NULL},
240
241{kSMBTypeMemoryDevice,kSMBString,getFieldOffset(SMBMemoryDevice, bankLocator),kSMBMemoryDeviceBankLocatorKey,
242NULL,NULL},
243
244{kSMBTypeMemoryDevice,kSMBByte,getFieldOffset(SMBMemoryDevice, memoryType),kSMBMemoryDeviceMemoryTypeKey,
245getSMBMemoryDeviceMemoryType,NULL},
246
247{kSMBTypeMemoryDevice,kSMBWord,getFieldOffset(SMBMemoryDevice, memorySpeed),kSMBMemoryDeviceMemorySpeedKey,
248getSMBMemoryDeviceMemorySpeed,NULL},
249
250{kSMBTypeMemoryDevice,kSMBString,getFieldOffset(SMBMemoryDevice, manufacturer),kSMBMemoryDeviceManufacturerKey,
251getSMBMemoryDeviceManufacturer,NULL},
252
253{kSMBTypeMemoryDevice,kSMBString,getFieldOffset(SMBMemoryDevice, serialNumber),kSMBMemoryDeviceSerialNumberKey,
254getSMBMemoryDeviceSerialNumber,NULL},
255
256{kSMBTypeMemoryDevice,kSMBString,getFieldOffset(SMBMemoryDevice, assetTag),NULL,NULL,NULL},
257
258{kSMBTypeMemoryDevice,kSMBString,getFieldOffset(SMBMemoryDevice, partNumber),kSMBMemoryDevicePartNumberKey,
259getSMBMemoryDevicePartNumber,NULL},
260
261
262//-------------------------------------------------------------------------------------------------------------------------
263// Apple Specific
264//-------------------------------------------------------------------------------------------------------------------------
265{kSMBTypeOemProcessorType,kSMBWord,getFieldOffset(SMBOemProcessorType, ProcessorType),kSMBOemProcessorTypeKey,
266getSMBOemProcessorType,NULL},
267
268{kSMBTypeOemProcessorBusSpeed,kSMBWord,getFieldOffset(SMBOemProcessorBusSpeed, ProcessorBusSpeed),kSMBOemProcessorBusSpeedKey,
269getSMBOemProcessorBusSpeed,NULL}
270};
271
272int numOfSetters = sizeof(SMBSetters) / sizeof(SMBValueSetter);
273
274
275SMBEntryPoint *origeps= 0;
276SMBEntryPoint *neweps= 0;
277
278static uint8_t stringIndex;// increament when a string is added and set the field value accordingly
279static uint8_t stringsSize;// add string size
280
281static SMBWord tableLength= 0;
282static SMBWord handle= 0;
283static SMBWord maxStructSize= 0;
284static SMBWord structureCount= 0;
285
286/* Rewrite this function */
287void setDefaultSMBData(void)
288{
289defaultBIOSInfo.vendor= kDefaultVendorManufacturer;
290defaultBIOSInfo.releaseDate= kDefaultBIOSReleaseDate;
291
292defaultSystemInfo.manufacturer= kDefaultVendorManufacturer;
293defaultSystemInfo.version= kDefaultSystemVersion;
294defaultSystemInfo.serialNumber= kDefaultSerialNumber;
295
296defaultBaseBoard.manufacturer= kDefaultVendorManufacturer;
297defaultBaseBoard.product= kDefaultBoardProduct;
298
299if (platformCPUFeature(CPU_FEATURE_MOBILE))
300{
301if (Platform->CPU.NoCores > 1)
302{
303defaultBIOSInfo.version= kDefaultMacBookProBIOSVersion;
304defaultSystemInfo.productName= kDefaultMacBookPro;
305defaultSystemInfo.family= kDefaultMacBookProFamily;
306}
307else
308{
309defaultBIOSInfo.version= kDefaultMacBookBIOSVersion;
310defaultSystemInfo.productName= kDefaultMacBook;
311defaultSystemInfo.family= kDefaultMacBookFamily;
312}
313}
314else
315{
316switch (Platform->CPU.NoCores)
317{
318case 1:
319defaultBIOSInfo.version= kDefaultMacminiBIOSVersion;
320defaultSystemInfo.productName= kDefaultMacmini;
321defaultSystemInfo.family= kDefaultMacminiFamily;
322break;
323
324case 2:
325defaultBIOSInfo.version= kDefaultiMacBIOSVersion;
326defaultSystemInfo.productName= kDefaultiMac;
327defaultSystemInfo.family= kDefaultiMacFamily;
328break;
329default:
330{
331switch (Platform->CPU.Family)
332{
333case 0x06:
334{
335switch (Platform->CPU.Model)
336{
337case CPU_MODEL_FIELDS:// Intel Core i5, i7, Xeon X34xx LGA1156 (45nm)
338case CPU_MODEL_DALES:
339case CPU_MODEL_DALES_32NM:// Intel Core i3, i5 LGA1156 (32nm)
340case 0x19:// ??? Intel Core i5 650 @3.20 GHz
341defaultBIOSInfo.version= kDefaultiMacNehalemBIOSVersion;
342defaultSystemInfo.productName= kDefaultiMacNehalem;
343defaultSystemInfo.family= kDefaultiMacFamily;
344break;
345
346case CPU_MODEL_SANDY:// Intel Core i3, i5, i7 LGA1155 (32nm)
347case CPU_MODEL_SANDY_XEON:// Intel Xeon E3
348defaultBIOSInfo.version= kDefaultiMacSandyBIOSVersion;
349defaultSystemInfo.productName= kDefaultiMacSandy;
350defaultSystemInfo.family= kDefaultiMacFamily;
351break;
352case CPU_MODEL_NEHALEM:// Intel Core i7, Xeon W35xx, Xeon X55xx, Xeon E55xx LGA1366 (45nm)
353case CPU_MODEL_NEHALEM_EX:// Intel Xeon X75xx, Xeon X65xx, Xeon E75xx, Xeon E65x
354defaultBIOSInfo.version= kDefaultMacProNehalemBIOSVersion;
355defaultSystemInfo.productName= kDefaultMacProNehalem;
356defaultSystemInfo.family= kDefaultMacProFamily;
357break;
358
359case CPU_MODEL_WESTMERE:// Intel Core i7, Xeon X56xx, Xeon E56xx, Xeon W36xx LGA1366 (32nm) 6 Core
360case CPU_MODEL_WESTMERE_EX:// Intel Xeon E7
361defaultBIOSInfo.version= kDefaultMacProWestmereBIOSVersion;
362defaultBIOSInfo.releaseDate= kDefaulMacProWestmereBIOSReleaseDate;
363defaultSystemInfo.productName= kDefaultMacProWestmere;
364defaultSystemInfo.family= kDefaultMacProFamily;
365break;
366
367default:
368defaultBIOSInfo.version= kDefaultMacProBIOSVersion;
369defaultSystemInfo.productName= kDefaultMacPro;
370defaultSystemInfo.family= kDefaultMacProFamily;
371break;
372}
373break;
374}
375default:
376defaultBIOSInfo.version= kDefaultMacProBIOSVersion;
377defaultSystemInfo.productName= kDefaultMacPro;
378defaultSystemInfo.family= kDefaultMacProFamily;
379break;
380}
381break;
382}
383}
384}
385}
386
387/* Used for SM*n smbios.plist keys */
388bool getSMBValueForKey(SMBStructHeader *structHeader, const char *keyString, const char **string, returnType *value)
389{
390static int idx = -1;
391static int current = -1;
392int len;
393char key[24];
394
395if (current != structHeader->handle)
396{
397idx++;
398current = structHeader->handle;
399}
400
401sprintf(key, "%s%d", keyString, idx);
402
403if (value)
404if (getIntForKey(key, (int *)&(value->dword), SMBPlist))
405return true;
406else
407if (getValueForKey(key, string, &len, SMBPlist))
408return true;
409return false;
410}
411
412char *getSMBStringForField(SMBStructHeader *structHeader, uint8_t field)
413{
414uint8_t *stringPtr = (uint8_t *)structHeader + structHeader->length;
415
416if (!field)
417return NULL;
418
419for (field--; field != 0 && strlen((char *)stringPtr) > 0;
420field--, stringPtr = (uint8_t *)((uint32_t)stringPtr + strlen((char *)stringPtr) + 1));
421
422return (char *)stringPtr;
423}
424
425void setSMBStringForField(SMBStructHeader *structHeader, const char *string, uint8_t *field)
426{
427int strSize;
428
429if (!field)
430return;
431if (!string)
432{
433*field = 0;
434return;
435}
436
437strSize = strlen(string);
438
439// remove any spaces found at the end
440while ((strSize != 0) && (string[strSize - 1] == ' '))
441strSize--;
442
443if (strSize == 0)
444{
445*field = 0;
446return;
447}
448
449memcpy((uint8_t *)structHeader + structHeader->length + stringsSize, string, strSize);
450*field = stringIndex;
451
452stringIndex++;
453stringsSize += strSize + 1;
454}
455
456bool setSMBValue(SMBStructPtrs *structPtr, int idx, returnType *value)
457{
458const char *string = 0;
459int len;
460bool parsed;
461int val;
462
463if (numOfSetters <= idx)
464return false;
465
466switch (SMBSetters[idx].valueType)
467{
468case kSMBString:
469if (SMBSetters[idx].keyString)
470{
471if (getValueForKey(SMBSetters[idx].keyString, &string, &len, SMBPlist))
472break;
473else
474if (structPtr->orig->type == kSMBTypeMemoryDevice)// MemoryDevice only
475if (getSMBValueForKey(structPtr->orig, SMBSetters[idx].keyString, &string, NULL))
476break;
477}
478if (SMBSetters[idx].getSMBValue)
479if (SMBSetters[idx].getSMBValue((returnType *)&string))
480break;
481if ((SMBSetters[idx].defaultValue) && *(SMBSetters[idx].defaultValue))
482{
483string = *(SMBSetters[idx].defaultValue);
484break;
485}
486string = getSMBStringForField(structPtr->orig, *(uint8_t *)value);
487break;
488
489case kSMBByte:
490case kSMBWord:
491case kSMBDWord:
492//case kSMBQWord:
493if (SMBSetters[idx].keyString)
494{
495parsed = getIntForKey(SMBSetters[idx].keyString, &val, SMBPlist);
496if (!parsed)
497if (structPtr->orig->type == kSMBTypeMemoryDevice)// MemoryDevice only
498parsed = getSMBValueForKey(structPtr->orig, SMBSetters[idx].keyString, NULL, (returnType *)&val);
499if (parsed)
500{
501switch (SMBSetters[idx].valueType)
502{
503case kSMBByte:
504value->byte = (uint8_t)val;
505break;
506case kSMBWord:
507value->word = (uint16_t)val;
508break;
509case kSMBDWord:
510default:
511value->dword = (uint32_t)val;
512break;
513}
514return true;
515}
516}
517
518if (SMBSetters[idx].getSMBValue)
519if (SMBSetters[idx].getSMBValue(value))
520return true;
521#if 0
522if (*(SMBSetters[idx].defaultValue))
523{
524value->dword = *(uint32_t *)(SMBSetters[idx].defaultValue);
525return true;
526}
527#endif
528break;
529}
530
531if (SMBSetters[idx].valueType == kSMBString && string)
532setSMBStringForField(structPtr->new, string, &value->byte);
533
534return true;
535}
536
537//-------------------------------------------------------------------------------------------------------------------------
538// Apple Specific
539//-------------------------------------------------------------------------------------------------------------------------
540void addSMBFirmwareVolume(SMBStructPtrs *structPtr)
541{
542return;
543}
544
545void addSMBMemorySPD(SMBStructPtrs *structPtr)
546{
547/* SPD data from Platform->RAM.spd */
548return;
549}
550
551void addSMBOemProcessorType(SMBStructPtrs *structPtr)
552{
553SMBOemProcessorType *p = (SMBOemProcessorType *)structPtr->new;
554
555p->header.type= kSMBTypeOemProcessorType;
556p->header.length= sizeof(SMBOemProcessorType);
557p->header.handle= handle++;
558
559setSMBValue(structPtr, numOfSetters - 2 , (returnType *)&(p->ProcessorType));
560
561structPtr->new = (SMBStructHeader *)((uint8_t *)structPtr->new + sizeof(SMBOemProcessorType) + 2);
562tableLength += sizeof(SMBOemProcessorType) + 2;
563structureCount++;
564}
565
566void addSMBOemProcessorBusSpeed(SMBStructPtrs *structPtr)
567{
568SMBOemProcessorBusSpeed *p = (SMBOemProcessorBusSpeed *)structPtr->new;
569
570switch (Platform->CPU.Family)
571{
572case 0x06:
573{
574switch (Platform->CPU.Model)
575{
576case 0x19:// ??? Intel Core i5 650 @3.20 GHz
577case CPU_MODEL_FIELDS:// Intel Core i5, i7, Xeon X34xx LGA1156 (45nm)
578case CPU_MODEL_DALES:
579case CPU_MODEL_DALES_32NM:// Intel Core i3, i5 LGA1156 (32nm)
580case CPU_MODEL_NEHALEM:// Intel Core i7, Xeon W35xx, Xeon X55xx, Xeon E55xx LGA1366 (45nm)
581case CPU_MODEL_NEHALEM_EX:// Intel Xeon X75xx, Xeon X65xx, Xeon E75xx, Xeon E65x
582case CPU_MODEL_WESTMERE:// Intel Core i7, Xeon X56xx, Xeon E56xx, Xeon W36xx LGA1366 (32nm) 6 Core
583case CPU_MODEL_WESTMERE_EX:// Intel Xeon E7
584break;
585
586default:
587return;
588}
589}
590}
591
592p->header.type= kSMBTypeOemProcessorBusSpeed;
593p->header.length= sizeof(SMBOemProcessorBusSpeed);
594p->header.handle= handle++;
595
596setSMBValue(structPtr, numOfSetters -1, (returnType *)&(p->ProcessorBusSpeed));
597
598structPtr->new = (SMBStructHeader *)((uint8_t *)structPtr->new + sizeof(SMBOemProcessorBusSpeed) + 2);
599tableLength += sizeof(SMBOemProcessorBusSpeed) + 2;
600structureCount++;
601}
602
603//-------------------------------------------------------------------------------------------------------------------------
604// EndOfTable
605//-------------------------------------------------------------------------------------------------------------------------
606void addSMBEndOfTable(SMBStructPtrs *structPtr)
607{
608structPtr->new->type= kSMBTypeEndOfTable;
609structPtr->new->length= sizeof(SMBStructHeader);
610structPtr->new->handle= handle++;
611
612structPtr->new = (SMBStructHeader *)((uint8_t *)structPtr->new + sizeof(SMBStructHeader) + 2);
613tableLength += sizeof(SMBStructHeader) + 2;
614structureCount++;
615}
616
617void setSMBStruct(SMBStructPtrs *structPtr)
618{
619bool setterFound = false;
620
621uint8_t *ptr;
622SMBWord structSize;
623int i;
624
625stringIndex = 1;
626stringsSize = 0;
627
628if (handle < structPtr->orig->handle)
629handle = structPtr->orig->handle;
630
631memcpy((void *)structPtr->new, structPtr->orig, structPtr->orig->length);
632
633for (i = 0; i < numOfSetters; i++)
634if ((structPtr->orig->type == SMBSetters[i].type) && (SMBSetters[i].fieldOffset < structPtr->orig->length))
635{
636setterFound = true;
637setSMBValue(structPtr, i, (returnType *)((uint8_t *)structPtr->new + SMBSetters[i].fieldOffset));
638}
639
640if (setterFound)
641{
642ptr = (uint8_t *)structPtr->new + structPtr->orig->length;
643for (; ((uint16_t *)ptr)[0] != 0; ptr++);
644
645if (((uint16_t *)ptr)[0] == 0)
646ptr += 2;
647
648structSize = ptr - (uint8_t *)structPtr->new;
649}
650else
651{
652ptr = (uint8_t *)structPtr->orig + structPtr->orig->length;
653for (; ((uint16_t *)ptr)[0] != 0; ptr++);
654
655if (((uint16_t *)ptr)[0] == 0)
656ptr += 2;
657
658structSize = ptr - (uint8_t *)structPtr->orig;
659memcpy((void *)structPtr->new, structPtr->orig, structSize);
660}
661
662structPtr->new = (SMBStructHeader *)((uint8_t *)structPtr->new + structSize);
663
664tableLength += structSize;
665
666if (structSize > maxStructSize)
667maxStructSize = structSize;
668
669structureCount++;
670}
671
672void setupNewSMBIOSTable(SMBEntryPoint *eps, SMBStructPtrs *structPtr)
673{
674uint8_t *ptr = (uint8_t *)eps->dmi.tableAddress;
675structPtr->orig = (SMBStructHeader *)ptr;
676
677for (;((eps->dmi.tableAddress + eps->dmi.tableLength) > ((uint32_t)(uint8_t *)structPtr->orig + sizeof(SMBStructHeader)));)
678{
679switch (structPtr->orig->type)
680{
681/* Skip all Apple Specific Structures */
682case kSMBTypeFirmwareVolume:
683case kSMBTypeMemorySPD:
684case kSMBTypeOemProcessorType:
685case kSMBTypeOemProcessorBusSpeed:
686/* And this one too, to be added at the end */
687case kSMBTypeEndOfTable:
688break;
689
690default:
691/* Add */
692setSMBStruct(structPtr);
693break;
694}
695
696ptr = (uint8_t *)((uint32_t)structPtr->orig + structPtr->orig->length);
697for (; ((uint16_t *)ptr)[0] != 0; ptr++);
698
699if (((uint16_t *)ptr)[0] == 0)
700ptr += 2;
701
702structPtr->orig = (SMBStructHeader *)ptr;
703}
704
705addSMBFirmwareVolume(structPtr);
706addSMBMemorySPD(structPtr);
707addSMBOemProcessorType(structPtr);
708addSMBOemProcessorBusSpeed(structPtr);
709
710addSMBEndOfTable(structPtr);
711}
712
713void setupSMBIOSTable(void)
714{
715SMBStructPtrs *structPtr;
716uint8_t *buffer;
717bool setSMB = true;
718
719if (!origeps)
720return;
721
722neweps = origeps;
723
724structPtr = (SMBStructPtrs *)malloc(sizeof(SMBStructPtrs));
725if (!structPtr)
726return;
727
728buffer = malloc(SMB_ALLOC_SIZE);
729if (!buffer)
730return;
731
732bzero(buffer, SMB_ALLOC_SIZE);
733structPtr->new = (SMBStructHeader *)buffer;
734
735getBoolForKey(kSMBIOSdefaults, &setSMB, &bootInfo->chameleonConfig);
736if (setSMB)
737setDefaultSMBData();
738
739setupNewSMBIOSTable(origeps, structPtr);
740
741neweps = (SMBEntryPoint *)AllocateKernelMemory(sizeof(SMBEntryPoint));
742if (!neweps)
743return;
744bzero(neweps, sizeof(SMBEntryPoint));
745
746neweps->anchor[0]= '_';
747neweps->anchor[1]= 'S';
748neweps->anchor[2]= 'M';
749neweps->anchor[3]= '_';
750neweps->entryPointLength= sizeof(SMBEntryPoint);
751neweps->majorVersion= 2;
752neweps->minorVersion= 4;
753neweps->maxStructureSize= maxStructSize;
754neweps->entryPointRevision= 0;
755
756neweps->dmi.anchor[0]= '_';
757neweps->dmi.anchor[1]= 'D';
758neweps->dmi.anchor[2]= 'M';
759neweps->dmi.anchor[3]= 'I';
760neweps->dmi.anchor[4]= '_';
761neweps->dmi.tableLength= tableLength;
762neweps->dmi.tableAddress= AllocateKernelMemory(tableLength);
763neweps->dmi.structureCount= structureCount;
764neweps->dmi.bcdRevision= 0x24;
765
766if (!neweps->dmi.tableAddress)
767return;
768
769memcpy((void *)neweps->dmi.tableAddress, buffer, tableLength);
770
771neweps->dmi.checksum= 0;
772neweps->dmi.checksum= 0x100 - checksum8(&neweps->dmi, sizeof(DMIEntryPoint));
773
774neweps->checksum= 0;
775neweps->checksum= 0x100 - checksum8(neweps, sizeof(SMBEntryPoint));
776
777free(buffer);
778decodeSMBIOSTable(neweps);
779}
780
781void *getSmbios(int which)
782{
783switch (which)
784{
785case SMBIOS_ORIGINAL:
786if (!origeps)
787origeps = getAddressOfSmbiosTable();
788return origeps;
789case SMBIOS_PATCHED:
790return neweps;
791}
792
793return 0;
794}
795
796/** Find first original dmi Table with a particular type */
797SMBStructHeader* FindFirstDmiTableOfType(int type, int minlength)
798{
799 current_pos = 0; //static variable
800
801 return FindNextDmiTableOfType(type, minlength);
802};
803
804/** Find next original dmi Table with a particular type */
805SMBStructHeader* FindNextDmiTableOfType(int type, int minlength)
806{
807 int i;
808
809 if (ftTablePairInit) getSmbios(SMBIOS_ORIGINAL);
810
811 for (i=current_pos; i < DmiTablePairCount; i++) {
812 if (type == DmiTablePair[i].type &&
813 DmiTablePair[i].dmi &&
814 DmiTablePair[i].dmi->length >= minlength ) {
815 current_pos = i+1;
816 return DmiTablePair[i].dmi;
817 }
818 }
819 return NULL; // not found
820};
821
822
823/* Collect any information needed later */
824void readSMBIOSInfo(SMBEntryPoint *eps)
825{
826uint8_t *structPtr = (uint8_t *)eps->dmi.tableAddress;
827SMBStructHeader *structHeader = (SMBStructHeader *)structPtr;
828
829int dimmnbr = 0;
830Platform->DMI.MaxMemorySlots= 0;
831Platform->DMI.CntMemorySlots= 0;
832Platform->DMI.MemoryModules= 0;
833
834for (;((eps->dmi.tableAddress + eps->dmi.tableLength) > ((uint32_t)(uint8_t *)structHeader + sizeof(SMBStructHeader)));)
835{
836switch (structHeader->type)
837{
838case kSMBTypeSystemInformation:
839Platform->UUID = ((SMBSystemInformation *)structHeader)->uuid;
840break;
841
842case kSMBTypePhysicalMemoryArray:
843Platform->DMI.MaxMemorySlots += ((SMBPhysicalMemoryArray *)structHeader)->numMemoryDevices;
844break;
845
846case kSMBTypeMemoryDevice:
847Platform->DMI.CntMemorySlots++;
848if (((SMBMemoryDevice *)structHeader)->memorySize != 0)
849Platform->DMI.MemoryModules++;
850if (((SMBMemoryDevice *)structHeader)->memorySpeed > 0)
851Platform->RAM.DIMM[dimmnbr].Frequency = ((SMBMemoryDevice *)structHeader)->memorySpeed;
852dimmnbr++;
853break;
854}
855
856structPtr = (uint8_t *)((uint32_t)structHeader + structHeader->length);
857for (; ((uint16_t *)structPtr)[0] != 0; structPtr++);
858
859if (((uint16_t *)structPtr)[0] == 0)
860structPtr += 2;
861
862structHeader = (SMBStructHeader *)structPtr;
863}
864}
865

Archive Download this file

Revision: 1171