1 /** @file 2 Load the deferred images after user is identified. 3 4 Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR> 5 This program and the accompanying materials 6 are licensed and made available under the terms and conditions of the BSD License 7 which accompanies this distribution. The full text of the license may be found at 8 http://opensource.org/licenses/bsd-license.php 9 10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, 11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. 12 13 **/ 14 15 #include "UserIdentifyManager.h" 16 17 EFI_HANDLE mDeferredImageHandle; 18 19 /** 20 The function will load all the deferred images again. If the deferred image is loaded 21 successfully, try to start it. 22 23 @param Event Event whose notification function is being invoked. 24 @param Context Pointer to the notification function's context 25 26 **/ 27 VOID 28 EFIAPI 29 LoadDeferredImage ( 30 IN EFI_EVENT Event, 31 IN VOID *Context 32 ) 33 { 34 EFI_STATUS Status; 35 EFI_DEFERRED_IMAGE_LOAD_PROTOCOL *DeferredImage; 36 UINTN HandleCount; 37 EFI_HANDLE *HandleBuf; 38 UINTN Index; 39 UINTN DriverIndex; 40 EFI_DEVICE_PATH_PROTOCOL *ImageDevicePath; 41 VOID *DriverImage; 42 UINTN ImageSize; 43 BOOLEAN BootOption; 44 EFI_HANDLE ImageHandle; 45 UINTN ExitDataSize; 46 CHAR16 *ExitData; 47 48 // 49 // Find all the deferred image load protocols. 50 // 51 HandleCount = 0; 52 HandleBuf = NULL; 53 Status = gBS->LocateHandleBuffer ( 54 ByProtocol, 55 &gEfiDeferredImageLoadProtocolGuid, 56 NULL, 57 &HandleCount, 58 &HandleBuf 59 ); 60 if (EFI_ERROR (Status)) { 61 return ; 62 } 63 64 for (Index = 0; Index < HandleCount; Index++) { 65 Status = gBS->HandleProtocol ( 66 HandleBuf[Index], 67 &gEfiDeferredImageLoadProtocolGuid, 68 (VOID **) &DeferredImage 69 ); 70 if (EFI_ERROR (Status)) { 71 continue ; 72 } 73 74 DriverIndex = 0; 75 do { 76 // 77 // Load all the deferred images in this protocol instance. 78 // 79 Status = DeferredImage->GetImageInfo( 80 DeferredImage, 81 DriverIndex, 82 &ImageDevicePath, 83 (VOID **) &DriverImage, 84 &ImageSize, 85 &BootOption 86 ); 87 if (EFI_ERROR (Status)) { 88 break; 89 } 90 91 // 92 // Load and start the image. 93 // 94 Status = gBS->LoadImage ( 95 BootOption, 96 mDeferredImageHandle, 97 ImageDevicePath, 98 NULL, 99 0, 100 &ImageHandle 101 ); 102 if (!EFI_ERROR (Status)) { 103 // 104 // Before calling the image, enable the Watchdog Timer for 105 // a 5 Minute period 106 // 107 gBS->SetWatchdogTimer (5 * 60, 0x0000, 0x00, NULL); 108 Status = gBS->StartImage (ImageHandle, &ExitDataSize, &ExitData); 109 110 // 111 // Clear the Watchdog Timer after the image returns. 112 // 113 gBS->SetWatchdogTimer (0x0000, 0x0000, 0x0000, NULL); 114 } 115 DriverIndex++; 116 } while (TRUE); 117 } 118 FreePool (HandleBuf); 119 } 120 121 122 /** 123 Register an event notification function for user profile changed. 124 125 @param[in] ImageHandle Image handle this driver. 126 127 **/ 128 VOID 129 LoadDeferredImageInit ( 130 IN EFI_HANDLE ImageHandle 131 ) 132 { 133 EFI_STATUS Status; 134 EFI_EVENT Event; 135 136 mDeferredImageHandle = ImageHandle; 137 138 Status = gBS->CreateEventEx ( 139 EVT_NOTIFY_SIGNAL, 140 TPL_CALLBACK, 141 LoadDeferredImage, 142 NULL, 143 &gEfiEventUserProfileChangedGuid, 144 &Event 145 ); 146 147 ASSERT (Status == EFI_SUCCESS); 148 } 149