Chameleon

Chameleon Svn Source Tree

Root/branches/slice/trunkM/i386/modules/NVRAM/NVRAM.c

1/*
2 * Template by (c) 2009 Evan Lojewski. All rights reserved.
3 *
4 * NVRAM module by Slice 2010.
5 */
6
7#include "libsaio.h"
8#include "modules.h"
9#include "boot.h"
10#include "bootstruct.h"
11#include "pci.h"
12#include "efi.h"
13#include "smbios_getters.h"
14#include "xml.h"
15
16#ifndef DEBUG_NVRAM
17#define DEBUG_NVRAM 0
18#endif
19
20#if DEBUG_NVRAM
21#define DBG(x...) printf(x)
22#else
23#define DBG(x...) msglog(x)
24#endif
25
26/*static const char const FIRMWARE_REVISION_PROP[] = "firmware-revision";
27static const char const FIRMWARE_ABI_PROP[] = "firmware-abi";
28static const char const FIRMWARE_VENDOR_PROP[] = "firmware-vendor";
29static const char const FIRMWARE_ABI_32_PROP_VALUE[] = "EFI32";
30static const char const FIRMWARE_ABI_64_PROP_VALUE[] = "EFI64";
31static const char const SYSTEM_ID_PROP[] = "system-id";
32static const char const SYSTEM_SERIAL_PROP[] = "SystemSerialNumber";
33static const char const SYSTEM_TYPE_PROP[] = "system-type";
34static const char const MODEL_PROP[] = "Model";
35 */
36const char PLATFORM_UUID[] = "platform-uuid";
37//EFI_UINT32 const FIRMWARE_FEATURE_MASK = 0x000003FF;
38EFI_UINT32 const STATIC_ZERO = 0;
39
40#define kBL_GLOBAL_NVRAM_GUID "8BE4DF61-93CA-11D2-AA0D-00E098032B8C"
41
42// Check if a system supports CSM legacy mode
43#define kBL_APPLE_VENDOR_NVRAM_GUID "4D1EDE05-38C7-4A6A-9CC6-4BCCA8B38C14"
44#define UUID_LEN16
45
46//extern EFI_GUID* getSystemID();
47void NVRAM_start(void);
48
49typedef struct {
50char Name[32];
51char Value[512];
52} variables;
53int readNVRAM(variables* v);
54
55
56void NVRAM_hook(void* arg1, void* arg2, void* arg3, void* arg4);
57/*
58void NVRAM_start_hook(void* arg1, void* arg2, void* arg3, void* arg4)
59{
60msglog("NVRAM started with ExecKernel\n");
61
62}
63*/
64
65void NVRAM_start()
66{
67//register_hook_callback("ExecKernel", &NVRAM_start_hook);
68//register_hook_callback("Kernel Start", &NVRAM_hook);
69register_hook_callback("ModulesLoaded", &NVRAM_hook);
70}
71
72void NVRAM_hook(void* arg1, void* arg2, void* arg3, void* arg4)
73{
74charbootName[128];
75variables*var;
76char*ffName;
77uint8_t *FirmwareFeatures;
78EFI_UINT32*FirmwareFeaturesMask;
79char*ffmName;
80char*boName;
81char*bnName;
82//EFI_GUID*ret = 0;
83uint16_tbootOptionNumber = 0;
84int i, j;
85
86//BLESS_EFI_LOAD_OPTION* NextBoot =(BLESS_EFI_LOAD_OPTION*)gBootOrder;
87
88DBG("NVRAM started with ModulesLoaded\n");
89
90//Slice create /options node -> /fakenvram
91// I need to use fakenvram until I know what is happen
92//bool UseNVRAM = FALSE;
93bool ClearNVRAM = FALSE;
94const char* buff;
95//TagPtrdictionary;
96int cnt;
97var = malloc(sizeof(variables)+1);
98ClearNVRAM = getValueForKey("-c", &buff, &cnt, &bootInfo->bootConfig);
99if (!ClearNVRAM) {
100readNVRAM(var);
101}
102
103for (i=0; i<32; i++) {
104if (var[i].Name[0] == 0) {
105break;
106}
107if (strcmp(var[i].Name, "efi-boot-device")==0) {
108//XMLParseFile(var[i].Value, &dictionary);
109//buff = XMLGetProperty(dictionary, "BLLastBSDName")->string;
110verbose("Required boot device is %s\n", var[i].Value);
111//NextBoot->FilePathListLength = 1;
112//strcpy(NextBoot->Description, buff);
113break;
114}
115}
116
117Node* optionsNode = DT__FindNode("/options", true); //"/fakenvram"
118ffName = malloc(sizeof(PLATFORM_UUID)+1);
119strcpy(ffName, PLATFORM_UUID);
120//ret = getSystemID();
121//DT__AddProperty(optionsNode, ffName, UUID_LEN, (EFI_UINT32*) ret);
122
123// this information can be obtained from DMI Type 0
124SMBByte* p = (SMBByte*)FindFirstDmiTableOfType(0, 0x18);
125FirmwareFeatures = malloc(sizeof(SMBByte));
126//TODO - the bufferFF must be composed from bits p[0x12] and [0x13]. Datasheet needed
127*FirmwareFeatures = ((p[19] >> 1) & 1) //USB Legacy is supported
128| ((p[18] >> 14) & 2) //Boot from CD is supported
129| 0x14; //default for bless (GUID partition)
130
131sprintf(bootName, "%s:FirmwareFeatures", kBL_APPLE_VENDOR_NVRAM_GUID);
132ffName = malloc(sizeof(bootName)+1);
133strcpy(ffName, bootName);
134DT__AddProperty(optionsNode, ffName, sizeof(uint32_t), (char *)FirmwareFeatures); //legacy support
135
136sprintf(bootName, "%s:FirmwareFeaturesMask", kBL_APPLE_VENDOR_NVRAM_GUID);
137FirmwareFeaturesMask = malloc(sizeof(EFI_UINT32));
138*FirmwareFeaturesMask = (EFI_UINT32)0x3ff;
139ffmName = malloc(sizeof(bootName)+1);
140strcpy(ffmName, bootName);
141DT__AddProperty(optionsNode, ffmName, sizeof(uint32_t), (EFI_UINT32*)FirmwareFeaturesMask);
142
143//TODO - check, validate and fill by bvr structure.
144//here I am not sure what is BootOrder: node or property?
145//Node* bootNode = DT__AddChild(optionsNode, kBL_GLOBAL_NVRAM_GUID ":BootOrder");
146sprintf(bootName, "%s:BootOrder", kBL_GLOBAL_NVRAM_GUID);
147boName = malloc(sizeof(bootName)+1);
148strcpy(boName, bootName);
149DT__AddProperty(optionsNode, boName, sizeof(uint32_t), (EFI_UINT32*)&STATIC_ZERO);
150
151sprintf(bootName, "%s:Boot%04hx", kBL_GLOBAL_NVRAM_GUID, bootOptionNumber);
152bnName = malloc(sizeof(bootName)+1);
153strcpy(bnName, bootName);
154DT__AddProperty(optionsNode, bnName, sizeof(uint32_t), (EFI_UINT32*)&STATIC_ZERO);
155
156
157//can we add here boot-properties?
158//optionsNode = DT__FindNode("chosen", true);
159#if NOTYET
160int lbC = 0;
161while(((char*)&bootInfo->bootConfig)[lbC++]);
162if (lbC > sizeof(bootInfo->bootConfig)) lbC = sizeof(bootInfo->bootConfig);
163DT__AddProperty(optionsNode, "boot-args", lbC, (char*)&bootInfo->bootConfig);
164#endif
165//TODO - BootCamp emulation?
166/*
167 romNode = DT__FindNode("/rom", true);
168 DT__AddProperty(romNode, "fv-main-address"... //provided by AppleSMBIOS
169 DT__AddProperty(romNode, "fv-main-size"...
170 "IOEFIDevicePathType" -> "MediaFirmwareVolumeFilePath"
171 "Guid" -> "2B0585EB-D8B8-49A9-8B8C-E21B01AEF2B7"
172
173 */
174//
175
176for (i=0; i<32; i++) {
177DBG("NVRAM get a name %s\n", var[i].Name);
178if (var[i].Name[0]) {
179if (isdigit(var[i].Name[0])) {
180msglog(" ...it is digit...\n");
181continue;
182}
183j=0;
184while (var[i].Value[j++]);
185DT__AddProperty(optionsNode, var[i].Name, j,&var[i].Value);
186#if 1 //DEBUG_NVRAM
187DBG("NVRAM add name=%s value=%s length=%d\n", var[i].Name, var[i].Value, j);
188#endif
189} else {
190break;
191}
192
193}
194//Serialization?
195bnName[0] = bnName[1] = 0;
196DT__AddProperty(optionsNode, bnName, sizeof(uint32_t), (EFI_UINT32*)&STATIC_ZERO);
197}
198
199const char NVRAM_INF[] = "nvram.inf";
200int readNVRAM(variables* var)
201{
202int fd, fsize;
203char* nvr = 0;
204DBG("Start NVRAM reading\n");
205if ((fd = open(NVRAM_INF, 0)) < 0) {
206DBG("[ERROR] open NVRAM failed\n");
207return -1;
208}
209fsize = file_size(fd);
210if (!fsize) {
211DBG(" zero NVRAM file\n");
212close (fd);
213return -1;
214}
215if ((nvr = malloc(fsize)) == NULL) {
216DBG("[ERROR] alloc NVRAM memory failed\n");
217close (fd);
218return -1;
219}
220if (read (fd, nvr, fsize) != fsize) {
221DBG("[ERROR] read %s failed\n", NVRAM_INF);
222close (fd);
223return -1;
224}
225close (fd);
226/*if ((var = malloc(fsize)) == NULL) {
227DBG("[ERROR] alloc VAR memory failed\n");
228return -1;
229}*/
230int i = 0;
231char * onvr = nvr;
232bool skipGUID;
233while (*nvr) {
234int j = 0;
235skipGUID = false;
236DBG("Name[%d]:", i);
237while (*nvr != 9) {
238//DBG("%c", *nvr);
239if (*nvr == 4) {
240skipGUID = true; //TODO this is GUID
241nvr++;
242} else
243var[i].Name[j++] = *nvr++;
244}
245DBG("\n");
246nvr++; //skip \09
247var[i].Name[j] = 0; //end of c-string
248if (skipGUID) {
249//TODO this is GUID
250DBG("skip GUID\n");
251while (*nvr++ != 0x0A) {}
252i--;
253} else {
254
255j = 0;
256unsigned char c;
257while (*nvr != 0x0A) {
258c = *nvr++;
259if (c == 0x25) { //TODO this is hex
260int k1=*nvr++;
261if ((k1 >= 0x30) && (k1 <= 0x39)) {
262k1 = k1 - 0x30;
263}
264if ((k1 > 0x60) && (k1 <= 0x66)) {
265k1 = k1 - 0x60 + 10;
266}
267int k2=*nvr++;
268if ((k2 >= 0x30) && (k2 <= 0x39)) {
269k2 = k2 - 0x30;
270}
271if ((k2 > 0x60) && (k2 <= 0x66)) {
272k2 = k2 - 0x60 + 10;
273}
274c = (k1 << 4) + k2;
275//break;
276}
277var[i].Value[j++] = c;
278}
279nvr++;
280DBG("Value[%d]:", i);
281int m;
282for (m=0; m<j; m++) {
283//DBG("%02x ", var[i].Value[m]);
284}
285//DBG("Value[%d]:%s\n", i, var[i].Value);
286DBG("\n");
287}
288i++;
289if ((int)(nvr - onvr) > fsize) {
290DBG("end of buffer\n");
291break;
292}
293}
294var[i].Name[0]=0;
295var[i].Name[1]=0;
296
297return 0;
298}

Archive Download this file

Revision: 1290