init.c

来自「Next BIOS Source code : Extensible Firmw」· C语言 代码 · 共 555 行 · 第 1/2 页

C
555
字号

        Context = AllocateZeroPool (sizeof(FILE_MENU_CONTEXT));
        ASSERT (Context);
        Context->Handle = FsHandles[Index];
        Context->FHandle = FileHandle;
        Context->DevicePathStr = DevicePathToStr (DevicePathFromHandle (Context->Handle));
        Context->Info = LibFileSystemVolumeLabelInfo (Context->FHandle);
        Context->FileName = StrDuplicate (L"\\");
        Context->DevicePath = FileDevicePath (Context->Handle, Context->FileName);

        Context->IsDir = TRUE;
        Context->RootContext = TRUE;
        Context->IsRemovableMedia = FALSE;
        if (Context->Info == NULL) {
            VolLabel = L"NO FILE SYSTEM INFO";         
        } else {
            if (Context->Info->VolumeLabel == NULL) {
                VolLabel = L"NULL VOLUME LABEL"; 
            } else {
                VolLabel = Context->Info->VolumeLabel;
                if (*VolLabel == 0x0000) {
                    VolLabel = L"NO VOLUME LABEL"; 
                }
            }
        } 
        Str = LibGetUiString (Context->Handle, UiDeviceString, LanguageCodeEnglish, FALSE);
        if (!Str) {
            Str = Context->DevicePathStr;
        }
        SPrint (Buffer, MAX_CHAR, L"%s [%s]", VolLabel, Str);
        AllocateMenuOption (&FileSystemMenu, Buffer, FILE_UNSELECTED, Context);
    }
    if(NumberFsHandles) {
        FreePool (FsHandles);
    }

    // 
    // add removable media block devices 
    // (Includes fixed media with removable media boot algorithm
    //
    LibLocateHandle (ByProtocol, &BlockIoProtocol, NULL, &NumberBlkIoHandles, &BlkIoHandles);
    for (Index = 0; Index < NumberBlkIoHandles; Index++) {
        Status = BS->HandleProtocol (BlkIoHandles[Index], &BlockIoProtocol, &BlkIo);
        if (EFI_ERROR(Status)) {
            continue;
        }
        if (BlkIo->Media->LogicalPartition || !BlkIo->Media->RemovableMedia) {
            // Skip Logical Paritions and NON removable media devices
            continue;
        }

        Context = AllocateZeroPool (sizeof(FILE_MENU_CONTEXT));
        ASSERT (Context);
        Context->IsRemovableMedia = TRUE;
        Context->Handle = BlkIoHandles[Index];

        Context->DevicePath = DevicePathFromHandle (Context->Handle);
        Context->DevicePathStr = DevicePathToStr (Context->DevicePath);

        Str = LibGetUiString (Context->Handle, UiDeviceString, LanguageCodeEnglish, TRUE);
        SPrint (Buffer, MAX_CHAR, L"Removable Media Boot [%s]", Str);
        AllocateMenuOption (&FileSystemMenu, Buffer, FILE_UNSELECTED, Context);
    }
    if(NumberBlkIoHandles) {
        FreePool (BlkIoHandles);
    }

    // 
    // add loadfileprotocol devices as removable media
    //
    LibLocateHandle (ByProtocol, &LoadFileProtocol, NULL, &NumberLoadFileHandles, &LoadFileHandles);
    for (Index = 0; Index < NumberLoadFileHandles; Index++) {

        Context = AllocateZeroPool (sizeof(FILE_MENU_CONTEXT));
        ASSERT (Context);
        Context->IsRemovableMedia = FALSE;
        Context->IsLoadFile = TRUE;
        Context->Handle = LoadFileHandles[Index];

        Context->DevicePath = DevicePathFromHandle (Context->Handle);
        Context->DevicePathStr = DevicePathToStr (Context->DevicePath);

        Str = LibGetUiString (Context->Handle, UiDeviceString, LanguageCodeEnglish, TRUE);
        SPrint (Buffer, MAX_CHAR, L"Load File [%s]", Str);
        AllocateMenuOption (&FileSystemMenu, Buffer, FILE_UNSELECTED, Context);
    }

    if(NumberLoadFileHandles) {
        FreePool (LoadFileHandles);
    }

    //
    // Add Legacy boot support as well
    //
    Status = LibLocateProtocol (&LegacyBootProtocol, &Interface);
    if (!EFI_ERROR (Status)) {
      AddLegacyBootOption (BBS_TYPE_FLOPPY, 0, "", L"Legacy Boot", TRUE);
    }

    AllocateMenuOption (&FileSystemMenu, L"Exit", FILE_UNSELECTED, NULL);

    FileSystemMenu.Selection = NULL;
    for (;;) {
        ResultContext = MenuDisplay (&FileSystemMenu, &Key);
        if (ResultContext == NULL) {
            break;
        }       

        if (ResultContext->IsRemovableMedia || ResultContext->IsLoadFile) {
            if (BootFromAFileSystem) {
                if (!EFI_ERROR(BootFromFileContext (ResultContext))) {
                    break;
                }
            } else {
                ConvertFileContextToBootOption (ResultContext);
            }
        } else if (!FindAFileMenu (ResultContext, &DirMenu, BootFromAFileSystem)) {
            break;
        }
    }

    FreeFileSystemMenu (&FileSystemMenu);

    ST->ConOut->ClearScreen (ST->ConOut);
    Print (L"\n");
    return EFI_SUCCESS;
}

