TianoCore EDK2 master
Loading...
Searching...
No Matches
PlatDriOverrideLib.c
Go to the documentation of this file.
1
10
11#define PLATFORM_OVERRIDE_ITEM_SIGNATURE SIGNATURE_32('p','d','o','i')
13 UINTN Signature;
14 LIST_ENTRY Link;
15 UINT32 DriverInfoNum;
16 EFI_DEVICE_PATH_PROTOCOL *ControllerDevicePath;
21 EFI_HANDLE LastReturnedImageHandle;
23
24#define DRIVER_IMAGE_INFO_SIGNATURE SIGNATURE_32('p','d','i','i')
25typedef struct _DRIVER_IMAGE_INFO {
26 UINTN Signature;
27 LIST_ENTRY Link;
28 EFI_HANDLE ImageHandle;
29 EFI_DEVICE_PATH_PROTOCOL *DriverImagePath;
30 BOOLEAN UnLoadable;
31 BOOLEAN UnStartable;
33
34#define DEVICE_PATH_STACK_ITEM_SIGNATURE SIGNATURE_32('d','p','s','i')
36 UINTN Signature;
37 LIST_ENTRY Link;
38 EFI_DEVICE_PATH_PROTOCOL *DevicePath;
40
41LIST_ENTRY mDevicePathStack = INITIALIZE_LIST_HEAD_VARIABLE (mDevicePathStack);
42
52EFIAPI
55 )
56{
57 DEVICE_PATH_STACK_ITEM *DevicePathStackItem;
58
59 DevicePathStackItem = AllocateZeroPool (sizeof (DEVICE_PATH_STACK_ITEM));
60 ASSERT (DevicePathStackItem != NULL);
61 DevicePathStackItem->Signature = DEVICE_PATH_STACK_ITEM_SIGNATURE;
62 DevicePathStackItem->DevicePath = DuplicateDevicePath (DevicePath);
63 InsertTailList (&mDevicePathStack, &DevicePathStackItem->Link);
64 return EFI_SUCCESS;
65}
66
77EFIAPI
79 OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath
80 )
81{
82 DEVICE_PATH_STACK_ITEM *DevicePathStackItem;
83 LIST_ENTRY *ItemListIndex;
84
85 ItemListIndex = mDevicePathStack.BackLink;
86 //
87 // Check if the stack is empty
88 //
89 if (ItemListIndex != &mDevicePathStack) {
90 DevicePathStackItem = CR (ItemListIndex, DEVICE_PATH_STACK_ITEM, Link, DEVICE_PATH_STACK_ITEM_SIGNATURE);
91 if (DevicePath != NULL) {
92 *DevicePath = DuplicateDevicePath (DevicePathStackItem->DevicePath);
93 }
94
95 FreePool (DevicePathStackItem->DevicePath);
96 RemoveEntryList (&DevicePathStackItem->Link);
97 FreePool (DevicePathStackItem);
98 return EFI_SUCCESS;
99 }
100
101 return EFI_NOT_FOUND;
102}
103
113BOOLEAN
114EFIAPI
116 IN EFI_DEVICE_PATH_PROTOCOL *DevicePath
117 )
118{
119 DEVICE_PATH_STACK_ITEM *DevicePathStackItem;
120 LIST_ENTRY *ItemListIndex;
121 UINTN DevicePathSize;
122
123 ItemListIndex = mDevicePathStack.BackLink;
124 while (ItemListIndex != &mDevicePathStack) {
125 DevicePathStackItem = CR (ItemListIndex, DEVICE_PATH_STACK_ITEM, Link, DEVICE_PATH_STACK_ITEM_SIGNATURE);
126 DevicePathSize = GetDevicePathSize (DevicePath);
127 if (DevicePathSize == GetDevicePathSize (DevicePathStackItem->DevicePath)) {
128 if (CompareMem (DevicePath, DevicePathStackItem->DevicePath, DevicePathSize) == 0) {
129 return TRUE;
130 }
131 }
132
133 ItemListIndex = ItemListIndex->BackLink;
134 }
135
136 return FALSE;
137}
138
163EFIAPI
165 IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath,
166 IN EFI_GUID *FileGuid,
167 IN EFI_HANDLE CallerImageHandle
168 )
169{
170 EFI_DEVICE_PATH_PROTOCOL *TempDevicePath;
171 EFI_DEVICE_PATH_PROTOCOL *LastDeviceNode;
172 EFI_STATUS Status;
173 EFI_GUID *GuidPoint;
174 UINTN Index;
175 UINTN FvHandleCount;
176 EFI_HANDLE *FvHandleBuffer;
177 EFI_FV_FILETYPE Type;
178 UINTN Size;
179 EFI_FV_FILE_ATTRIBUTES Attributes;
180 UINT32 AuthenticationStatus;
181 BOOLEAN FindFvFile;
182 EFI_LOADED_IMAGE_PROTOCOL *LoadedImage;
185 EFI_HANDLE FoundFvHandle;
186 EFI_DEVICE_PATH_PROTOCOL *NewDevicePath;
187 BOOLEAN HasFvNode;
188
189 if (DevicePath == NULL) {
190 return EFI_INVALID_PARAMETER;
191 }
192
193 if (*DevicePath == NULL) {
194 return EFI_INVALID_PARAMETER;
195 }
196
197 //
198 // Check whether the device path points to the default the input FV file
199 //
200 TempDevicePath = *DevicePath;
201 LastDeviceNode = TempDevicePath;
202 while (!IsDevicePathEnd (TempDevicePath)) {
203 LastDeviceNode = TempDevicePath;
204 TempDevicePath = NextDevicePathNode (TempDevicePath);
205 }
206
208 if (GuidPoint == NULL) {
209 //
210 // If this option does not point to a FV file, just return EFI_UNSUPPORTED.
211 //
212 return EFI_UNSUPPORTED;
213 }
214
215 if (FileGuid != NULL) {
216 if (!CompareGuid (GuidPoint, FileGuid)) {
217 //
218 // If the FV file is not the input file GUID, just return EFI_UNSUPPORTED
219 //
220 return EFI_UNSUPPORTED;
221 }
222 } else {
223 FileGuid = GuidPoint;
224 }
225
226 //
227 // Check to see if the device path contains memory map node
228 //
229 TempDevicePath = *DevicePath;
230 HasFvNode = FALSE;
231 while (!IsDevicePathEnd (TempDevicePath)) {
232 //
233 // Use old Device Path
234 //
235 if ((DevicePathType (TempDevicePath) == HARDWARE_DEVICE_PATH) &&
236 (DevicePathSubType (TempDevicePath) == HW_MEMMAP_DP))
237 {
238 HasFvNode = TRUE;
239 break;
240 }
241
242 TempDevicePath = NextDevicePathNode (TempDevicePath);
243 }
244
245 if (!HasFvNode) {
246 return EFI_UNSUPPORTED;
247 }
248
249 //
250 // Check whether the input Fv file device path is valid
251 //
252 TempDevicePath = *DevicePath;
253 FoundFvHandle = NULL;
254 Status = gBS->LocateDevicePath (
255 &gEfiFirmwareVolume2ProtocolGuid,
256 &TempDevicePath,
257 &FoundFvHandle
258 );
259 if (!EFI_ERROR (Status)) {
260 Status = gBS->HandleProtocol (
261 FoundFvHandle,
262 &gEfiFirmwareVolume2ProtocolGuid,
263 (VOID **)&Fv
264 );
265 if (!EFI_ERROR (Status)) {
266 //
267 // Set FV ReadFile Buffer as NULL, only need to check whether input Fv file exist there
268 //
269 Status = Fv->ReadFile (
270 Fv,
271 FileGuid,
272 NULL,
273 &Size,
274 &Type,
275 &Attributes,
276 &AuthenticationStatus
277 );
278 if (!EFI_ERROR (Status)) {
279 return EFI_ALREADY_STARTED;
280 }
281 }
282 }
283
284 //
285 // Look for the input wanted FV file in current FV
286 // First, try to look for in Caller own FV. Caller and input wanted FV file usually are in the same FV
287 //
288 FindFvFile = FALSE;
289 FoundFvHandle = NULL;
290 Status = gBS->HandleProtocol (
291 CallerImageHandle,
292 &gEfiLoadedImageProtocolGuid,
293 (VOID **)&LoadedImage
294 );
295 if (!EFI_ERROR (Status)) {
296 Status = gBS->HandleProtocol (
297 LoadedImage->DeviceHandle,
298 &gEfiFirmwareVolume2ProtocolGuid,
299 (VOID **)&Fv
300 );
301 if (!EFI_ERROR (Status)) {
302 Status = Fv->ReadFile (
303 Fv,
304 FileGuid,
305 NULL,
306 &Size,
307 &Type,
308 &Attributes,
309 &AuthenticationStatus
310 );
311 if (!EFI_ERROR (Status)) {
312 FindFvFile = TRUE;
313 FoundFvHandle = LoadedImage->DeviceHandle;
314 }
315 }
316 }
317
318 //
319 // Second, if fail to find, try to enumerate all FV
320 //
321 if (!FindFvFile) {
322 gBS->LocateHandleBuffer (
324 &gEfiFirmwareVolume2ProtocolGuid,
325 NULL,
326 &FvHandleCount,
327 &FvHandleBuffer
328 );
329 for (Index = 0; Index < FvHandleCount; Index++) {
330 gBS->HandleProtocol (
331 FvHandleBuffer[Index],
332 &gEfiFirmwareVolume2ProtocolGuid,
333 (VOID **)&Fv
334 );
335
336 Status = Fv->ReadFile (
337 Fv,
338 FileGuid,
339 NULL,
340 &Size,
341 &Type,
342 &Attributes,
343 &AuthenticationStatus
344 );
345 if (EFI_ERROR (Status)) {
346 //
347 // Skip if input Fv file not in the FV
348 //
349 continue;
350 }
351
352 FindFvFile = TRUE;
353 FoundFvHandle = FvHandleBuffer[Index];
354 break;
355 }
356 }
357
358 if (FindFvFile) {
359 //
360 // Build the shell device path
361 //
362 NewDevicePath = DevicePathFromHandle (FoundFvHandle);
363 EfiInitializeFwVolDevicepathNode (&FvFileNode, FileGuid);
364 NewDevicePath = AppendDevicePathNode (NewDevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&FvFileNode);
365 *DevicePath = NewDevicePath;
366 return EFI_SUCCESS;
367 }
368
369 return EFI_NOT_FOUND;
370}
371
388VOID *
389EFIAPI
391 IN CHAR16 *Name,
392 IN EFI_GUID *VendorGuid,
393 OUT UINTN *VariableSize
394 )
395{
396 EFI_STATUS Status;
397 UINTN BufferSize;
398 VOID *Buffer;
399
400 Buffer = NULL;
401
402 //
403 // Pass in a zero size buffer to find the required buffer size.
404 //
405 BufferSize = 0;
406 Status = gRT->GetVariable (Name, VendorGuid, NULL, &BufferSize, Buffer);
407 if (Status == EFI_BUFFER_TOO_SMALL) {
408 //
409 // Allocate the buffer to return
410 //
411 Buffer = AllocateZeroPool (BufferSize);
412 if (Buffer == NULL) {
413 return NULL;
414 }
415
416 //
417 // Read variable into the allocated buffer.
418 //
419 Status = gRT->GetVariable (Name, VendorGuid, NULL, &BufferSize, Buffer);
420 if (EFI_ERROR (Status)) {
421 BufferSize = 0;
422 }
423 }
424
425 *VariableSize = BufferSize;
426 return Buffer;
427}
428
448EFIAPI
450 IN EFI_DEVICE_PATH_PROTOCOL *DevicePathToConnect
451 )
452{
453 EFI_STATUS Status;
454 EFI_DEVICE_PATH_PROTOCOL *DevicePath;
455 EFI_DEVICE_PATH_PROTOCOL *CopyOfDevicePath;
456 EFI_DEVICE_PATH_PROTOCOL *Instance;
457 EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath;
459 EFI_HANDLE Handle;
460 EFI_HANDLE PreviousHandle;
461 UINTN Size;
462
463 if (DevicePathToConnect == NULL) {
464 return EFI_SUCCESS;
465 }
466
467 DevicePath = DuplicateDevicePath (DevicePathToConnect);
468 CopyOfDevicePath = DevicePath;
469 if (DevicePath == NULL) {
470 return EFI_OUT_OF_RESOURCES;
471 }
472
473 do {
474 //
475 // The outer loop handles multi instance device paths.
476 // Only console variables contain multiple instance device paths.
477 //
478 // After this call DevicePath points to the next Instance
479 //
480 Instance = GetNextDevicePathInstance (&DevicePath, &Size);
481 ASSERT (Instance != NULL);
482
483 Next = Instance;
484 while (!IsDevicePathEndType (Next)) {
485 Next = NextDevicePathNode (Next);
486 }
487
489
490 //
491 // Start the real work of connect with RemainingDevicePath
492 //
493 PreviousHandle = NULL;
494 do {
495 //
496 // Find the handle that best matches the Device Path. If it is only a
497 // partial match the remaining part of the device path is returned in
498 // RemainingDevicePath.
499 //
500 RemainingDevicePath = Instance;
501 Status = gBS->LocateDevicePath (&gEfiDevicePathProtocolGuid, &RemainingDevicePath, &Handle);
502
503 if (!EFI_ERROR (Status)) {
504 if (Handle == PreviousHandle) {
505 //
506 // If no forward progress is made try invoking the Dispatcher.
507 // A new FV may have been added to the system an new drivers
508 // may now be found.
509 // Status == EFI_SUCCESS means a driver was dispatched
510 // Status == EFI_NOT_FOUND means no new drivers were dispatched
511 //
512 Status = gDS->Dispatch ();
513 }
514
515 if (!EFI_ERROR (Status)) {
516 PreviousHandle = Handle;
517 //
518 // Connect all drivers that apply to Handle and RemainingDevicePath,
519 // the Recursive flag is FALSE so only one level will be expanded.
520 //
521 // Do not check the connect status here, if the connect controller fail,
522 // then still give the chance to do dispatch, because partial
523 // RemainingDevicepath may be in the new FV
524 //
525 // 1. If the connect fails, RemainingDevicepath and handle will not
526 // change, so next time will do the dispatch, then dispatch's status
527 // will take effect
528 // 2. If the connect succeeds, the RemainingDevicepath and handle will
529 // change, then avoid the dispatch, we have chance to continue the
530 // next connection
531 //
532 gBS->ConnectController (Handle, NULL, RemainingDevicePath, FALSE);
533 }
534 }
535
536 //
537 // Loop until RemainingDevicePath is an empty device path
538 //
539 } while (!EFI_ERROR (Status) && !IsDevicePathEnd (RemainingDevicePath));
540 } while (DevicePath != NULL);
541
542 if (CopyOfDevicePath != NULL) {
543 FreePool (CopyOfDevicePath);
544 }
545
546 //
547 // All handle with DevicePath exists in the handle database
548 //
549 return Status;
550}
551
562EFIAPI
564 IN OUT LIST_ENTRY *MappingDataBase
565 )
566{
567 LIST_ENTRY *OverrideItemListIndex;
568 LIST_ENTRY *ImageInfoListIndex;
569 PLATFORM_OVERRIDE_ITEM *OverrideItem;
570 DRIVER_IMAGE_INFO *DriverImageInfo;
571
572 if (MappingDataBase == NULL) {
573 return EFI_INVALID_PARAMETER;
574 }
575
576 OverrideItemListIndex = GetFirstNode (MappingDataBase);
577 while (!IsNull (MappingDataBase, OverrideItemListIndex)) {
578 OverrideItem = CR (OverrideItemListIndex, PLATFORM_OVERRIDE_ITEM, Link, PLATFORM_OVERRIDE_ITEM_SIGNATURE);
579 //
580 // Free PLATFORM_OVERRIDE_ITEM.ControllerDevicePath[]
581 //
582 if (OverrideItem->ControllerDevicePath != NULL) {
583 FreePool (OverrideItem->ControllerDevicePath);
584 }
585
586 ImageInfoListIndex = GetFirstNode (&OverrideItem->DriverInfoList);
587 while (!IsNull (&OverrideItem->DriverInfoList, ImageInfoListIndex)) {
588 //
589 // Free DRIVER_IMAGE_INFO.DriverImagePath[]
590 //
591 DriverImageInfo = CR (ImageInfoListIndex, DRIVER_IMAGE_INFO, Link, DRIVER_IMAGE_INFO_SIGNATURE);
592 if (DriverImageInfo->DriverImagePath != NULL) {
593 FreePool (DriverImageInfo->DriverImagePath);
594 }
595
596 //
597 // Free DRIVER_IMAGE_INFO itself
598 //
599 ImageInfoListIndex = GetNextNode (&OverrideItem->DriverInfoList, ImageInfoListIndex);
600 RemoveEntryList (&DriverImageInfo->Link);
601 FreePool (DriverImageInfo);
602 }
603
604 //
605 // Free PLATFORM_OVERRIDE_ITEM itself
606 //
607 OverrideItemListIndex = GetNextNode (MappingDataBase, OverrideItemListIndex);
608 RemoveEntryList (&OverrideItem->Link);
609 FreePool (OverrideItem);
610 }
611
612 InitializeListHead (MappingDataBase);
613 return EFI_SUCCESS;
614}
615
659EFIAPI
661 OUT LIST_ENTRY *MappingDataBase
662 )
663{
664 UINTN BufferSize;
665 VOID *VariableBuffer;
666 UINT8 *VariableIndex;
667 UINTN VariableNum;
668 CHAR16 OverrideVariableName[40];
669 UINT32 NotEnd;
670 UINT32 DriverNumber;
671 PLATFORM_OVERRIDE_ITEM *OverrideItem;
672 DRIVER_IMAGE_INFO *DriverImageInfo;
673 BOOLEAN Corrupted;
674 UINT32 Signature;
675 EFI_DEVICE_PATH_PROTOCOL *ControllerDevicePath;
676 EFI_DEVICE_PATH_PROTOCOL *DriverDevicePath;
677 UINTN Index;
678
679 if (MappingDataBase == NULL) {
680 return EFI_INVALID_PARAMETER;
681 }
682
683 //
684 // Check the environment variable(s) that contain the override mappings .
685 //
686 VariableBuffer = GetVariableAndSize (L"PlatDriOver", &gEfiCallerIdGuid, &BufferSize);
687 ASSERT ((UINTN)VariableBuffer % sizeof (UINTN) == 0);
688 if (VariableBuffer == NULL) {
689 return EFI_NOT_FOUND;
690 }
691
692 //
693 // Traverse all variables.
694 //
695 VariableNum = 1;
696 Corrupted = FALSE;
697 NotEnd = 0;
698 do {
699 VariableIndex = VariableBuffer;
700 if (VariableIndex + sizeof (UINT32) > (UINT8 *)VariableBuffer + BufferSize) {
701 Corrupted = TRUE;
702 } else {
703 //
704 // End flag
705 //
706 NotEnd = *(UINT32 *)VariableIndex;
707 }
708
709 //
710 // Traverse the entries containing the mapping that Controller Device Path
711 // to a set of Driver Device Paths within this variable.
712 //
713 VariableIndex = VariableIndex + sizeof (UINT32);
714 while (VariableIndex < ((UINT8 *)VariableBuffer + BufferSize)) {
715 //
716 // Check signature of this entry
717 //
718 if (VariableIndex + sizeof (UINT32) > (UINT8 *)VariableBuffer + BufferSize) {
719 Corrupted = TRUE;
720 break;
721 }
722
723 Signature = *(UINT32 *)VariableIndex;
724 if (Signature != PLATFORM_OVERRIDE_ITEM_SIGNATURE) {
725 Corrupted = TRUE;
726 break;
727 }
728
729 //
730 // Create PLATFORM_OVERRIDE_ITEM for this mapping
731 //
732 OverrideItem = AllocateZeroPool (sizeof (PLATFORM_OVERRIDE_ITEM));
733 ASSERT (OverrideItem != NULL);
734 OverrideItem->Signature = PLATFORM_OVERRIDE_ITEM_SIGNATURE;
735 InitializeListHead (&OverrideItem->DriverInfoList);
736 VariableIndex = VariableIndex + sizeof (UINT32);
737 //
738 // Get DriverNum
739 //
740 if (VariableIndex + sizeof (UINT32) >= (UINT8 *)VariableBuffer + BufferSize) {
741 Corrupted = TRUE;
742 break;
743 }
744
745 DriverNumber = *(UINT32 *)VariableIndex;
746 OverrideItem->DriverInfoNum = DriverNumber;
747 VariableIndex = VariableIndex + sizeof (UINT32);
748 //
749 // Get ControllerDevicePath[]
750 //
751 ControllerDevicePath = (EFI_DEVICE_PATH_PROTOCOL *)VariableIndex;
752 OverrideItem->ControllerDevicePath = DuplicateDevicePath (ControllerDevicePath);
753 VariableIndex = VariableIndex + GetDevicePathSize (ControllerDevicePath);
754 //
755 // Align the VariableIndex since the controller device path may not be aligned, refer to the SaveOverridesMapping()
756 //
757 VariableIndex += ((sizeof (UINT32) - ((UINTN)(VariableIndex))) & (sizeof (UINT32) - 1));
758 //
759 // Check buffer overflow.
760 //
761 if ((OverrideItem->ControllerDevicePath == NULL) || (VariableIndex < (UINT8 *)ControllerDevicePath) ||
762 (VariableIndex > (UINT8 *)VariableBuffer + BufferSize))
763 {
764 Corrupted = TRUE;
765 break;
766 }
767
768 //
769 // Get all DriverImageDevicePath[]
770 //
771 for (Index = 0; Index < DriverNumber; Index++) {
772 //
773 // Create DRIVER_IMAGE_INFO for this DriverDevicePath[]
774 //
775 DriverImageInfo = AllocateZeroPool (sizeof (DRIVER_IMAGE_INFO));
776 ASSERT (DriverImageInfo != NULL);
777 DriverImageInfo->Signature = DRIVER_IMAGE_INFO_SIGNATURE;
778
779 DriverDevicePath = (EFI_DEVICE_PATH_PROTOCOL *)VariableIndex;
780 DriverImageInfo->DriverImagePath = DuplicateDevicePath (DriverDevicePath);
781 VariableIndex = VariableIndex + GetDevicePathSize (DriverDevicePath);
782 //
783 // Align the VariableIndex since the driver image device path may not be aligned, refer to the SaveOverridesMapping()
784 //
785 VariableIndex += ((sizeof (UINT32) - ((UINTN)(VariableIndex))) & (sizeof (UINT32) - 1));
786
787 InsertTailList (&OverrideItem->DriverInfoList, &DriverImageInfo->Link);
788
789 //
790 // Check buffer overflow
791 //
792 if ((DriverImageInfo->DriverImagePath == NULL) || (VariableIndex < (UINT8 *)DriverDevicePath) ||
793 (VariableIndex > (UINT8 *)VariableBuffer + BufferSize))
794 {
795 Corrupted = TRUE;
796 break;
797 }
798 }
799
800 InsertTailList (MappingDataBase, &OverrideItem->Link);
801 if (Corrupted) {
802 break;
803 }
804 }
805
806 FreePool (VariableBuffer);
807 if (Corrupted) {
808 FreeMappingDatabase (MappingDataBase);
809 return EFI_VOLUME_CORRUPTED;
810 }
811
812 //
813 // If there are additional variables (PlatDriOver1, PlatDriOver2, PlatDriOver3.....), get them.
814 // NotEnd indicates whether current variable is the end variable.
815 //
816 if (NotEnd != 0) {
817 UnicodeSPrint (OverrideVariableName, sizeof (OverrideVariableName), L"PlatDriOver%d", VariableNum++);
818 VariableBuffer = GetVariableAndSize (OverrideVariableName, &gEfiCallerIdGuid, &BufferSize);
819 ASSERT ((UINTN)VariableBuffer % sizeof (UINTN) == 0);
820 if (VariableBuffer == NULL) {
821 FreeMappingDatabase (MappingDataBase);
822 return EFI_VOLUME_CORRUPTED;
823 }
824 }
825 } while (NotEnd != 0);
826
827 return EFI_SUCCESS;
828}
829
838UINTN
839EFIAPI
841 IN LIST_ENTRY *OverrideItemListIndex
842 )
843{
844 UINTN NeededSize;
845 PLATFORM_OVERRIDE_ITEM *OverrideItem;
846 LIST_ENTRY *ImageInfoListIndex;
847 DRIVER_IMAGE_INFO *DriverImageInfo;
848 UINTN DevicePathSize;
849
850 NeededSize = 0;
851 OverrideItem = CR (OverrideItemListIndex, PLATFORM_OVERRIDE_ITEM, Link, PLATFORM_OVERRIDE_ITEM_SIGNATURE);
852 NeededSize += sizeof (UINT32); // UINT32 SIGNATURE;
853 NeededSize += sizeof (UINT32); // UINT32 DriverNum;
854 DevicePathSize = GetDevicePathSize (OverrideItem->ControllerDevicePath);
855 NeededSize += DevicePathSize; // ControllerDevicePath
856 //
857 // Align the controller device path
858 //
859 NeededSize += ((sizeof (UINT32) - DevicePathSize) & (sizeof (UINT32) - 1));
860 //
861 // Traverse the Driver Info List of this Override Item
862 //
863 ImageInfoListIndex = GetFirstNode (&OverrideItem->DriverInfoList);
864 while (!IsNull (&OverrideItem->DriverInfoList, ImageInfoListIndex)) {
865 DriverImageInfo = CR (ImageInfoListIndex, DRIVER_IMAGE_INFO, Link, DRIVER_IMAGE_INFO_SIGNATURE);
866 DevicePathSize = GetDevicePathSize (DriverImageInfo->DriverImagePath);
867 NeededSize += DevicePathSize; // DriverDevicePath
868 //
869 // Align the driver image device path
870 //
871 NeededSize += ((sizeof (UINT32) - DevicePathSize) & (sizeof (UINT32) - 1));
872 ImageInfoListIndex = GetNextNode (&OverrideItem->DriverInfoList, ImageInfoListIndex);
873 }
874
875 return NeededSize;
876}
877
886EFIAPI
888 VOID
889 )
890{
891 EFI_STATUS Status;
892 VOID *VariableBuffer;
893 UINTN VariableNum;
894 UINTN BufferSize;
895 UINTN Index;
896 CHAR16 OverrideVariableName[40];
897
898 //
899 // Get environment variable(s) number
900 //
901 VariableNum = 0;
902 VariableBuffer = GetVariableAndSize (L"PlatDriOver", &gEfiCallerIdGuid, &BufferSize);
903 VariableNum++;
904 if (VariableBuffer == NULL) {
905 return EFI_NOT_FOUND;
906 }
907
908 //
909 // Check NotEnd to get all PlatDriOverX variable(s)
910 //
911 while ((VariableBuffer != NULL) && ((*(UINT32 *)VariableBuffer) != 0)) {
912 FreePool (VariableBuffer);
913 UnicodeSPrint (OverrideVariableName, sizeof (OverrideVariableName), L"PlatDriOver%d", VariableNum);
914 VariableBuffer = GetVariableAndSize (OverrideVariableName, &gEfiCallerIdGuid, &BufferSize);
915 VariableNum++;
916 }
917
918 //
919 // Delete PlatDriOver and all additional variables, if exist.
920 //
921 Status = gRT->SetVariable (
922 L"PlatDriOver",
923 &gEfiCallerIdGuid,
924 EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_NON_VOLATILE,
925 0,
926 NULL
927 );
928 ASSERT (!EFI_ERROR (Status));
929 for (Index = 1; Index < VariableNum; Index++) {
930 UnicodeSPrint (OverrideVariableName, sizeof (OverrideVariableName), L"PlatDriOver%d", Index);
931 Status = gRT->SetVariable (
932 OverrideVariableName,
933 &gEfiCallerIdGuid,
934 EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_NON_VOLATILE,
935 0,
936 NULL
937 );
938 ASSERT (!EFI_ERROR (Status));
939 }
940
941 return EFI_SUCCESS;
942}
943
954EFIAPI
956 IN LIST_ENTRY *MappingDataBase
957 )
958{
959 EFI_STATUS Status;
960 VOID *VariableBuffer;
961 UINT8 *VariableIndex;
962 UINTN NumIndex;
963 CHAR16 OverrideVariableName[40];
964 UINT32 NotEnd;
965 PLATFORM_OVERRIDE_ITEM *OverrideItem;
966 DRIVER_IMAGE_INFO *DriverImageInfo;
967 LIST_ENTRY *OverrideItemListIndex;
968 LIST_ENTRY *ItemIndex;
969 LIST_ENTRY *ImageInfoListIndex;
970 UINTN VariableNeededSize;
971 UINT64 MaximumVariableStorageSize;
972 UINT64 RemainingVariableStorageSize;
973 UINT64 MaximumVariableSize;
974 UINTN OneItemNeededSize;
975
976 if (MappingDataBase == NULL) {
977 return EFI_INVALID_PARAMETER;
978 }
979
980 if (IsListEmpty (MappingDataBase)) {
981 Status = DeleteOverridesVariables ();
982 return EFI_SUCCESS;
983 }
984
985 //
986 // Get the the maximum size of an individual EFI variable in current system
987 //
988 gRT->QueryVariableInfo (
989 EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_NON_VOLATILE,
990 &MaximumVariableStorageSize,
991 &RemainingVariableStorageSize,
992 &MaximumVariableSize
993 );
994
995 NumIndex = 0;
996 OverrideItemListIndex = GetFirstNode (MappingDataBase);
997 while (!IsNull (MappingDataBase, OverrideItemListIndex)) {
998 //
999 // Try to find the most proper variable size which <= MaximumVariableSize,
1000 // but can contain mapping info as much as possible
1001 //
1002 VariableNeededSize = sizeof (UINT32); // NotEnd;
1003 ItemIndex = OverrideItemListIndex;
1004 NotEnd = FALSE;
1005 //
1006 // Traverse all PLATFORM_OVERRIDE_ITEMs and get the total size.
1007 //
1008 while (!IsNull (MappingDataBase, ItemIndex)) {
1009 OneItemNeededSize = GetOneItemNeededSize (ItemIndex);
1010 //
1011 // If the total size exceeds the MaximumVariableSize, then we must use
1012 // multiple variables.
1013 //
1014 if ((VariableNeededSize +
1015 OneItemNeededSize +
1016 StrSize (L"PlatDriOver ")
1017 ) >= MaximumVariableSize
1018 )
1019 {
1020 NotEnd = TRUE;
1021 break;
1022 }
1023
1024 VariableNeededSize += OneItemNeededSize;
1025 ItemIndex = GetNextNode (MappingDataBase, ItemIndex);
1026 }
1027
1028 if (NotEnd != 0) {
1029 if (VariableNeededSize == sizeof (UINT32)) {
1030 //
1031 // If an individual EFI variable cannot contain a single Item, return error
1032 //
1033 return EFI_OUT_OF_RESOURCES;
1034 }
1035 }
1036
1037 //
1038 // VariableNeededSize is the most proper variable size, allocate variable buffer
1039 // ItemIndex now points to the next PLATFORM_OVERRIDE_ITEM which is not covered by VariableNeededSize
1040 //
1041 VariableBuffer = AllocateZeroPool (VariableNeededSize);
1042 ASSERT (VariableBuffer != NULL);
1043 ASSERT ((UINTN)VariableBuffer % sizeof (UINTN) == 0);
1044
1045 //
1046 // Fill the variable buffer according to MappingDataBase
1047 //
1048 VariableIndex = VariableBuffer;
1049 *(UINT32 *)VariableIndex = NotEnd;
1050 VariableIndex += sizeof (UINT32); // pass NotEnd
1051 //
1052 // ItemIndex points to the next PLATFORM_OVERRIDE_ITEM which is not covered by VariableNeededSize
1053 //
1054 while (OverrideItemListIndex != ItemIndex) {
1055 *(UINT32 *)VariableIndex = PLATFORM_OVERRIDE_ITEM_SIGNATURE;
1056 VariableIndex += sizeof (UINT32); // pass SIGNATURE
1057
1058 OverrideItem = CR (OverrideItemListIndex, PLATFORM_OVERRIDE_ITEM, Link, PLATFORM_OVERRIDE_ITEM_SIGNATURE);
1059 *(UINT32 *)VariableIndex = OverrideItem->DriverInfoNum;
1060 VariableIndex += sizeof (UINT32); // pass DriverNum
1061
1062 CopyMem (VariableIndex, OverrideItem->ControllerDevicePath, GetDevicePathSize (OverrideItem->ControllerDevicePath));
1063 VariableIndex += GetDevicePathSize (OverrideItem->ControllerDevicePath); // pass ControllerDevicePath
1064
1065 //
1066 // Align the VariableIndex since the controller device path may not be aligned
1067 //
1068 VariableIndex += ((sizeof (UINT32) - ((UINTN)(VariableIndex))) & (sizeof (UINT32) - 1));
1069 //
1070 // Save the Driver Info List of this PLATFORM_OVERRIDE_ITEM
1071 //
1072 ImageInfoListIndex = GetFirstNode (&OverrideItem->DriverInfoList);
1073 while (!IsNull (&OverrideItem->DriverInfoList, ImageInfoListIndex)) {
1074 DriverImageInfo = CR (ImageInfoListIndex, DRIVER_IMAGE_INFO, Link, DRIVER_IMAGE_INFO_SIGNATURE);
1075 CopyMem (VariableIndex, DriverImageInfo->DriverImagePath, GetDevicePathSize (DriverImageInfo->DriverImagePath));
1076 VariableIndex += GetDevicePathSize (DriverImageInfo->DriverImagePath); // pass DriverImageDevicePath
1077 //
1078 // Align the VariableIndex since the driver image device path may not be aligned
1079 //
1080 VariableIndex += ((sizeof (UINT32) - ((UINTN)(VariableIndex))) & (sizeof (UINT32) - 1));
1081 ImageInfoListIndex = GetNextNode (&OverrideItem->DriverInfoList, ImageInfoListIndex);
1082 }
1083
1084 OverrideItemListIndex = GetNextNode (MappingDataBase, OverrideItemListIndex);
1085 }
1086
1087 ASSERT (((UINTN)VariableIndex - (UINTN)VariableBuffer) == VariableNeededSize);
1088
1089 if (NumIndex == 0) {
1090 UnicodeSPrint (OverrideVariableName, sizeof (OverrideVariableName), L"PlatDriOver");
1091 } else {
1092 UnicodeSPrint (OverrideVariableName, sizeof (OverrideVariableName), L"PlatDriOver%d", NumIndex);
1093 }
1094
1095 Status = gRT->SetVariable (
1096 OverrideVariableName,
1097 &gEfiCallerIdGuid,
1098 EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_NON_VOLATILE,
1099 VariableNeededSize,
1100 VariableBuffer
1101 );
1102 FreePool (VariableBuffer);
1103
1104 if (EFI_ERROR (Status)) {
1105 if (NumIndex > 0) {
1106 //
1107 // Delete all PlatDriOver variables when full mapping can't be set.
1108 //
1110 }
1111
1112 return Status;
1113 }
1114
1115 NumIndex++;
1116 }
1117
1118 return EFI_SUCCESS;
1119}
1120
1133EFIAPI
1135 IN EFI_HANDLE ImageHandle,
1136 OUT EFI_HANDLE *BindingHandle
1137 )
1138{
1139 EFI_STATUS Status;
1140 UINTN Index;
1141 UINTN DriverBindingHandleCount;
1142 EFI_HANDLE *DriverBindingHandleBuffer;
1143 EFI_DRIVER_BINDING_PROTOCOL *DriverBindingInterface;
1144
1145 if ((BindingHandle == NULL) || (ImageHandle == NULL)) {
1146 return NULL;
1147 }
1148
1149 //
1150 // Get all drivers which support driver binding protocol
1151 //
1152 DriverBindingHandleCount = 0;
1153 Status = gBS->LocateHandleBuffer (
1154 ByProtocol,
1155 &gEfiDriverBindingProtocolGuid,
1156 NULL,
1157 &DriverBindingHandleCount,
1158 &DriverBindingHandleBuffer
1159 );
1160 if (EFI_ERROR (Status) || (DriverBindingHandleCount == 0)) {
1161 return NULL;
1162 }
1163
1164 for (Index = 0; Index < DriverBindingHandleCount; Index++) {
1165 DriverBindingInterface = NULL;
1166 Status = gBS->OpenProtocol (
1167 DriverBindingHandleBuffer[Index],
1168 &gEfiDriverBindingProtocolGuid,
1169 (VOID **)&DriverBindingInterface,
1170 NULL,
1171 NULL,
1172 EFI_OPEN_PROTOCOL_GET_PROTOCOL
1173 );
1174 if (EFI_ERROR (Status)) {
1175 continue;
1176 }
1177
1178 if (DriverBindingInterface->ImageHandle == ImageHandle) {
1179 *BindingHandle = DriverBindingHandleBuffer[Index];
1180 FreePool (DriverBindingHandleBuffer);
1181 return DriverBindingInterface;
1182 }
1183 }
1184
1185 //
1186 // If no Driver Binding Protocol instance is found
1187 //
1188 FreePool (DriverBindingHandleBuffer);
1189 *BindingHandle = NULL;
1190 return NULL;
1191}
1192
1199EFI_TPL
1201 VOID
1202 )
1203{
1204 EFI_TPL Tpl;
1205
1206 Tpl = gBS->RaiseTPL (TPL_HIGH_LEVEL);
1207 gBS->RestoreTPL (Tpl);
1208
1209 return Tpl;
1210}
1211
1238EFIAPI
1240 IN EFI_HANDLE ControllerHandle,
1241 IN OUT EFI_HANDLE *DriverImageHandle,
1242 IN LIST_ENTRY *MappingDataBase,
1243 IN EFI_HANDLE CallerImageHandle
1244 )
1245{
1246 EFI_STATUS Status;
1247 EFI_DEVICE_PATH_PROTOCOL *ControllerDevicePath;
1248 BOOLEAN ControllerFound;
1249 BOOLEAN ImageFound;
1250 EFI_HANDLE *ImageHandleBuffer;
1251 UINTN ImageHandleCount;
1252 UINTN Index;
1253 EFI_DRIVER_BINDING_PROTOCOL *DriverBinding;
1254 EFI_HANDLE DriverBindingHandle;
1255 BOOLEAN FoundLastReturned;
1256 PLATFORM_OVERRIDE_ITEM *OverrideItem;
1257 DRIVER_IMAGE_INFO *DriverImageInfo;
1258 LIST_ENTRY *OverrideItemListIndex;
1259 LIST_ENTRY *ImageInfoListIndex;
1260 EFI_DEVICE_PATH_PROTOCOL *TempDriverImagePath;
1261 EFI_HANDLE ImageHandle;
1262 EFI_HANDLE Handle;
1263 EFI_DEVICE_PATH_PROTOCOL *LoadedImageDevicePath;
1264 EFI_BUS_SPECIFIC_DRIVER_OVERRIDE_PROTOCOL *BusSpecificDriverOverride;
1265 UINTN DevicePathSize;
1266
1267 //
1268 // Check that ControllerHandle is a valid handle
1269 //
1270 if (ControllerHandle == NULL) {
1271 return EFI_INVALID_PARAMETER;
1272 }
1273
1274 //
1275 // Get the device path of ControllerHandle
1276 //
1277 Status = gBS->HandleProtocol (
1278 ControllerHandle,
1279 &gEfiDevicePathProtocolGuid,
1280 (VOID **)&ControllerDevicePath
1281 );
1282 if (EFI_ERROR (Status) || (ControllerDevicePath == NULL)) {
1283 return EFI_INVALID_PARAMETER;
1284 }
1285
1286 //
1287 // Search ControllerDevicePath in MappingDataBase
1288 //
1289 OverrideItem = NULL;
1290 ControllerFound = FALSE;
1291 DevicePathSize = GetDevicePathSize (ControllerDevicePath);
1292
1293 OverrideItemListIndex = GetFirstNode (MappingDataBase);
1294 while (!IsNull (MappingDataBase, OverrideItemListIndex)) {
1295 OverrideItem = CR (OverrideItemListIndex, PLATFORM_OVERRIDE_ITEM, Link, PLATFORM_OVERRIDE_ITEM_SIGNATURE);
1296 if (DevicePathSize == GetDevicePathSize (OverrideItem->ControllerDevicePath)) {
1297 if (CompareMem (
1298 ControllerDevicePath,
1299 OverrideItem->ControllerDevicePath,
1300 DevicePathSize
1301 ) == 0
1302 )
1303 {
1304 ControllerFound = TRUE;
1305 break;
1306 }
1307 }
1308
1309 OverrideItemListIndex = GetNextNode (MappingDataBase, OverrideItemListIndex);
1310 }
1311
1312 if (!ControllerFound) {
1313 return EFI_NOT_FOUND;
1314 }
1315
1316 //
1317 // Passing in a pointer to NULL, will return the first driver device path for ControllerHandle.
1318 // Check whether the driverImagePath is not a device path that was returned on a previous call to GetDriverPath().
1319 //
1320 if (*DriverImageHandle != NULL) {
1321 if (*DriverImageHandle != OverrideItem->LastReturnedImageHandle) {
1322 return EFI_INVALID_PARAMETER;
1323 }
1324 }
1325
1326 //
1327 // The GetDriverPath() may be called recursively, because it use ConnectDevicePath() internally,
1328 // so should check whether there is a dead loop.
1329 // Here use a controller device path stack to record all processed controller device path during a GetDriverPath() call,
1330 // and check the controller device path whether appear again during the GetDriverPath() call.
1331 //
1332 if (CheckExistInStack (OverrideItem->ControllerDevicePath)) {
1333 //
1334 // There is a dependency dead loop if the ControllerDevicePath appear in stack twice
1335 //
1336 return EFI_UNSUPPORTED;
1337 }
1338
1339 PushDevPathStack (OverrideItem->ControllerDevicePath);
1340
1341 //
1342 // Check every override driver, try to load and start them
1343 //
1344 ImageInfoListIndex = GetFirstNode (&OverrideItem->DriverInfoList);
1345 while (!IsNull (&OverrideItem->DriverInfoList, ImageInfoListIndex)) {
1346 DriverImageInfo = CR (ImageInfoListIndex, DRIVER_IMAGE_INFO, Link, DRIVER_IMAGE_INFO_SIGNATURE);
1347 if (DriverImageInfo->ImageHandle == NULL) {
1348 //
1349 // Skip if the image is unloadable or unstartable
1350 //
1351 if ((!DriverImageInfo->UnLoadable) && ((!DriverImageInfo->UnStartable))) {
1352 TempDriverImagePath = DriverImageInfo->DriverImagePath;
1353 //
1354 // If the image device path contains an FV node, check the FV file device path is valid.
1355 // If it is invalid, try to return the valid device path.
1356 // FV address maybe changes for memory layout adjust from time to time,
1357 // use this function could promise the FV file device path is right.
1358 //
1359 Status = UpdateFvFileDevicePath (&TempDriverImagePath, NULL, CallerImageHandle);
1360 if (!EFI_ERROR (Status)) {
1361 FreePool (DriverImageInfo->DriverImagePath);
1362 DriverImageInfo->DriverImagePath = TempDriverImagePath;
1363 }
1364
1365 //
1366 // Get all Loaded Image protocol to check whether the driver image has been loaded and started
1367 //
1368 ImageFound = FALSE;
1369 ImageHandleCount = 0;
1370 Status = gBS->LocateHandleBuffer (
1371 ByProtocol,
1372 &gEfiLoadedImageProtocolGuid,
1373 NULL,
1374 &ImageHandleCount,
1375 &ImageHandleBuffer
1376 );
1377 if (EFI_ERROR (Status) || (ImageHandleCount == 0)) {
1378 return EFI_NOT_FOUND;
1379 }
1380
1381 for (Index = 0; Index < ImageHandleCount; Index++) {
1382 //
1383 // Get the EFI Loaded Image Device Path Protocol
1384 //
1385 LoadedImageDevicePath = NULL;
1386 Status = gBS->HandleProtocol (
1387 ImageHandleBuffer[Index],
1388 &gEfiLoadedImageDevicePathProtocolGuid,
1389 (VOID **)&LoadedImageDevicePath
1390 );
1391 if (EFI_ERROR (Status)) {
1392 //
1393 // Maybe not all EFI_LOADED_IMAGE_DEVICE_PATH_PROTOCOL existed.
1394 //
1395 continue;
1396 }
1397
1398 DevicePathSize = GetDevicePathSize (DriverImageInfo->DriverImagePath);
1399 if (DevicePathSize == GetDevicePathSize (LoadedImageDevicePath)) {
1400 if (CompareMem (
1401 DriverImageInfo->DriverImagePath,
1402 LoadedImageDevicePath,
1403 GetDevicePathSize (LoadedImageDevicePath)
1404 ) == 0
1405 )
1406 {
1407 ImageFound = TRUE;
1408 break;
1409 }
1410 }
1411 }
1412
1413 if (ImageFound) {
1414 //
1415 // Find its related driver binding protocol
1416 // Driver binding handle may be different with its driver's Image Handle.
1417 //
1418 DriverBindingHandle = NULL;
1419 DriverBinding = GetBindingProtocolFromImageHandle (
1420 ImageHandleBuffer[Index],
1421 &DriverBindingHandle
1422 );
1423 ASSERT (DriverBinding != NULL);
1424 DriverImageInfo->ImageHandle = ImageHandleBuffer[Index];
1425 } else if (GetCurrentTpl () <= TPL_CALLBACK) {
1426 //
1427 // The driver image has not been loaded and started. Try to load and start it now.
1428 // Try to connect all device in the driver image path.
1429 //
1430 // Note: LoadImage() and StartImage() should be called under CALLBACK TPL in theory, but
1431 // since many device need to be connected in CALLBACK level environment( e.g. Usb devices )
1432 // and the Fat and Patition driver can endure executing in CALLBACK level in fact, so here permit
1433 // to use LoadImage() and StartImage() in CALLBACK TPL.
1434 //
1435 Status = ConnectDevicePath (DriverImageInfo->DriverImagePath);
1436 //
1437 // check whether it points to a PCI Option Rom image,
1438 // and try to use bus override protocol to get its first option rom image driver
1439 //
1440 TempDriverImagePath = DriverImageInfo->DriverImagePath;
1441 gBS->LocateDevicePath (&gEfiDevicePathProtocolGuid, &TempDriverImagePath, &Handle);
1442 //
1443 // Get the Bus Specific Driver Override Protocol instance on the Controller Handle
1444 //
1445 Status = gBS->HandleProtocol (
1446 Handle,
1447 &gEfiBusSpecificDriverOverrideProtocolGuid,
1448 (VOID **)&BusSpecificDriverOverride
1449 );
1450 if (!EFI_ERROR (Status) && (BusSpecificDriverOverride != NULL)) {
1451 ImageHandle = NULL;
1452 Status = BusSpecificDriverOverride->GetDriver (
1453 BusSpecificDriverOverride,
1454 &ImageHandle
1455 );
1456 if (!EFI_ERROR (Status)) {
1457 //
1458 // Find its related driver binding protocol
1459 // Driver binding handle may be different with its driver's Image handle
1460 //
1461 DriverBindingHandle = NULL;
1462 DriverBinding = GetBindingProtocolFromImageHandle (
1463 ImageHandle,
1464 &DriverBindingHandle
1465 );
1466 ASSERT (DriverBinding != NULL);
1467 DriverImageInfo->ImageHandle = ImageHandle;
1468 }
1469 }
1470
1471 //
1472 // Skip if any device cannot be connected now, future passes through GetDriver() may be able to load that driver.
1473 // Only file path media or FwVol Device Path Node remain if all device is connected
1474 //
1475 TempDriverImagePath = DriverImageInfo->DriverImagePath;
1476 gBS->LocateDevicePath (&gEfiDevicePathProtocolGuid, &TempDriverImagePath, &Handle);
1477 if (((DevicePathType (TempDriverImagePath) == MEDIA_DEVICE_PATH) &&
1478 (DevicePathSubType (TempDriverImagePath) == MEDIA_FILEPATH_DP)) ||
1480 )
1481 {
1482 //
1483 // Try to load the driver
1484 //
1485 TempDriverImagePath = DriverImageInfo->DriverImagePath;
1486 Status = gBS->LoadImage (
1487 FALSE,
1488 CallerImageHandle,
1489 TempDriverImagePath,
1490 NULL,
1491 0,
1492 &ImageHandle
1493 );
1494 if (!EFI_ERROR (Status)) {
1495 //
1496 // Try to start the driver
1497 //
1498 Status = gBS->StartImage (ImageHandle, NULL, NULL);
1499 if (EFI_ERROR (Status)) {
1500 DriverImageInfo->UnStartable = TRUE;
1501 DriverImageInfo->ImageHandle = NULL;
1502 } else {
1503 //
1504 // Find its related driver binding protocol
1505 // Driver binding handle may be different with its driver's Image handle
1506 //
1507 DriverBindingHandle = NULL;
1508 DriverBinding = GetBindingProtocolFromImageHandle (
1509 ImageHandle,
1510 &DriverBindingHandle
1511 );
1512 ASSERT (DriverBinding != NULL);
1513 DriverImageInfo->ImageHandle = ImageHandle;
1514 }
1515 } else {
1516 //
1517 // With EFI_SECURITY_VIOLATION retval, the Image was loaded and an ImageHandle was created
1518 // with a valid EFI_LOADED_IMAGE_PROTOCOL, but the image can not be started right now.
1519 // If the caller doesn't have the option to defer the execution of an image, we should
1520 // unload image for the EFI_SECURITY_VIOLATION to avoid resource leak.
1521 //
1522 if (Status == EFI_SECURITY_VIOLATION) {
1523 gBS->UnloadImage (ImageHandle);
1524 }
1525
1526 DriverImageInfo->UnLoadable = TRUE;
1527 DriverImageInfo->ImageHandle = NULL;
1528 }
1529 }
1530 }
1531
1532 FreePool (ImageHandleBuffer);
1533 }
1534 }
1535
1536 ImageInfoListIndex = GetNextNode (&OverrideItem->DriverInfoList, ImageInfoListIndex);
1537 }
1538
1539 //
1540 // Finish try to load and start the override driver of a controller, popup the controller's device path
1541 //
1543
1544 //
1545 // return the DriverImageHandle for ControllerHandle
1546 //
1547 FoundLastReturned = FALSE;
1548 ImageInfoListIndex = GetFirstNode (&OverrideItem->DriverInfoList);
1549 while (!IsNull (&OverrideItem->DriverInfoList, ImageInfoListIndex)) {
1550 DriverImageInfo = CR (ImageInfoListIndex, DRIVER_IMAGE_INFO, Link, DRIVER_IMAGE_INFO_SIGNATURE);
1551 if (DriverImageInfo->ImageHandle != NULL) {
1552 if ((*DriverImageHandle == NULL) || FoundLastReturned) {
1553 //
1554 // If DriverImageHandle is NULL, then we just need to return the first driver.
1555 // If FoundLastReturned, this means we have just encountered the previously returned driver.
1556 // For both cases, we just return the image handle of this driver.
1557 //
1558 OverrideItem->LastReturnedImageHandle = DriverImageInfo->ImageHandle;
1559 *DriverImageHandle = DriverImageInfo->ImageHandle;
1560 return EFI_SUCCESS;
1561 } else if (*DriverImageHandle == DriverImageInfo->ImageHandle) {
1562 //
1563 // We have found the previously returned driver.
1564 //
1565 FoundLastReturned = TRUE;
1566 }
1567 }
1568
1569 ImageInfoListIndex = GetNextNode (&OverrideItem->DriverInfoList, ImageInfoListIndex);
1570 }
1571
1572 return EFI_NOT_FOUND;
1573}
1574
1593EFIAPI
1595 IN EFI_DEVICE_PATH_PROTOCOL *ControllerDevicePath,
1596 IN EFI_DEVICE_PATH_PROTOCOL *DriverImageDevicePath OPTIONAL,
1597 IN LIST_ENTRY *MappingDataBase,
1598 OUT UINT32 *DriverInfoNum OPTIONAL,
1599 OUT UINT32 *DriverImageNO OPTIONAL
1600 )
1601{
1602 LIST_ENTRY *OverrideItemListIndex;
1603 PLATFORM_OVERRIDE_ITEM *OverrideItem;
1604 LIST_ENTRY *ImageInfoListIndex;
1605 DRIVER_IMAGE_INFO *DriverImageInfo;
1606 BOOLEAN Found;
1607 UINT32 ImageNO;
1608 UINTN DevicePathSize;
1609
1610 if (ControllerDevicePath == NULL) {
1611 return EFI_INVALID_PARAMETER;
1612 }
1613
1614 if (MappingDataBase == NULL) {
1615 return EFI_INVALID_PARAMETER;
1616 }
1617
1618 //
1619 // Search ControllerDevicePath in MappingDataBase
1620 //
1621 Found = FALSE;
1622 OverrideItem = NULL;
1623 OverrideItemListIndex = GetFirstNode (MappingDataBase);
1624 while (!IsNull (MappingDataBase, OverrideItemListIndex)) {
1625 OverrideItem = CR (OverrideItemListIndex, PLATFORM_OVERRIDE_ITEM, Link, PLATFORM_OVERRIDE_ITEM_SIGNATURE);
1626 DevicePathSize = GetDevicePathSize (ControllerDevicePath);
1627 if (DevicePathSize == GetDevicePathSize (OverrideItem->ControllerDevicePath)) {
1628 if (CompareMem (
1629 ControllerDevicePath,
1630 OverrideItem->ControllerDevicePath,
1631 DevicePathSize
1632 ) == 0
1633 )
1634 {
1635 Found = TRUE;
1636 break;
1637 }
1638 }
1639
1640 OverrideItemListIndex = GetNextNode (MappingDataBase, OverrideItemListIndex);
1641 }
1642
1643 if (!Found) {
1644 //
1645 // ControllerDevicePath is not in MappingDataBase
1646 //
1647 return EFI_NOT_FOUND;
1648 }
1649
1650 ASSERT (OverrideItem->DriverInfoNum != 0);
1651 if (DriverInfoNum != NULL) {
1652 *DriverInfoNum = OverrideItem->DriverInfoNum;
1653 }
1654
1655 //
1656 // If DriverImageDevicePath is NULL, skip checking DriverImageDevicePath
1657 // in the controller's Driver Image Info List
1658 //
1659 if (DriverImageDevicePath == NULL) {
1660 return EFI_SUCCESS;
1661 }
1662
1663 //
1664 // return the DriverImageHandle for ControllerHandle
1665 //
1666 ImageNO = 0;
1667 Found = FALSE;
1668 ImageInfoListIndex = GetFirstNode (&OverrideItem->DriverInfoList);
1669 while (!IsNull (&OverrideItem->DriverInfoList, ImageInfoListIndex)) {
1670 DriverImageInfo = CR (ImageInfoListIndex, DRIVER_IMAGE_INFO, Link, DRIVER_IMAGE_INFO_SIGNATURE);
1671 ImageNO++;
1672 DevicePathSize = GetDevicePathSize (DriverImageDevicePath);
1673 if (DevicePathSize == GetDevicePathSize (DriverImageInfo->DriverImagePath)) {
1674 if (CompareMem (
1675 DriverImageDevicePath,
1676 DriverImageInfo->DriverImagePath,
1677 GetDevicePathSize (DriverImageInfo->DriverImagePath)
1678 ) == 0
1679 )
1680 {
1681 Found = TRUE;
1682 break;
1683 }
1684 }
1685
1686 ImageInfoListIndex = GetNextNode (&OverrideItem->DriverInfoList, ImageInfoListIndex);
1687 }
1688
1689 if (!Found) {
1690 //
1691 // DriverImageDevicePath is not found in the controller's Driver Image Info List
1692 //
1693 return EFI_NOT_FOUND;
1694 } else {
1695 if (DriverImageNO != NULL) {
1696 *DriverImageNO = ImageNO;
1697 }
1698
1699 return EFI_SUCCESS;
1700 }
1701}
1702
1723EFIAPI
1725 IN EFI_DEVICE_PATH_PROTOCOL *ControllerDevicePath,
1726 IN EFI_DEVICE_PATH_PROTOCOL *DriverImageDevicePath,
1727 IN LIST_ENTRY *MappingDataBase,
1728 IN UINT32 DriverImageNO
1729 )
1730{
1731 EFI_STATUS Status;
1732 LIST_ENTRY *OverrideItemListIndex;
1733 PLATFORM_OVERRIDE_ITEM *OverrideItem;
1734 LIST_ENTRY *ImageInfoListIndex;
1735 DRIVER_IMAGE_INFO *DriverImageInfo;
1736 BOOLEAN Found;
1737 UINT32 ImageNO;
1738 UINTN DevicePathSize;
1739
1740 if (ControllerDevicePath == NULL) {
1741 return EFI_INVALID_PARAMETER;
1742 }
1743
1744 if (DriverImageDevicePath == NULL) {
1745 return EFI_INVALID_PARAMETER;
1746 }
1747
1748 if (MappingDataBase == NULL) {
1749 return EFI_INVALID_PARAMETER;
1750 }
1751
1752 //
1753 // If the driver is already in the controller's Driver Image Info List,
1754 // just return EFI_ALREADY_STARTED.
1755 //
1756 Status = CheckMapping (
1757 ControllerDevicePath,
1758 DriverImageDevicePath,
1759 MappingDataBase,
1760 NULL,
1761 NULL
1762 );
1763 if (Status == EFI_SUCCESS) {
1764 return EFI_ALREADY_STARTED;
1765 }
1766
1767 //
1768 // Search the input ControllerDevicePath in MappingDataBase
1769 //
1770 Found = FALSE;
1771 OverrideItem = NULL;
1772 OverrideItemListIndex = GetFirstNode (MappingDataBase);
1773 while (!IsNull (MappingDataBase, OverrideItemListIndex)) {
1774 OverrideItem = CR (OverrideItemListIndex, PLATFORM_OVERRIDE_ITEM, Link, PLATFORM_OVERRIDE_ITEM_SIGNATURE);
1775 DevicePathSize = GetDevicePathSize (ControllerDevicePath);
1776 if (DevicePathSize == GetDevicePathSize (OverrideItem->ControllerDevicePath)) {
1777 if (CompareMem (
1778 ControllerDevicePath,
1779 OverrideItem->ControllerDevicePath,
1780 DevicePathSize
1781 ) == 0
1782 )
1783 {
1784 Found = TRUE;
1785 break;
1786 }
1787 }
1788
1789 OverrideItemListIndex = GetNextNode (MappingDataBase, OverrideItemListIndex);
1790 }
1791
1792 //
1793 // If cannot find, this is a new controller item
1794 // Add the Controller related PLATFORM_OVERRIDE_ITEM structrue in mapping data base
1795 //
1796 if (!Found) {
1797 OverrideItem = AllocateZeroPool (sizeof (PLATFORM_OVERRIDE_ITEM));
1798 ASSERT (OverrideItem != NULL);
1799 OverrideItem->Signature = PLATFORM_OVERRIDE_ITEM_SIGNATURE;
1800 OverrideItem->ControllerDevicePath = DuplicateDevicePath (ControllerDevicePath);
1801 InitializeListHead (&OverrideItem->DriverInfoList);
1802 InsertTailList (MappingDataBase, &OverrideItem->Link);
1803 }
1804
1805 //
1806 // Prepare the driver image related DRIVER_IMAGE_INFO structure.
1807 //
1808 DriverImageInfo = AllocateZeroPool (sizeof (DRIVER_IMAGE_INFO));
1809 ASSERT (DriverImageInfo != NULL);
1810 DriverImageInfo->Signature = DRIVER_IMAGE_INFO_SIGNATURE;
1811 DriverImageInfo->DriverImagePath = DuplicateDevicePath (DriverImageDevicePath);
1812 //
1813 // Find the driver image wanted order location
1814 //
1815 ImageNO = 0;
1816 Found = FALSE;
1817 ImageInfoListIndex = GetFirstNode (&OverrideItem->DriverInfoList);
1818 while (!IsNull (&OverrideItem->DriverInfoList, ImageInfoListIndex)) {
1819 if (ImageNO == (DriverImageNO - 1)) {
1820 //
1821 // find the wanted order location, insert it
1822 //
1823 InsertTailList (ImageInfoListIndex, &DriverImageInfo->Link);
1824 OverrideItem->DriverInfoNum++;
1825 Found = TRUE;
1826 break;
1827 }
1828
1829 ImageNO++;
1830 ImageInfoListIndex = GetNextNode (&OverrideItem->DriverInfoList, ImageInfoListIndex);
1831 }
1832
1833 if (!Found) {
1834 //
1835 // if not find the wanted order location, add it as last item of the controller mapping item
1836 //
1837 InsertTailList (&OverrideItem->DriverInfoList, &DriverImageInfo->Link);
1838 OverrideItem->DriverInfoNum++;
1839 }
1840
1841 return EFI_SUCCESS;
1842}
1843
1860EFIAPI
1862 IN EFI_DEVICE_PATH_PROTOCOL *ControllerDevicePath,
1863 IN EFI_DEVICE_PATH_PROTOCOL *DriverImageDevicePath,
1864 IN LIST_ENTRY *MappingDataBase
1865 )
1866{
1867 EFI_STATUS Status;
1868 LIST_ENTRY *OverrideItemListIndex;
1869 PLATFORM_OVERRIDE_ITEM *OverrideItem;
1870 LIST_ENTRY *ImageInfoListIndex;
1871 DRIVER_IMAGE_INFO *DriverImageInfo;
1872 BOOLEAN Found;
1873 UINTN DevicePathSize;
1874
1875 if (ControllerDevicePath == NULL) {
1876 return EFI_INVALID_PARAMETER;
1877 }
1878
1879 if (MappingDataBase == NULL) {
1880 return EFI_INVALID_PARAMETER;
1881 }
1882
1883 //
1884 // If ControllerDevicePath is not found in mapping database, return EFI_NOT_FOUND.
1885 //
1886 Status = CheckMapping (
1887 ControllerDevicePath,
1888 DriverImageDevicePath,
1889 MappingDataBase,
1890 NULL,
1891 NULL
1892 );
1893 if (EFI_ERROR (Status)) {
1894 return EFI_NOT_FOUND;
1895 }
1896
1897 //
1898 // Search ControllerDevicePath in MappingDataBase
1899 //
1900 Found = FALSE;
1901 OverrideItem = NULL;
1902 OverrideItemListIndex = GetFirstNode (MappingDataBase);
1903 while (!IsNull (MappingDataBase, OverrideItemListIndex)) {
1904 OverrideItem = CR (OverrideItemListIndex, PLATFORM_OVERRIDE_ITEM, Link, PLATFORM_OVERRIDE_ITEM_SIGNATURE);
1905 DevicePathSize = GetDevicePathSize (ControllerDevicePath);
1906 if (DevicePathSize == GetDevicePathSize (OverrideItem->ControllerDevicePath)) {
1907 if (CompareMem (
1908 ControllerDevicePath,
1909 OverrideItem->ControllerDevicePath,
1910 DevicePathSize
1911 ) == 0
1912 )
1913 {
1914 Found = TRUE;
1915 break;
1916 }
1917 }
1918
1919 OverrideItemListIndex = GetNextNode (MappingDataBase, OverrideItemListIndex);
1920 }
1921
1922 ASSERT (Found);
1923 ASSERT (OverrideItem->DriverInfoNum != 0);
1924
1925 Found = FALSE;
1926 ImageInfoListIndex = GetFirstNode (&OverrideItem->DriverInfoList);
1927 while (!IsNull (&OverrideItem->DriverInfoList, ImageInfoListIndex)) {
1928 DriverImageInfo = CR (ImageInfoListIndex, DRIVER_IMAGE_INFO, Link, DRIVER_IMAGE_INFO_SIGNATURE);
1929 ImageInfoListIndex = GetNextNode (&OverrideItem->DriverInfoList, ImageInfoListIndex);
1930 if (DriverImageDevicePath != NULL) {
1931 //
1932 // Search for the specified DriverImageDevicePath and remove it, then break.
1933 //
1934 DevicePathSize = GetDevicePathSize (DriverImageDevicePath);
1935 if (DevicePathSize == GetDevicePathSize (DriverImageInfo->DriverImagePath)) {
1936 if (CompareMem (
1937 DriverImageDevicePath,
1938 DriverImageInfo->DriverImagePath,
1939 GetDevicePathSize (DriverImageInfo->DriverImagePath)
1940 ) == 0
1941 )
1942 {
1943 Found = TRUE;
1944 FreePool (DriverImageInfo->DriverImagePath);
1945 RemoveEntryList (&DriverImageInfo->Link);
1946 OverrideItem->DriverInfoNum--;
1947 break;
1948 }
1949 }
1950 } else {
1951 //
1952 // Remove all existing driver image info entries, so no break here.
1953 //
1954 Found = TRUE;
1955 FreePool (DriverImageInfo->DriverImagePath);
1956 RemoveEntryList (&DriverImageInfo->Link);
1957 OverrideItem->DriverInfoNum--;
1958 }
1959 }
1960
1961 //
1962 // Confirm all driver image info entries have been removed,
1963 // if DriverImageDevicePath is NULL.
1964 //
1965 if (DriverImageDevicePath == NULL) {
1966 ASSERT (OverrideItem->DriverInfoNum == 0);
1967 }
1968
1969 //
1970 // If Override Item has no driver image info entry, then delete this item.
1971 //
1972 if (OverrideItem->DriverInfoNum == 0) {
1973 FreePool (OverrideItem->ControllerDevicePath);
1974 RemoveEntryList (&OverrideItem->Link);
1975 FreePool (OverrideItem);
1976 }
1977
1978 if (!Found) {
1979 //
1980 // DriverImageDevicePath is not NULL and cannot be found in the controller's
1981 // driver image info list.
1982 //
1983 return EFI_NOT_FOUND;
1984 }
1985
1986 return EFI_SUCCESS;
1987}
UINT64 UINTN
BOOLEAN EFIAPI IsNull(IN CONST LIST_ENTRY *List, IN CONST LIST_ENTRY *Node)
Definition: LinkedList.c:443
UINTN EFIAPI StrSize(IN CONST CHAR16 *String)
Definition: String.c:72
BOOLEAN EFIAPI IsListEmpty(IN CONST LIST_ENTRY *ListHead)
Definition: LinkedList.c:403
LIST_ENTRY *EFIAPI GetNextNode(IN CONST LIST_ENTRY *List, IN CONST LIST_ENTRY *Node)
Definition: LinkedList.c:333
LIST_ENTRY *EFIAPI GetFirstNode(IN CONST LIST_ENTRY *List)
Definition: LinkedList.c:298
LIST_ENTRY *EFIAPI RemoveEntryList(IN CONST LIST_ENTRY *Entry)
Definition: LinkedList.c:590
LIST_ENTRY *EFIAPI InitializeListHead(IN OUT LIST_ENTRY *ListHead)
Definition: LinkedList.c:182
#define INITIALIZE_LIST_HEAD_VARIABLE(ListHead)
Definition: BaseLib.h:2904
LIST_ENTRY *EFIAPI InsertTailList(IN OUT LIST_ENTRY *ListHead, IN OUT LIST_ENTRY *Entry)
Definition: LinkedList.c:259
INTN EFIAPI CompareMem(IN CONST VOID *DestinationBuffer, IN CONST VOID *SourceBuffer, IN UINTN Length)
VOID *EFIAPI CopyMem(OUT VOID *DestinationBuffer, IN CONST VOID *SourceBuffer, IN UINTN Length)
BOOLEAN EFIAPI CompareGuid(IN CONST GUID *Guid1, IN CONST GUID *Guid2)
Definition: MemLibGuid.c:73
#define MEDIA_FILEPATH_DP
Definition: DevicePath.h:1098
#define HARDWARE_DEVICE_PATH
Definition: DevicePath.h:68
#define HW_MEMMAP_DP
Definition: DevicePath.h:109
UINT8 EFIAPI DevicePathType(IN CONST VOID *Node)
UINT8 EFIAPI DevicePathSubType(IN CONST VOID *Node)
EFI_DEVICE_PATH_PROTOCOL *EFIAPI AppendDevicePathNode(IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath OPTIONAL, IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePathNode OPTIONAL)
BOOLEAN EFIAPI IsDevicePathEnd(IN CONST VOID *Node)
EFI_DEVICE_PATH_PROTOCOL *EFIAPI NextDevicePathNode(IN CONST VOID *Node)
EFI_DEVICE_PATH_PROTOCOL *EFIAPI DevicePathFromHandle(IN EFI_HANDLE Handle)
EFI_DEVICE_PATH_PROTOCOL *EFIAPI GetNextDevicePathInstance(IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath, OUT UINTN *Size)
UINTN EFIAPI GetDevicePathSize(IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath)
EFI_DEVICE_PATH_PROTOCOL *EFIAPI DuplicateDevicePath(IN CONST EFI_DEVICE_PATH_PROTOCOL *DevicePath)
BOOLEAN EFIAPI IsDevicePathEndType(IN CONST VOID *Node)
VOID EFIAPI SetDevicePathEndNode(OUT VOID *Node)
EFI_DXE_SERVICES * gDS
VOID *EFIAPI AllocateZeroPool(IN UINTN AllocationSize)
VOID EFIAPI FreePool(IN VOID *Buffer)
UINTN EFIAPI UnicodeSPrint(OUT CHAR16 *StartOfBuffer, IN UINTN BufferSize, IN CONST CHAR16 *FormatString,...)
Definition: PrintLib.c:408
EFI_RUNTIME_SERVICES * gRT
#define NULL
Definition: Base.h:319
#define TRUE
Definition: Base.h:301
#define FALSE
Definition: Base.h:307
#define IN
Definition: Base.h:279
#define OUT
Definition: Base.h:284
#define CR(Record, TYPE, Field, TestSignature)
Definition: DebugLib.h:659
UINT32 EFI_FV_FILE_ATTRIBUTES
VOID *EFIAPI GetVariableAndSize(IN CHAR16 *Name, IN EFI_GUID *VendorGuid, OUT UINTN *VariableSize)
BOOLEAN EFIAPI CheckExistInStack(IN EFI_DEVICE_PATH_PROTOCOL *DevicePath)
EFI_STATUS EFIAPI DeleteDriverImage(IN EFI_DEVICE_PATH_PROTOCOL *ControllerDevicePath, IN EFI_DEVICE_PATH_PROTOCOL *DriverImageDevicePath, IN LIST_ENTRY *MappingDataBase)
EFI_TPL GetCurrentTpl(VOID)
EFI_STATUS EFIAPI PushDevPathStack(IN EFI_DEVICE_PATH_PROTOCOL *DevicePath)
EFI_STATUS EFIAPI PopDevPathStack(OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath)
EFI_STATUS EFIAPI DeleteOverridesVariables(VOID)
EFI_STATUS EFIAPI FreeMappingDatabase(IN OUT LIST_ENTRY *MappingDataBase)
EFI_STATUS EFIAPI SaveOverridesMapping(IN LIST_ENTRY *MappingDataBase)
EFI_STATUS EFIAPI CheckMapping(IN EFI_DEVICE_PATH_PROTOCOL *ControllerDevicePath, IN EFI_DEVICE_PATH_PROTOCOL *DriverImageDevicePath OPTIONAL, IN LIST_ENTRY *MappingDataBase, OUT UINT32 *DriverInfoNum OPTIONAL, OUT UINT32 *DriverImageNO OPTIONAL)
EFI_STATUS EFIAPI ConnectDevicePath(IN EFI_DEVICE_PATH_PROTOCOL *DevicePathToConnect)
EFI_STATUS EFIAPI InsertDriverImage(IN EFI_DEVICE_PATH_PROTOCOL *ControllerDevicePath, IN EFI_DEVICE_PATH_PROTOCOL *DriverImageDevicePath, IN LIST_ENTRY *MappingDataBase, IN UINT32 DriverImageNO)
EFI_STATUS EFIAPI InitOverridesMapping(OUT LIST_ENTRY *MappingDataBase)
EFI_DRIVER_BINDING_PROTOCOL *EFIAPI GetBindingProtocolFromImageHandle(IN EFI_HANDLE ImageHandle, OUT EFI_HANDLE *BindingHandle)
UINTN EFIAPI GetOneItemNeededSize(IN LIST_ENTRY *OverrideItemListIndex)
EFI_STATUS EFIAPI GetDriverFromMapping(IN EFI_HANDLE ControllerHandle, IN OUT EFI_HANDLE *DriverImageHandle, IN LIST_ENTRY *MappingDataBase, IN EFI_HANDLE CallerImageHandle)
EFI_STATUS EFIAPI UpdateFvFileDevicePath(IN OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath, IN EFI_GUID *FileGuid, IN EFI_HANDLE CallerImageHandle)
RETURN_STATUS EFI_STATUS
Definition: UefiBaseType.h:29
UINTN EFI_TPL
Definition: UefiBaseType.h:41
VOID * EFI_HANDLE
Definition: UefiBaseType.h:33
#define EFI_SUCCESS
Definition: UefiBaseType.h:112
EFI_BOOT_SERVICES * gBS
VOID EFIAPI EfiInitializeFwVolDevicepathNode(IN OUT MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *FvDevicePathNode, IN CONST EFI_GUID *NameGuid)
Definition: UefiNotTiano.c:325
EFI_GUID *EFIAPI EfiGetNameGuidFromFwVolDevicePathNode(IN CONST MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *FvDevicePathNode)
Definition: UefiNotTiano.c:292
#define EFI_VARIABLE_NON_VOLATILE
@ ByProtocol
Definition: UefiSpec.h:1518
EFI_HANDLE DeviceHandle
The device handle that the EFI Image was loaded from.
Definition: LoadedImage.h:53
Definition: Base.h:213