Refine some internal functions of PCD Driver.
[mirror_edk2.git] / EdkModulePkg / Universal / PCD / Dxe / Service.c
CommitLineData
878ddf1f 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
878ddf1f 17#include "Service.h"\r
18\r
878ddf1f 19\r
52e1905d 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
878ddf1f 24\r
4c114006 25PCD_DATABASE * mPcdDatabase;\r
878ddf1f 26\r
4c114006 27LIST_ENTRY mCallbackFnTable[PCD_TOTAL_TOKEN_NUMBER];\r
878ddf1f 28\r
52e1905d 29VOID *\r
9d6d8b24 30GetWorker (\r
31 PCD_TOKEN_NUMBER TokenNumber,\r
32 UINTN GetSize\r
33 )\r
878ddf1f 34{\r
9d6d8b24 35 UINT32 *LocalTokenNumberTable;\r
36 UINT16 *SizeTable;\r
37 BOOLEAN IsPeiDb;\r
38 UINTN Size;\r
52e1905d 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
9d6d8b24 51 UINT32 LocalTokenNumber;\r
52\r
53\r
54 ASSERT (TokenNumber < PCD_TOTAL_TOKEN_NUMBER);\r
55\r
56 Size = DxePcdGetSize (TokenNumber);\r
57 ASSERT (GetSize == Size || GetSize == 0);\r
52e1905d 58\r
9d6d8b24 59 \r
60 IsPeiDb = (TokenNumber <= PEI_LOCAL_TOKEN_NUMBER) ? TRUE : FALSE;\r
61\r
62 LocalTokenNumberTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.LocalTokenNumberTable : \r
63 mPcdDatabase->DxeDb.Init.LocalTokenNumberTable;\r
64\r
65 SizeTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.SizeTable: \r
66 mPcdDatabase->DxeDb.Init.SizeTable;\r
67\r
68 TokenNumber = IsPeiDb ? TokenNumber :\r
69 TokenNumber - PEI_LOCAL_TOKEN_NUMBER;\r
70\r
71 LocalTokenNumber = LocalTokenNumberTable[TokenNumber];\r
72 \r
52e1905d 73 if ((LocalTokenNumber & PCD_TYPE_SKU_ENABLED) == PCD_TYPE_SKU_ENABLED) {\r
74 LocalTokenNumber = GetSkuEnabledTokenNumber (LocalTokenNumber & ~PCD_TYPE_SKU_ENABLED, Size, IsPeiDb);\r
75 }\r
76\r
4c114006 77 PcdDb = IsPeiDb ? ((UINT8 *) &mPcdDatabase->PeiDb) : ((UINT8 *) &mPcdDatabase->DxeDb);\r
78 StringTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.StringTable :\r
79 mPcdDatabase->DxeDb.Init.StringTable;\r
52e1905d 80 \r
81 Offset = LocalTokenNumber & PCD_DATABASE_OFFSET_MASK;\r
82 \r
83 switch (LocalTokenNumber & ~PCD_DATABASE_OFFSET_MASK) {\r
84 case PCD_TYPE_VPD:\r
85 VpdHead = (VPD_HEAD *) ((UINT8 *) PcdDb + Offset);\r
86 return (VOID *) (FixedPcdGet32(PcdVpdBaseAddress) + VpdHead->Offset);\r
87 \r
88 case PCD_TYPE_HII:\r
4c114006 89 GuidTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.GuidTable :\r
90 mPcdDatabase->DxeDb.Init.GuidTable;\r
52e1905d 91 \r
92 VariableHead = (VARIABLE_HEAD *) (PcdDb + Offset);\r
93 \r
94 Guid = &(GuidTable[VariableHead->GuidTableIndex]);\r
95 Name = &(StringTable[VariableHead->StringIndex]);\r
878ddf1f 96\r
52e1905d 97 Status = GetHiiVariable (Guid, Name, &Data, &DataSize);\r
98 ASSERT_EFI_ERROR (Status);\r
99 ASSERT (DataSize >= (UINTN) (VariableHead->Offset + Size));\r
878ddf1f 100\r
52e1905d 101 return (UINT8 *) Data + VariableHead->Offset;\r
878ddf1f 102\r
52e1905d 103 case PCD_TYPE_STRING:\r
104 StringTableIdx = (UINT16) *((UINT8 *) PcdDb + Offset);\r
105 return (VOID *) &StringTable[StringTableIdx];\r
878ddf1f 106\r
52e1905d 107 case PCD_TYPE_DATA:\r
108 return (VOID *) ((UINT8 *) PcdDb + Offset);\r
109 break;\r
878ddf1f 110\r
52e1905d 111 default:\r
112 ASSERT (FALSE);\r
113 break;\r
114 \r
115 }\r
878ddf1f 116\r
52e1905d 117 ASSERT (FALSE);\r
118 \r
119 return NULL;\r
52e1905d 120 \r
52e1905d 121}\r
878ddf1f 122\r
878ddf1f 123\r
124\r
52e1905d 125EFI_STATUS\r
126DxeRegisterCallBackWorker (\r
9d6d8b24 127 IN PCD_TOKEN_NUMBER TokenNumber,\r
52e1905d 128 IN CONST GUID *Guid, OPTIONAL\r
4c114006 129 IN PCD_PROTOCOL_CALLBACK CallBackFunction\r
52e1905d 130)\r
131{\r
4c114006 132 CALLBACK_FN_ENTRY *FnTableEntry;\r
4c114006 133 LIST_ENTRY *ListHead;\r
134 LIST_ENTRY *ListNode;\r
135\r
136 if (Guid != NULL) {\r
9d6d8b24 137 TokenNumber = GetExPcdTokenNumber (Guid, TokenNumber);\r
4c114006 138 }\r
139\r
140 ListHead = &mCallbackFnTable[TokenNumber];\r
141 ListNode = GetFirstNode (ListHead);\r
142\r
143 while (ListNode != ListHead) {\r
144 FnTableEntry = CR_FNENTRY_FROM_LISTNODE(ListNode, CALLBACK_FN_ENTRY, Node);\r
145\r
146 if (FnTableEntry->CallbackFn == CallBackFunction) {\r
147 //\r
148 // We only allow a Callback function to be register once\r
149 // for a TokenNumber. So just return EFI_SUCCESS\r
150 //\r
151 return EFI_SUCCESS;\r
152 }\r
153 ListNode = GetNextNode (ListHead, ListNode);\r
154 }\r
155\r
156 FnTableEntry = AllocatePool (sizeof(CALLBACK_FN_ENTRY));\r
157 ASSERT (FnTableEntry != NULL);\r
158\r
159 FnTableEntry->CallbackFn = CallBackFunction;\r
160 InsertTailList (ListHead, &FnTableEntry->Node);\r
52e1905d 161 \r
162 return EFI_SUCCESS;\r
878ddf1f 163}\r
164\r
165\r
4c114006 166\r
167\r
52e1905d 168EFI_STATUS\r
4c114006 169DxeUnRegisterCallBackWorker (\r
9d6d8b24 170 IN PCD_TOKEN_NUMBER TokenNumber,\r
4c114006 171 IN CONST GUID *Guid, OPTIONAL\r
172 IN PCD_PROTOCOL_CALLBACK CallBackFunction\r
173)\r
174{\r
175 CALLBACK_FN_ENTRY *FnTableEntry;\r
4c114006 176 LIST_ENTRY *ListHead;\r
177 LIST_ENTRY *ListNode;\r
178\r
179 if (Guid != NULL) {\r
9d6d8b24 180 TokenNumber = GetExPcdTokenNumber (Guid, TokenNumber);\r
4c114006 181 }\r
182\r
183 ListHead = &mCallbackFnTable[TokenNumber];\r
184 ListNode = GetFirstNode (ListHead);\r
185\r
186 while (ListNode != ListHead) {\r
187 FnTableEntry = CR_FNENTRY_FROM_LISTNODE(ListNode, CALLBACK_FN_ENTRY, Node);\r
188\r
189 if (FnTableEntry->CallbackFn == CallBackFunction) {\r
190 //\r
191 // We only allow a Callback function to be register once\r
192 // for a TokenNumber. So we can safely remove the Node from\r
193 // the Link List and return EFI_SUCCESS.\r
194 //\r
195 RemoveEntryList (ListNode);\r
196 FreePool (FnTableEntry);\r
197 \r
198 return EFI_SUCCESS;\r
199 }\r
200 ListNode = GetNextNode (ListHead, ListNode);\r
201 }\r
202\r
203 return EFI_INVALID_PARAMETER;\r
204}\r
205\r
206\r
207\r
208PCD_TOKEN_NUMBER\r
209ExGetNextTokeNumber (\r
210 IN CONST EFI_GUID *Guid,\r
211 IN PCD_TOKEN_NUMBER TokenNumber,\r
212 IN EFI_GUID *GuidTable,\r
213 IN UINTN SizeOfGuidTable,\r
214 IN DYNAMICEX_MAPPING *ExMapTable,\r
215 IN UINTN SizeOfExMapTable\r
878ddf1f 216 )\r
217{\r
4c114006 218 EFI_GUID *MatchGuid;\r
219 UINTN Idx;\r
220 UINTN GuidTableIdx;\r
221 BOOLEAN Found;\r
222\r
223 MatchGuid = ScanGuid (GuidTable, SizeOfGuidTable, Guid);\r
224 if (MatchGuid == NULL) {\r
225 return PCD_INVALID_TOKEN_NUMBER;\r
226 }\r
227\r
228 Found = FALSE;\r
229 GuidTableIdx = MatchGuid - GuidTable;\r
230 for (Idx = 0; Idx < SizeOfExMapTable; Idx++) {\r
231 if (ExMapTable[Idx].ExGuidIndex == GuidTableIdx) {\r
232 Found = TRUE;\r
233 break;\r
234 }\r
235 }\r
236\r
237 if (Found) {\r
238 if (TokenNumber == PCD_INVALID_TOKEN_NUMBER) {\r
239 return ExMapTable[Idx].ExTokenNumber;\r
240 }\r
241 \r
242 for ( ; Idx < SizeOfExMapTable; Idx++) {\r
243 if (ExMapTable[Idx].ExTokenNumber == TokenNumber) {\r
244 Idx++;\r
245 if (Idx == SizeOfExMapTable) {\r
246 //\r
247 // Exceed the length of ExMap Table\r
248 //\r
249 return PCD_INVALID_TOKEN_NUMBER;\r
250 } else if (ExMapTable[Idx].ExGuidIndex == GuidTableIdx) {\r
251 //\r
252 // Found the next match\r
253 //\r
254 return ExMapTable[Idx].ExTokenNumber;\r
255 } else {\r
256 //\r
257 // Guid has been changed. It is the next Token Space Guid.\r
258 // We should flag no more TokenNumber.\r
259 //\r
260 return PCD_INVALID_TOKEN_NUMBER;\r
261 }\r
262 }\r
263 }\r
264 }\r
265 \r
266 return PCD_INVALID_TOKEN_NUMBER;\r
878ddf1f 267}\r
4c114006 268 \r
878ddf1f 269\r
270\r
271\r
52e1905d 272VOID\r
273BuildPcdDxeDataBase (\r
274 VOID\r
275)\r
878ddf1f 276{\r
52e1905d 277 PEI_PCD_DATABASE *PeiDatabase;\r
278 EFI_HOB_GUID_TYPE *GuidHob;\r
4c114006 279 UINTN Idx;\r
878ddf1f 280\r
4c114006 281 mPcdDatabase = AllocateZeroPool (sizeof(PCD_DATABASE));\r
282 ASSERT (mPcdDatabase != NULL);\r
878ddf1f 283\r
52e1905d 284 GuidHob = GetFirstGuidHob (&gPcdDataBaseHobGuid);\r
285 ASSERT (GuidHob != NULL);\r
878ddf1f 286\r
52e1905d 287 PeiDatabase = (PEI_PCD_DATABASE *) GET_GUID_HOB_DATA (GuidHob);\r
288 //\r
289 // Copy PCD Entries refereneced in PEI phase to PCD DATABASE\r
290 //\r
4c114006 291 CopyMem (&mPcdDatabase->PeiDb, PeiDatabase, sizeof (PEI_PCD_DATABASE));\r
52e1905d 292\r
293 //\r
294 // Copy PCD Entries with default value to PCD DATABASE\r
295 //\r
4c114006 296 CopyMem (&mPcdDatabase->DxeDb.Init, &gDXEPcdDbInit, sizeof(DXE_PCD_DATABASE_INIT));\r
297\r
298\r
299 //\r
300 // Initialized the Callback Function Table\r
301 //\r
302 for (Idx = 0; Idx < PCD_TOTAL_TOKEN_NUMBER; Idx++) {\r
303 InitializeListHead (&mCallbackFnTable[Idx]);\r
304 }\r
52e1905d 305 \r
306 return;\r
878ddf1f 307}\r
308\r
309\r
310\r
52e1905d 311EFI_STATUS\r
312GetHiiVariable (\r
313 IN EFI_GUID *VariableGuid,\r
314 IN UINT16 *VariableName,\r
315 OUT VOID ** VariableData,\r
316 OUT UINTN *VariableSize\r
878ddf1f 317 )\r
318{\r
52e1905d 319 UINTN Size;\r
320 EFI_STATUS Status;\r
321 VOID *Buffer;\r
878ddf1f 322\r
52e1905d 323 Status = EfiGetVariable (\r
324 (UINT16 *)VariableName,\r
325 VariableGuid,\r
326 NULL,\r
327 &Size,\r
328 NULL\r
329 );\r
330 ASSERT (Status == EFI_BUFFER_TOO_SMALL);\r
878ddf1f 331\r
52e1905d 332 Buffer = AllocatePool (Size);\r
878ddf1f 333\r
52e1905d 334 ASSERT (Buffer != NULL);\r
878ddf1f 335\r
52e1905d 336 Status = EfiGetVariable (\r
337 VariableName,\r
338 VariableGuid,\r
339 NULL,\r
340 &Size,\r
341 Buffer\r
342 );\r
878ddf1f 343\r
52e1905d 344 return Status;\r
878ddf1f 345\r
878ddf1f 346}\r
347\r
348\r
52e1905d 349UINT32\r
350GetSkuEnabledTokenNumber (\r
351 UINT32 LocalTokenNumber,\r
352 UINTN Size,\r
353 BOOLEAN IsPeiDb\r
354 ) \r
355{\r
356 SKU_HEAD *SkuHead;\r
357 SKU_ID *SkuIdTable;\r
358 INTN i;\r
359 UINT8 *Value;\r
360 SKU_ID *PhaseSkuIdTable;\r
361 UINT8 *PcdDb;\r
878ddf1f 362\r
52e1905d 363 ASSERT ((LocalTokenNumber & PCD_TYPE_SKU_ENABLED) == 0);\r
878ddf1f 364\r
4c114006 365 PcdDb = IsPeiDb ? (UINT8 *) &mPcdDatabase->PeiDb : (UINT8 *) &mPcdDatabase->DxeDb;\r
878ddf1f 366\r
52e1905d 367 SkuHead = (SKU_HEAD *) (PcdDb + (LocalTokenNumber & PCD_DATABASE_OFFSET_MASK));\r
368 Value = (UINT8 *) (PcdDb + SkuHead->SkuDataStartOffset); \r
878ddf1f 369\r
4c114006 370 PhaseSkuIdTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.SkuIdTable :\r
371 mPcdDatabase->DxeDb.Init.SkuIdTable;\r
52e1905d 372 \r
373 SkuIdTable = &PhaseSkuIdTable[SkuHead->SkuIdTableOffset];\r
374 \r
375 for (i = 0; i < SkuIdTable[0]; i++) {\r
4c114006 376 if (mPcdDatabase->PeiDb.Init.SystemSkuId == SkuIdTable[i + 1]) {\r
52e1905d 377 break;\r
878ddf1f 378 }\r
878ddf1f 379 }\r
52e1905d 380 ASSERT (i < SkuIdTable[0]);\r
878ddf1f 381\r
52e1905d 382 switch (LocalTokenNumber & ~PCD_DATABASE_OFFSET_MASK) {\r
383 case PCD_TYPE_VPD:\r
384 Value = (UINT8 *) &(((VPD_HEAD *) Value)[i]);\r
385 return ((Value - PcdDb) | PCD_TYPE_VPD);\r
878ddf1f 386\r
52e1905d 387 case PCD_TYPE_HII:\r
388 Value = (UINT8 *) &(((VARIABLE_HEAD *) Value)[i]);\r
389 return ((Value - PcdDb) | PCD_TYPE_HII);\r
390 \r
391 case PCD_TYPE_DATA:\r
392 Value += Size * i;\r
393 return (Value - PcdDb);\r
394 \r
395 default:\r
396 ASSERT (FALSE);\r
397 }\r
398\r
399 ASSERT (FALSE);\r
400\r
401 return 0;\r
878ddf1f 402 \r
403}\r
404\r
878ddf1f 405\r
878ddf1f 406\r
878ddf1f 407\r
878ddf1f 408\r
52e1905d 409VOID\r
410InvokeCallbackOnSet (\r
411 UINT32 ExTokenNumber,\r
412 CONST EFI_GUID *Guid, OPTIONAL\r
413 UINTN TokenNumber,\r
414 VOID *Data,\r
415 UINTN Size\r
416 )\r
417{\r
4c114006 418 CALLBACK_FN_ENTRY *FnTableEntry;\r
419 LIST_ENTRY *ListHead;\r
420 LIST_ENTRY *ListNode;\r
421\r
422 ListHead = &mCallbackFnTable[TokenNumber];\r
423 ListNode = GetFirstNode (ListHead);\r
424\r
425 while (ListNode != ListHead) {\r
426 FnTableEntry = CR_FNENTRY_FROM_LISTNODE(ListNode, CALLBACK_FN_ENTRY, Node);\r
427\r
428 FnTableEntry->CallbackFn(Guid, \r
429 (Guid == NULL) ? TokenNumber : ExTokenNumber,\r
430 Data,\r
431 Size);\r
432 \r
433 ListNode = GetNextNode (ListHead, ListNode);\r
434 }\r
435 \r
52e1905d 436 return;\r
878ddf1f 437}\r
438\r
439\r
440\r
52e1905d 441\r
878ddf1f 442EFI_STATUS\r
52e1905d 443SetWorker (\r
0653eb89 444 PCD_TOKEN_NUMBER TokenNumber,\r
445 VOID *Data,\r
446 UINTN Size,\r
447 BOOLEAN PtrType\r
878ddf1f 448 )\r
449{\r
52e1905d 450 UINT32 *LocalTokenNumberTable;\r
451 BOOLEAN IsPeiDb;\r
9d6d8b24 452 UINT32 LocalTokenNumber;\r
453 EFI_GUID *GuidTable;\r
454 UINT16 *StringTable;\r
455 EFI_GUID *Guid;\r
456 UINT16 *Name;\r
457 VOID *InternalData;\r
458 VARIABLE_HEAD *VariableHead;\r
459 UINTN Offset;\r
460 UINT8 *PcdDb;\r
878ddf1f 461\r
878ddf1f 462\r
52e1905d 463 ASSERT (TokenNumber < PCD_TOTAL_TOKEN_NUMBER);\r
878ddf1f 464\r
52e1905d 465 if (PtrType) {\r
466 ASSERT (Size <= DxePcdGetSize (TokenNumber));\r
467 } else {\r
468 ASSERT (Size == DxePcdGetSize (TokenNumber));\r
878ddf1f 469 }\r
878ddf1f 470 \r
52e1905d 471 IsPeiDb = (TokenNumber <= PEI_LOCAL_TOKEN_NUMBER) ? TRUE : FALSE;\r
878ddf1f 472\r
4c114006 473 LocalTokenNumberTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.LocalTokenNumberTable : \r
474 mPcdDatabase->DxeDb.Init.LocalTokenNumberTable;\r
878ddf1f 475\r
9d6d8b24 476 if ((TokenNumber < PEI_NEX_TOKEN_NUMBER) ||\r
477 (TokenNumber >= PEI_LOCAL_TOKEN_NUMBER || TokenNumber < (PEI_LOCAL_TOKEN_NUMBER + DXE_NEX_TOKEN_NUMBER))) {\r
478 InvokeCallbackOnSet (0, NULL, TokenNumber, Data, Size);\r
479 }\r
0653eb89 480\r
52e1905d 481 TokenNumber = IsPeiDb ? TokenNumber\r
482 : TokenNumber - PEI_LOCAL_TOKEN_NUMBER;\r
878ddf1f 483\r
9d6d8b24 484 LocalTokenNumber = LocalTokenNumberTable[TokenNumber];\r
52e1905d 485 \r
52e1905d 486 if ((LocalTokenNumber & PCD_TYPE_SKU_ENABLED) == PCD_TYPE_SKU_ENABLED) {\r
487 LocalTokenNumber = GetSkuEnabledTokenNumber (LocalTokenNumber & ~PCD_TYPE_SKU_ENABLED, Size, IsPeiDb);\r
488 }\r
878ddf1f 489\r
52e1905d 490 Offset = LocalTokenNumber & PCD_DATABASE_OFFSET_MASK;\r
878ddf1f 491\r
4c114006 492 PcdDb = IsPeiDb ? ((UINT8 *) &mPcdDatabase->PeiDb) : ((UINT8 *) &mPcdDatabase->DxeDb);\r
878ddf1f 493\r
4c114006 494 StringTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.StringTable :\r
495 mPcdDatabase->DxeDb.Init.StringTable;\r
52e1905d 496 \r
497 InternalData = PcdDb + Offset;\r
878ddf1f 498\r
52e1905d 499 switch (LocalTokenNumber & ~PCD_DATABASE_OFFSET_MASK) {\r
500 case PCD_TYPE_VPD:\r
501 ASSERT (FALSE);\r
502 return EFI_INVALID_PARAMETER;\r
503 \r
504 case PCD_TYPE_STRING:\r
505 CopyMem (&StringTable[*((UINT16 *)InternalData)], Data, Size);\r
506 break;\r
878ddf1f 507\r
52e1905d 508 case PCD_TYPE_HII:\r
509 //\r
510 // Bug Bug: Please implement this\r
511 //\r
4c114006 512 GuidTable = IsPeiDb ? mPcdDatabase->PeiDb.Init.GuidTable :\r
513 mPcdDatabase->DxeDb.Init.GuidTable;\r
52e1905d 514 \r
515 VariableHead = (VARIABLE_HEAD *) (PcdDb + Offset);\r
516 \r
517 Guid = &(GuidTable[VariableHead->GuidTableIndex]);\r
518 Name = &(StringTable[VariableHead->StringIndex]);\r
878ddf1f 519\r
52e1905d 520 return EFI_SUCCESS;\r
878ddf1f 521\r
52e1905d 522 case PCD_TYPE_DATA:\r
523 if (PtrType) {\r
524 CopyMem (InternalData, Data, Size);\r
525 return EFI_SUCCESS;\r
526 }\r
878ddf1f 527\r
52e1905d 528 switch (Size) {\r
529 case sizeof(UINT8):\r
530 *((UINT8 *) InternalData) = *((UINT8 *) Data);\r
531 return EFI_SUCCESS;\r
878ddf1f 532\r
52e1905d 533 case sizeof(UINT16):\r
534 *((UINT16 *) InternalData) = *((UINT16 *) Data);\r
535 return EFI_SUCCESS;\r
536\r
537 case sizeof(UINT32):\r
538 *((UINT32 *) InternalData) = *((UINT32 *) Data);\r
539 return EFI_SUCCESS;\r
540\r
541 case sizeof(UINT64):\r
542 *((UINT64 *) InternalData) = *((UINT64 *) Data);\r
543 return EFI_SUCCESS;\r
878ddf1f 544\r
52e1905d 545 default:\r
546 ASSERT (FALSE);\r
547 return EFI_NOT_FOUND;\r
548 }\r
549\r
550 default:\r
551 ASSERT (FALSE);\r
552 break;\r
553 }\r
554 \r
555 ASSERT (FALSE);\r
556 return EFI_NOT_FOUND;\r
878ddf1f 557}\r
558\r
559\r
560\r
9d6d8b24 561\r
562\r
563VOID *\r
564ExGetWorker (\r
565 IN CONST EFI_GUID *Guid,\r
566 IN UINTN ExTokenNumber,\r
567 IN UINTN GetSize\r
568 ) \r
569{\r
570 return GetWorker(GetExPcdTokenNumber (Guid, ExTokenNumber), GetSize);\r
571}\r
572\r
573\r
574\r
575\r
576\r
577EFI_STATUS\r
578ExSetWorker (\r
579 IN PCD_TOKEN_NUMBER ExTokenNumber,\r
580 IN CONST EFI_GUID *Guid,\r
581 VOID *Data,\r
582 UINTN SetSize,\r
583 BOOLEAN PtrType\r
584 )\r
585{\r
586 PCD_TOKEN_NUMBER TokenNumber;\r
587 \r
588 TokenNumber = GetExPcdTokenNumber (Guid, ExTokenNumber);\r
589\r
590 InvokeCallbackOnSet (ExTokenNumber, Guid, TokenNumber, Data, SetSize);\r
591\r
592 SetWorker (TokenNumber, Data, SetSize, PtrType);\r
593\r
594 return EFI_SUCCESS;\r
595 \r
596}\r
597\r
598\r
599\r
600\r
878ddf1f 601EFI_STATUS\r
602SetHiiVariable (\r
603 IN EFI_GUID *VariableGuid,\r
604 IN UINT16 *VariableName,\r
605 IN CONST VOID *Data,\r
606 IN UINTN DataSize,\r
607 IN UINTN Offset\r
608 )\r
609{\r
52e1905d 610 UINTN Size;\r
611 VOID *Buffer;\r
612 EFI_STATUS Status;\r
613 UINT32 Attribute;\r
878ddf1f 614\r
615 Size = 0;\r
616\r
617 Status = EfiGetVariable (\r
618 (UINT16 *)VariableName,\r
619 VariableGuid,\r
52e1905d 620 &Attribute,\r
878ddf1f 621 &Size,\r
622 NULL\r
623 );\r
624\r
625 ASSERT (Status == EFI_BUFFER_TOO_SMALL);\r
626\r
627 Buffer = AllocatePool (Size);\r
628\r
629 ASSERT (Buffer != NULL);\r
630\r
631 Status = EfiGetVariable (\r
632 VariableName,\r
633 VariableGuid,\r
52e1905d 634 &Attribute,\r
878ddf1f 635 &Size,\r
636 Buffer\r
637 );\r
638\r
639\r
640 CopyMem ((UINT8 *)Buffer + Offset, Data, DataSize);\r
641\r
642 return EfiSetVariable (\r
643 VariableName,\r
644 VariableGuid,\r
52e1905d 645 Attribute,\r
878ddf1f 646 Size,\r
647 Buffer\r
648 );\r
649\r
650}\r
651\r
52e1905d 652\r
653\r
654\r
655\r
9d6d8b24 656PCD_TOKEN_NUMBER\r
657GetExPcdTokenNumber (\r
52e1905d 658 IN CONST EFI_GUID *Guid,\r
9d6d8b24 659 IN PCD_TOKEN_NUMBER ExTokenNumber\r
52e1905d 660 )\r
661{\r
662 UINT32 i;\r
663 DYNAMICEX_MAPPING *ExMap;\r
664 EFI_GUID *GuidTable;\r
9d6d8b24 665 EFI_GUID *MatchGuid;\r
666 UINTN MatchGuidIdx;\r
52e1905d 667\r
4c114006 668 ExMap = mPcdDatabase->PeiDb.Init.ExMapTable;\r
669 GuidTable = mPcdDatabase->PeiDb.Init.GuidTable;\r
9d6d8b24 670 \r
671 MatchGuid = ScanGuid (GuidTable, sizeof(mPcdDatabase->PeiDb.Init.GuidTable), Guid);\r
672 ASSERT (MatchGuid != NULL);\r
673\r
674 MatchGuidIdx = MatchGuid - GuidTable;\r
52e1905d 675 \r
676 for (i = 0; i < PEI_EXMAPPING_TABLE_SIZE; i++) {\r
677 if ((ExTokenNumber == ExMap[i].ExTokenNumber) &&\r
9d6d8b24 678 (MatchGuidIdx == ExMap[i].ExGuidIndex)) {\r
679 return ExMap[i].LocalTokenNumber;\r
52e1905d 680\r
681 }\r
682 }\r
683 \r
4c114006 684 ExMap = mPcdDatabase->DxeDb.Init.ExMapTable;\r
685 GuidTable = mPcdDatabase->DxeDb.Init.GuidTable;\r
9d6d8b24 686\r
687 MatchGuid = ScanGuid (GuidTable, sizeof(mPcdDatabase->DxeDb.Init.GuidTable), Guid);\r
688 ASSERT (MatchGuid != NULL);\r
689\r
690 MatchGuidIdx = MatchGuid - GuidTable;\r
52e1905d 691 \r
692 for (i = 0; i < DXE_EXMAPPING_TABLE_SIZE; i++) {\r
693 if ((ExTokenNumber == ExMap[i].ExTokenNumber) &&\r
9d6d8b24 694 (MatchGuidIdx == ExMap[i].ExGuidIndex)) {\r
695 return ExMap[i].LocalTokenNumber + PEI_LOCAL_TOKEN_NUMBER;\r
52e1905d 696 }\r
697 }\r
698\r
699 ASSERT (FALSE);\r
700\r
9d6d8b24 701 return 0;\r
52e1905d 702}\r
703\r