VOID
AddLegacyBootOption (
    IN  UINT16  BbsType,
    IN  UINT16  BbsFlag,
    IN  UINT8   *BbsString,
    IN  UINT16  *String,
    IN  BOOLEAN Removable
    )
{
    EFI_DEVICE_PATH     *DevicePath;
    UINTN               BbsStrLen;
    EFI_DEV_PATH        Node;
    FILE_MENU_CONTEXT   *Context;    

    ZeroMem (&Node, sizeof(Node));
    Node.DevPath.Type = BBS_DEVICE_PATH;
    Node.DevPath.SubType = BBS_BBS_DP;

    BbsStrLen = strlena(BbsString);
    SetDevicePathNodeLength (&Node.DevPath, sizeof(BBS_BBS_DEVICE_PATH) + BbsStrLen);
    Node.Bbs.DeviceType = BbsType;
    Node.Bbs.StatusFlag = BbsFlag;
    CopyMem (&Node.Bbs.String[0], BbsString, BbsStrLen + 1);
   
    DevicePath = AppendDevicePathNode (EndDevicePath, &Node.DevPath);

    Context = AllocateZeroPool (sizeof(FILE_MENU_CONTEXT));
    ASSERT (Context);
    Context->IsRemovableMedia = Removable;
    Context->IsLoadFile = TRUE;
    Context->DevicePath = DuplicateDevicePath(DevicePath);
    Context->DevicePathStr = DevicePathToStr (Context->DevicePath);
    AllocateMenuOption (&FileSystemMenu, String, FILE_UNSELECTED, Context);

    FreePool (DevicePath);
}    
VOID
FreeFileSystemMenu (
    IN EFI_MENU     *Menu
    )
{
    MENU_OPTION         *MenuOption;
    FILE_MENU_CONTEXT   *MenuContext;
    LIST_ENTRY          *List;   
    //
    // Delete the menu option's Context
    //
    List = Menu->Head.Flink;
    while (List != &Menu->Head) {
        MenuOption = CR(List, MENU_OPTION, Link, MENU_OPTION_SIGNATURE);
        
        MenuContext = (FILE_MENU_CONTEXT *)MenuOption->Context;
        if (MenuContext != NULL) {
            if (MenuContext->FHandle) {
                MenuContext->FHandle->Close (MenuContext->FHandle);
            }
            FreePool (MenuContext->DevicePathStr);
            if (MenuContext->FileName) {
                FreePool (MenuContext->FileName);
            }
            FreePool (MenuOption->Context);
        }
        
        List = List->Flink;
    }
    MenuFree (Menu);
}


EFI_STATUS
Bmnt_DisplayWarmReset () 
{
    RT->ResetSystem(EfiResetWarm, EFI_SUCCESS, 0, NULL);
    return EFI_DEVICE_ERROR;
}

EFI_STATUS
Bmnt_DisplayColdReset () 
{
    RT->ResetSystem(EfiResetCold, EFI_SUCCESS, 0, NULL);
    return EFI_DEVICE_ERROR;
}

VOID
InitializeMainMenuFooter()
{
    EFI_STATUS  Status;
    EFI_GUID    SystemGuid;
    CHAR8       *SerialNumber;
    UINT16      Timeout;
    UINTN       TimoutSize;
    UINTN       SprintSize;
    UINT16      *Str;
    CHAR16      Buffer[240];

    Str = Buffer;
    *Str = L'\0';

    TimoutSize = sizeof(Timeout);
    Status = RT->GetVariable (
                VarTimeout,
                &EfiGlobalVariable,
                NULL,
                &TimoutSize,
                &Timeout
                );
    if (!EFI_ERROR(Status)) {
        SprintSize = SPrint (Str, 240, L"Timeout-->[%hd] sec ", Timeout);
        Str += SprintSize;
    }

    Status = LibGetSmbiosSystemGuidAndSerialNumber (&SystemGuid, &SerialNumber);
    if (!EFI_ERROR(Status)) {
        SprintSize = SPrint (Str, 240, L"SystemGuid-->[%hg]\n    SerialNumber-->[%ha] ", &SystemGuid, SerialNumber);
        Str += SprintSize;    
    }

    MainMenu.Footer = PoolPrint(Buffer);
}

VOID
FreeMainMenuFooter()
{
    if (MainMenu.Footer) {
        FreePool(MainMenu.Footer);
        MainMenu.Footer = NULL;
    }
}

VOID
PrintBanner (
    VOID
    )
{
    SIMPLE_TEXT_OUTPUT_INTERFACE    *Con;

    //
    // Clear the display
    //

    Con = ST->ConOut;
    Con->SetAttribute (Con, EFI_TEXT_ATTR(EFI_LIGHTGRAY, EFI_BLACK));
    Con->ClearScreen (Con);

    Print(L"%EEFI Boot Maintenance Manager ver %01d.%02d [%d.%d]\n\n", ST->Hdr.Revision >> 16, ST->Hdr.Revision & 0xffff, ST->FirmwareRevision >> 16,ST->FirmwareRevision & 0xffff);
}


⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?