]> git.proxmox.com Git - mirror_edk2.git/blame_incremental - EdkModulePkg/Universal/PCD/Dxe/Service.c
Add follows warpped tianotools to frameworktask:
[mirror_edk2.git] / EdkModulePkg / Universal / PCD / Dxe / Service.c
... / ...
CommitLineData
1/** @file\r
2Private functions used by PCD DXE driver.s\r
3\r
4Copyright (c) 2006, Intel Corporation\r
5All rights reserved. This program and the accompanying materials\r
6are licensed and made available under the terms and conditions of the BSD License\r
7which accompanies this distribution. The full text of the license may be found at\r
8http://opensource.org/licenses/bsd-license.php\r
9\r
10THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
11WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
12\r
13\r
14Module Name: Service.c\r
15\r
16**/\r
17#include "Service.h"\r
18\r
19\r
20//\r
21// Build Tool will generate DXE_PCD_DB_INIT_VALUE in Autogen.h\r
22// Compression Algorithm will take care of the size optimization.\r
23//\r
24\r
25PCD_DATABASE * mPcdDatabase;\r
26\r
27LIST_ENTRY *mCallbackFnTable;\r
28\r
29VOID *\r
30GetWorker (\r
31 UINTN TokenNumber,\r
32 UINTN GetSize\r
33 )\r
34{\r
35 UINT32 *LocalTokenNumberTable;\r
36 UINT16 *SizeTable;\r
37 BOOLEAN IsPeiDb;\r
38 UINTN Size;\r
39 UINT32 Offset;\r
40 EFI_GUID *GuidTable;\r
41 UINT16 *StringTable;\r
42 EFI_GUID *Guid;\r
43 UINT16 *Name;\r
44 VARIABLE_HEAD *VariableHead;\r
45 EFI_STATUS Status;\r
46 UINTN DataSize;\r
47 VOID *Data;\r
48 VPD_HEAD *VpdHead;\r
49 UINT8 *PcdDb;\r
50 UINT16 StringTableIdx; \r
51 UINT32 LocalTokenNumber;\r
52\r
53 //\r
54 // TokenNumber Zero is reserved as PCD_INVALID_TOKEN_NUMBER.\r
55 // We have to decrement TokenNumber by 1 to make it usable\r
56 // as the array index.\r
57 //\r
58 TokenNumber--;\r
59 \r
60 ASSERT (TokenNumber < PCD_TOTAL_TOKEN_NUMBER);\r
61\r
62 Size = DxePcdGetSize (TokenNumber + 1);\r
63 ASSERT (GetSize == Size || GetSize == 0);\r
64\r
65 \r
66 IsPeiDb = (TokenNumber < PEI_LOCAL_TOKEN_NUMBER) ? TRUE : FALSE;\r
67\r
68 LocalTokenNumberTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.LocalTokenNumberTable : \r
69 mPcdDatabase->DxeDb.Init.LocalTokenNumberTable;\r
70\r
71 SizeTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.SizeTable: \r
72 mPcdDatabase->DxeDb.Init.SizeTable;\r
73\r
74 TokenNumber = IsPeiDb ? TokenNumber :\r
75 TokenNumber - PEI_LOCAL_TOKEN_NUMBER;\r
76\r
77 LocalTokenNumber = LocalTokenNumberTable[TokenNumber];\r
78 \r
79 if ((LocalTokenNumber & PCD_TYPE_SKU_ENABLED) == PCD_TYPE_SKU_ENABLED) {\r
80 LocalTokenNumber = GetSkuEnabledTokenNumber (LocalTokenNumber & ~PCD_TYPE_SKU_ENABLED, Size, IsPeiDb);\r
81 }\r
82\r
83 PcdDb = IsPeiDb ? ((UINT8 *) &mPcdDatabase->PeiDb) : ((UINT8 *) &mPcdDatabase->DxeDb);\r
84 StringTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.StringTable :\r
85 mPcdDatabase->DxeDb.Init.StringTable;\r
86 \r
87 Offset = LocalTokenNumber & PCD_DATABASE_OFFSET_MASK;\r
88 \r
89 switch (LocalTokenNumber & ~PCD_DATABASE_OFFSET_MASK) {\r
90 case PCD_TYPE_VPD:\r
91 VpdHead = (VPD_HEAD *) ((UINT8 *) PcdDb + Offset);\r
92 return (VOID *) (UINTN) (FixedPcdGet32(PcdVpdBaseAddress) + VpdHead->Offset);\r
93 \r
94 case PCD_TYPE_HII:\r
95 GuidTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.GuidTable :\r
96 mPcdDatabase->DxeDb.Init.GuidTable;\r
97 \r
98 VariableHead = (VARIABLE_HEAD *) (PcdDb + Offset);\r
99 \r
100 Guid = &(GuidTable[VariableHead->GuidTableIndex]);\r
101 Name = &(StringTable[VariableHead->StringIndex]);\r
102\r
103 Status = GetHiiVariable (Guid, Name, &Data, &DataSize);\r
104 if (Status == EFI_SUCCESS) {\r
105 ASSERT (DataSize >= (UINTN) (VariableHead->Offset + Size));\r
106 return (UINT8 *) Data + VariableHead->Offset;\r
107 } else {\r
108 //\r
109 // Return the default value specified by Platform Integrator \r
110 //\r
111 return (VOID *) ((UINT8 *) PcdDb + VariableHead->DefaultValueOffset);\r
112 }\r
113\r
114 case PCD_TYPE_STRING:\r
115 StringTableIdx = (UINT16) *((UINT8 *) PcdDb + Offset);\r
116 return (VOID *) &StringTable[StringTableIdx];\r
117\r
118 case PCD_TYPE_DATA:\r
119 return (VOID *) ((UINT8 *) PcdDb + Offset);\r
120 break;\r
121\r
122 default:\r
123 ASSERT (FALSE);\r
124 break;\r
125 \r
126 }\r
127\r
128 ASSERT (FALSE);\r
129 \r
130 return NULL;\r
131 \r
132}\r
133\r
134\r
135\r
136EFI_STATUS\r
137DxeRegisterCallBackWorker (\r
138 IN UINTN TokenNumber,\r
139 IN CONST GUID *Guid, OPTIONAL\r
140 IN PCD_PROTOCOL_CALLBACK CallBackFunction\r
141)\r
142{\r
143 CALLBACK_FN_ENTRY *FnTableEntry;\r
144 LIST_ENTRY *ListHead;\r
145 LIST_ENTRY *ListNode;\r
146\r
147 if (Guid != NULL) {\r
148 TokenNumber = GetExPcdTokenNumber (Guid, (UINT32) TokenNumber);\r
149 }\r
150\r
151 //\r
152 // TokenNumber Zero is reserved as PCD_INVALID_TOKEN_NUMBER.\r
153 // We have to decrement TokenNumber by 1 to make it usable\r
154 // as the array index.\r
155 //\r
156 TokenNumber--;\r
157\r
158 ListHead = &mCallbackFnTable[TokenNumber];\r
159 ListNode = GetFirstNode (ListHead);\r
160\r
161 while (ListNode != ListHead) {\r
162 FnTableEntry = CR_FNENTRY_FROM_LISTNODE(ListNode, CALLBACK_FN_ENTRY, Node);\r
163\r
164 if (FnTableEntry->CallbackFn == CallBackFunction) {\r
165 //\r
166 // We only allow a Callback function to be register once\r
167 // for a TokenNumber. So just return EFI_SUCCESS\r
168 //\r
169 return EFI_SUCCESS;\r
170 }\r
171 ListNode = GetNextNode (ListHead, ListNode);\r
172 }\r
173\r
174 FnTableEntry = AllocatePool (sizeof(CALLBACK_FN_ENTRY));\r
175 ASSERT (FnTableEntry != NULL);\r
176\r
177 FnTableEntry->CallbackFn = CallBackFunction;\r
178 InsertTailList (ListHead, &FnTableEntry->Node);\r
179 \r
180 return EFI_SUCCESS;\r
181}\r
182\r
183\r
184\r
185\r
186EFI_STATUS\r
187DxeUnRegisterCallBackWorker (\r
188 IN UINTN TokenNumber,\r
189 IN CONST GUID *Guid, OPTIONAL\r
190 IN PCD_PROTOCOL_CALLBACK CallBackFunction\r
191)\r
192{\r
193 CALLBACK_FN_ENTRY *FnTableEntry;\r
194 LIST_ENTRY *ListHead;\r
195 LIST_ENTRY *ListNode;\r
196\r
197 if (Guid != NULL) {\r
198 TokenNumber = GetExPcdTokenNumber (Guid, (UINT32) TokenNumber);\r
199 }\r
200\r
201 //\r
202 // TokenNumber Zero is reserved as PCD_INVALID_TOKEN_NUMBER.\r
203 // We have to decrement TokenNumber by 1 to make it usable\r
204 // as the array index.\r
205 //\r
206 TokenNumber--;\r
207\r
208 ListHead = &mCallbackFnTable[TokenNumber];\r
209 ListNode = GetFirstNode (ListHead);\r
210\r
211 while (ListNode != ListHead) {\r
212 FnTableEntry = CR_FNENTRY_FROM_LISTNODE(ListNode, CALLBACK_FN_ENTRY, Node);\r
213\r
214 if (FnTableEntry->CallbackFn == CallBackFunction) {\r
215 //\r
216 // We only allow a Callback function to be register once\r
217 // for a TokenNumber. So we can safely remove the Node from\r
218 // the Link List and return EFI_SUCCESS.\r
219 //\r
220 RemoveEntryList (ListNode);\r
221 FreePool (FnTableEntry);\r
222 \r
223 return EFI_SUCCESS;\r
224 }\r
225 ListNode = GetNextNode (ListHead, ListNode);\r
226 }\r
227\r
228 return EFI_INVALID_PARAMETER;\r
229}\r
230\r
231\r
232\r
233UINTN \r
234ExGetNextTokeNumber (\r
235 IN CONST EFI_GUID *Guid,\r
236 IN UINTN TokenNumber,\r
237 IN EFI_GUID *GuidTable,\r
238 IN UINTN SizeOfGuidTable,\r
239 IN DYNAMICEX_MAPPING *ExMapTable,\r
240 IN UINTN SizeOfExMapTable\r
241 )\r
242{\r
243 EFI_GUID *MatchGuid;\r
244 UINTN Idx;\r
245 UINTN GuidTableIdx;\r
246 BOOLEAN Found;\r
247\r
248 MatchGuid = ScanGuid (GuidTable, SizeOfGuidTable, Guid);\r
249 if (MatchGuid == NULL) {\r
250 return PCD_INVALID_TOKEN_NUMBER;\r
251 }\r
252\r
253 Found = FALSE;\r
254 GuidTableIdx = MatchGuid - GuidTable;\r
255 for (Idx = 0; Idx < SizeOfExMapTable; Idx++) {\r
256 if (ExMapTable[Idx].ExGuidIndex == GuidTableIdx) {\r
257 Found = TRUE;\r
258 break;\r
259 }\r
260 }\r
261\r
262 if (Found) {\r
263 if (TokenNumber == PCD_INVALID_TOKEN_NUMBER) {\r
264 return ExMapTable[Idx].ExTokenNumber;\r
265 }\r
266\r
267 for ( ; Idx < SizeOfExMapTable; Idx++) {\r
268 if (ExMapTable[Idx].ExTokenNumber == TokenNumber) {\r
269 Idx++;\r
270 if (Idx == SizeOfExMapTable) {\r
271 //\r
272 // Exceed the length of ExMap Table\r
273 //\r
274 return PCD_INVALID_TOKEN_NUMBER;\r
275 } else if (ExMapTable[Idx].ExGuidIndex == GuidTableIdx) {\r
276 //\r
277 // Found the next match\r
278 //\r
279 return ExMapTable[Idx].ExTokenNumber;\r
280 } else {\r
281 //\r
282 // Guid has been changed. It is the next Token Space Guid.\r
283 // We should flag no more TokenNumber.\r
284 //\r
285 return PCD_INVALID_TOKEN_NUMBER;\r
286 }\r
287 }\r
288 }\r
289 }\r
290 \r
291 return PCD_INVALID_TOKEN_NUMBER;\r
292}\r
293 \r
294\r
295\r
296\r
297VOID\r
298BuildPcdDxeDataBase (\r
299 VOID\r
300 )\r
301{\r
302 PEI_PCD_DATABASE *PeiDatabase;\r
303 EFI_HOB_GUID_TYPE *GuidHob;\r
304 UINTN Idx;\r
305\r
306 mPcdDatabase = AllocateZeroPool (sizeof(PCD_DATABASE));\r
307 ASSERT (mPcdDatabase != NULL);\r
308\r
309 GuidHob = GetFirstGuidHob (&gPcdDataBaseHobGuid);\r
310\r
311 if (GuidHob != NULL) {\r
312\r
313 //\r
314 // We will copy over the PEI phase's PCD Database.\r
315 // \r
316 // If no PEIMs use dynamic Pcd Entry, the Pcd Service PEIM\r
317 // should not be included at all. So the GuidHob could\r
318 // be NULL. If it is NULL, we just copy over the DXE Default\r
319 // Value to PCD Database.\r
320 //\r
321 \r
322 PeiDatabase = (PEI_PCD_DATABASE *) GET_GUID_HOB_DATA (GuidHob);\r
323 //\r
324 // Copy PCD Entries refereneced in PEI phase to PCD DATABASE\r
325 //\r
326 CopyMem (&mPcdDatabase->PeiDb, PeiDatabase, sizeof (PEI_PCD_DATABASE));\r
327 }\r
328\r
329 //\r
330 // Copy PCD Entries with default value to PCD DATABASE\r
331 //\r
332 CopyMem (&mPcdDatabase->DxeDb.Init, &gDXEPcdDbInit, sizeof(DXE_PCD_DATABASE_INIT));\r
333\r
334\r
335 //\r
336 // Initialized the Callback Function Table\r
337 //\r
338\r
339 if (PCD_TOTAL_TOKEN_NUMBER != 0) {\r
340 mCallbackFnTable = AllocateZeroPool (PCD_TOTAL_TOKEN_NUMBER * sizeof (LIST_ENTRY));\r
341 }\r
342 \r
343 for (Idx = 0; Idx < PCD_TOTAL_TOKEN_NUMBER; Idx++) {\r
344 InitializeListHead (&mCallbackFnTable[Idx]);\r
345 }\r
346 \r
347 return;\r
348}\r
349\r
350\r
351\r
352EFI_STATUS\r
353GetHiiVariable (\r
354 IN EFI_GUID *VariableGuid,\r
355 IN UINT16 *VariableName,\r
356 OUT VOID ** VariableData,\r
357 OUT UINTN *VariableSize\r
358 )\r
359{\r
360 UINTN Size;\r
361 EFI_STATUS Status;\r
362 VOID *Buffer;\r
363\r
364 Size = 0;\r
365 Buffer = NULL;\r
366 \r
367 Status = EfiGetVariable (\r
368 (UINT16 *)VariableName,\r
369 VariableGuid,\r
370 NULL,\r
371 &Size,\r
372 Buffer\r
373 );\r
374 \r
375 if (Status == EFI_BUFFER_TOO_SMALL) {\r
376\r
377 Buffer = AllocatePool (Size);\r
378\r
379 ASSERT (Buffer != NULL);\r
380\r
381 Status = EfiGetVariable (\r
382 VariableName,\r
383 VariableGuid,\r
384 NULL,\r
385 &Size,\r
386 Buffer\r
387 );\r
388\r
389 ASSERT (Status == EFI_SUCCESS);\r
390 }\r
391\r
392 *VariableData = Buffer;\r
393 *VariableSize = Size;\r
394\r
395 return Status;\r
396\r
397}\r
398\r
399\r
400UINT32\r
401GetSkuEnabledTokenNumber (\r
402 UINT32 LocalTokenNumber,\r
403 UINTN Size,\r
404 BOOLEAN IsPeiDb\r
405 ) \r
406{\r
407 SKU_HEAD *SkuHead;\r
408 SKU_ID *SkuIdTable;\r
409 INTN i;\r
410 UINT8 *Value;\r
411 SKU_ID *PhaseSkuIdTable;\r
412 UINT8 *PcdDb;\r
413\r
414 ASSERT ((LocalTokenNumber & PCD_TYPE_SKU_ENABLED) == 0);\r
415\r
416 PcdDb = IsPeiDb ? (UINT8 *) &mPcdDatabase->PeiDb : (UINT8 *) &mPcdDatabase->DxeDb;\r
417\r
418 SkuHead = (SKU_HEAD *) (PcdDb + (LocalTokenNumber & PCD_DATABASE_OFFSET_MASK));\r
419 Value = (UINT8 *) (PcdDb + SkuHead->SkuDataStartOffset); \r
420\r
421 PhaseSkuIdTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.SkuIdTable :\r
422 mPcdDatabase->DxeDb.Init.SkuIdTable;\r
423 \r
424 SkuIdTable = &PhaseSkuIdTable[SkuHead->SkuIdTableOffset];\r
425 \r
426 for (i = 0; i < SkuIdTable[0]; i++) {\r
427 if (mPcdDatabase->PeiDb.Init.SystemSkuId == SkuIdTable[i + 1]) {\r
428 break;\r
429 }\r
430 }\r
431 ASSERT (i < SkuIdTable[0]);\r
432\r
433 switch (LocalTokenNumber & ~PCD_DATABASE_OFFSET_MASK) {\r
434 case PCD_TYPE_VPD:\r
435 Value = (UINT8 *) &(((VPD_HEAD *) Value)[i]);\r
436 return (UINT32) ((Value - PcdDb) | PCD_TYPE_VPD);\r
437\r
438 case PCD_TYPE_HII:\r
439 Value = (UINT8 *) &(((VARIABLE_HEAD *) Value)[i]);\r
440 return (UINT32) ((Value - PcdDb) | PCD_TYPE_HII);\r
441 \r
442 case PCD_TYPE_DATA:\r
443 Value += Size * i;\r
444 return (UINT32) (Value - PcdDb);\r
445 \r
446 default:\r
447 ASSERT (FALSE);\r
448 }\r
449\r
450 ASSERT (FALSE);\r
451\r
452 return 0;\r
453 \r
454}\r
455\r
456\r
457\r
458\r
459\r
460VOID\r
461InvokeCallbackOnSet (\r
462 UINT32 ExTokenNumber,\r
463 CONST EFI_GUID *Guid, OPTIONAL\r
464 UINTN TokenNumber,\r
465 VOID *Data,\r
466 UINTN Size\r
467 )\r
468{\r
469 CALLBACK_FN_ENTRY *FnTableEntry;\r
470 LIST_ENTRY *ListHead;\r
471 LIST_ENTRY *ListNode;\r
472\r
473 //\r
474 // TokenNumber Zero is reserved as PCD_INVALID_TOKEN_NUMBER.\r
475 // We have to decrement TokenNumber by 1 to make it usable\r
476 // as the array index.\r
477 //\r
478 TokenNumber--;\r
479 \r
480 ListHead = &mCallbackFnTable[TokenNumber];\r
481 ListNode = GetFirstNode (ListHead);\r
482\r
483 while (ListNode != ListHead) {\r
484 FnTableEntry = CR_FNENTRY_FROM_LISTNODE(ListNode, CALLBACK_FN_ENTRY, Node);\r
485\r
486 FnTableEntry->CallbackFn(Guid, \r
487 (Guid == NULL) ? TokenNumber : ExTokenNumber,\r
488 Data,\r
489 Size);\r
490 \r
491 ListNode = GetNextNode (ListHead, ListNode);\r
492 }\r
493 \r
494 return;\r
495}\r
496\r
497\r
498\r
499\r
500EFI_STATUS\r
501SetWorker (\r
502 UINTN TokenNumber,\r
503 VOID *Data,\r
504 UINTN Size,\r
505 BOOLEAN PtrType\r
506 )\r
507{\r
508 UINT32 *LocalTokenNumberTable;\r
509 BOOLEAN IsPeiDb;\r
510 UINT32 LocalTokenNumber;\r
511 EFI_GUID *GuidTable;\r
512 UINT16 *StringTable;\r
513 EFI_GUID *Guid;\r
514 UINT16 *Name;\r
515 UINTN VariableOffset;\r
516 VOID *InternalData;\r
517 VARIABLE_HEAD *VariableHead;\r
518 UINTN Offset;\r
519 UINT8 *PcdDb;\r
520\r
521 //\r
522 // TokenNumber Zero is reserved as PCD_INVALID_TOKEN_NUMBER.\r
523 // We have to decrement TokenNumber by 1 to make it usable\r
524 // as the array index.\r
525 //\r
526 TokenNumber--;\r
527 \r
528 ASSERT (TokenNumber < PCD_TOTAL_TOKEN_NUMBER);\r
529\r
530 if (PtrType) {\r
531 ASSERT (Size <= DxePcdGetSize (TokenNumber + 1));\r
532 } else {\r
533 ASSERT (Size == DxePcdGetSize (TokenNumber + 1));\r
534 }\r
535 \r
536 IsPeiDb = (TokenNumber < PEI_LOCAL_TOKEN_NUMBER) ? TRUE : FALSE;\r
537\r
538 LocalTokenNumberTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.LocalTokenNumberTable : \r
539 mPcdDatabase->DxeDb.Init.LocalTokenNumberTable;\r
540\r
541 if ((TokenNumber < PEI_NEX_TOKEN_NUMBER) ||\r
542 (TokenNumber >= PEI_LOCAL_TOKEN_NUMBER || TokenNumber < (PEI_LOCAL_TOKEN_NUMBER + DXE_NEX_TOKEN_NUMBER))) {\r
543 InvokeCallbackOnSet (0, NULL, TokenNumber + 1, Data, Size);\r
544 }\r
545\r
546 TokenNumber = IsPeiDb ? TokenNumber\r
547 : TokenNumber - PEI_LOCAL_TOKEN_NUMBER;\r
548\r
549 LocalTokenNumber = LocalTokenNumberTable[TokenNumber];\r
550 \r
551 if ((LocalTokenNumber & PCD_TYPE_SKU_ENABLED) == PCD_TYPE_SKU_ENABLED) {\r
552 LocalTokenNumber = GetSkuEnabledTokenNumber (LocalTokenNumber & ~PCD_TYPE_SKU_ENABLED, Size, IsPeiDb);\r
553 }\r
554\r
555 Offset = LocalTokenNumber & PCD_DATABASE_OFFSET_MASK;\r
556\r
557 PcdDb = IsPeiDb ? ((UINT8 *) &mPcdDatabase->PeiDb) : ((UINT8 *) &mPcdDatabase->DxeDb);\r
558\r
559 StringTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.StringTable :\r
560 mPcdDatabase->DxeDb.Init.StringTable;\r
561 \r
562 InternalData = PcdDb + Offset;\r
563\r
564 switch (LocalTokenNumber & ~PCD_DATABASE_OFFSET_MASK) {\r
565 case PCD_TYPE_VPD:\r
566 ASSERT (FALSE);\r
567 return EFI_INVALID_PARAMETER;\r
568 \r
569 case PCD_TYPE_STRING:\r
570 CopyMem (&StringTable[*((UINT16 *)InternalData)], Data, Size);\r
571 return EFI_SUCCESS;\r
572\r
573 case PCD_TYPE_HII:\r
574 //\r
575 // Bug Bug: Please implement this\r
576 //\r
577 GuidTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.GuidTable :\r
578 mPcdDatabase->DxeDb.Init.GuidTable;\r
579 \r
580 VariableHead = (VARIABLE_HEAD *) (PcdDb + Offset);\r
581 \r
582 Guid = &(GuidTable[VariableHead->GuidTableIndex]);\r
583 Name = &(StringTable[VariableHead->StringIndex]);\r
584 VariableOffset = VariableHead->Offset;\r
585\r
586 return SetHiiVariable (Guid, Name, Data, Size, VariableOffset);\r
587\r
588 case PCD_TYPE_DATA:\r
589 if (PtrType) {\r
590 CopyMem (InternalData, Data, Size);\r
591 return EFI_SUCCESS;\r
592 }\r
593\r
594 switch (Size) {\r
595 case sizeof(UINT8):\r
596 *((UINT8 *) InternalData) = *((UINT8 *) Data);\r
597 return EFI_SUCCESS;\r
598\r
599 case sizeof(UINT16):\r
600 *((UINT16 *) InternalData) = *((UINT16 *) Data);\r
601 return EFI_SUCCESS;\r
602\r
603 case sizeof(UINT32):\r
604 *((UINT32 *) InternalData) = *((UINT32 *) Data);\r
605 return EFI_SUCCESS;\r
606\r
607 case sizeof(UINT64):\r
608 *((UINT64 *) InternalData) = *((UINT64 *) Data);\r
609 return EFI_SUCCESS;\r
610\r
611 default:\r
612 ASSERT (FALSE);\r
613 return EFI_NOT_FOUND;\r
614 }\r
615\r
616 default:\r
617 ASSERT (FALSE);\r
618 break;\r
619 }\r
620 \r
621 ASSERT (FALSE);\r
622 return EFI_NOT_FOUND;\r
623}\r
624\r
625\r
626\r
627\r
628\r
629VOID *\r
630ExGetWorker (\r
631 IN CONST EFI_GUID *Guid,\r
632 IN UINTN ExTokenNumber,\r
633 IN UINTN GetSize\r
634 ) \r
635{\r
636 return GetWorker(GetExPcdTokenNumber (Guid, (UINT32) ExTokenNumber), GetSize);\r
637}\r
638\r
639\r
640\r
641\r
642\r
643EFI_STATUS\r
644ExSetWorker (\r
645 IN UINTN ExTokenNumber,\r
646 IN CONST EFI_GUID *Guid,\r
647 VOID *Data,\r
648 UINTN SetSize,\r
649 BOOLEAN PtrType\r
650 )\r
651{\r
652 UINTN TokenNumber;\r
653 \r
654 TokenNumber = GetExPcdTokenNumber (Guid, (UINT32) ExTokenNumber);\r
655\r
656 InvokeCallbackOnSet ((UINT32) ExTokenNumber, Guid, TokenNumber, Data, SetSize);\r
657\r
658 SetWorker (TokenNumber, Data, SetSize, PtrType);\r
659\r
660 return EFI_SUCCESS;\r
661 \r
662}\r
663\r
664\r
665\r
666\r
667EFI_STATUS\r
668SetHiiVariable (\r
669 IN EFI_GUID *VariableGuid,\r
670 IN UINT16 *VariableName,\r
671 IN CONST VOID *Data,\r
672 IN UINTN DataSize,\r
673 IN UINTN Offset\r
674 )\r
675{\r
676 UINTN Size;\r
677 VOID *Buffer;\r
678 EFI_STATUS Status;\r
679 UINT32 Attribute;\r
680\r
681 Size = 0;\r
682\r
683 Status = EfiGetVariable (\r
684 (UINT16 *)VariableName,\r
685 VariableGuid,\r
686 &Attribute,\r
687 &Size,\r
688 NULL\r
689 );\r
690\r
691 if (Status == EFI_BUFFER_TOO_SMALL) {\r
692\r
693 Buffer = AllocatePool (Size);\r
694\r
695 ASSERT (Buffer != NULL);\r
696\r
697 Status = EfiGetVariable (\r
698 VariableName,\r
699 VariableGuid,\r
700 &Attribute,\r
701 &Size,\r
702 Buffer\r
703 );\r
704 \r
705 ASSERT_EFI_ERROR (Status);\r
706\r
707 CopyMem ((UINT8 *)Buffer + Offset, Data, DataSize);\r
708\r
709 } else {\r
710\r
711 Attribute = EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS;\r
712 Size = DataSize + Offset;\r
713 Buffer = AllocateZeroPool (Size);\r
714 ASSERT (Buffer != NULL);\r
715 CopyMem ((UINT8 *)Buffer + Offset, Data, DataSize);\r
716 \r
717 }\r
718\r
719 return EfiSetVariable (\r
720 VariableName,\r
721 VariableGuid,\r
722 Attribute,\r
723 Size,\r
724 Buffer\r
725 );\r
726\r
727}\r
728\r
729\r
730\r
731\r
732\r
733UINTN \r
734GetExPcdTokenNumber (\r
735 IN CONST EFI_GUID *Guid,\r
736 IN UINT32 ExTokenNumber\r
737 )\r
738{\r
739 UINT32 i;\r
740 DYNAMICEX_MAPPING *ExMap;\r
741 EFI_GUID *GuidTable;\r
742 EFI_GUID *MatchGuid;\r
743 UINTN MatchGuidIdx;\r
744\r
745 ExMap = mPcdDatabase->PeiDb.Init.ExMapTable;\r
746 GuidTable = mPcdDatabase->PeiDb.Init.GuidTable;\r
747 \r
748 MatchGuid = ScanGuid (GuidTable, sizeof(mPcdDatabase->PeiDb.Init.GuidTable), Guid);\r
749 ASSERT (MatchGuid != NULL);\r
750\r
751 MatchGuidIdx = MatchGuid - GuidTable;\r
752 \r
753 for (i = 0; i < PEI_EXMAPPING_TABLE_SIZE; i++) {\r
754 if ((ExTokenNumber == ExMap[i].ExTokenNumber) &&\r
755 (MatchGuidIdx == ExMap[i].ExGuidIndex)) {\r
756 return ExMap[i].LocalTokenNumber;\r
757\r
758 }\r
759 }\r
760 \r
761 ExMap = mPcdDatabase->DxeDb.Init.ExMapTable;\r
762 GuidTable = mPcdDatabase->DxeDb.Init.GuidTable;\r
763\r
764 MatchGuid = ScanGuid (GuidTable, sizeof(mPcdDatabase->DxeDb.Init.GuidTable), Guid);\r
765 ASSERT (MatchGuid != NULL);\r
766\r
767 MatchGuidIdx = MatchGuid - GuidTable;\r
768 \r
769 for (i = 0; i < DXE_EXMAPPING_TABLE_SIZE; i++) {\r
770 if ((ExTokenNumber == ExMap[i].ExTokenNumber) &&\r
771 (MatchGuidIdx == ExMap[i].ExGuidIndex)) {\r
772 return ExMap[i].LocalTokenNumber + PEI_LOCAL_TOKEN_NUMBER;\r
773 }\r
774 }\r
775\r
776 ASSERT (FALSE);\r
777\r
778 return 0;\r
779}\r
780\r