mirror of
https://github.com/systemd/systemd.git
synced 2025-01-10 05:18:17 +03:00
Merge pull request #18423 from DaanDeMeyer/sd-boot-no-include
More sd-boot cleanups
This commit is contained in:
commit
89d2da287b
@ -13,6 +13,7 @@
|
||||
#include "measure.h"
|
||||
#include "pe.h"
|
||||
#include "random-seed.h"
|
||||
#include "secure-boot.h"
|
||||
#include "shim.h"
|
||||
#include "util.h"
|
||||
|
||||
@ -23,8 +24,6 @@
|
||||
/* magic string to find in the binary image */
|
||||
static const char __attribute__((used)) magic[] = "#### LoaderInfo: systemd-boot " GIT_VERSION " ####";
|
||||
|
||||
static const EFI_GUID global_guid = EFI_GLOBAL_VARIABLE;
|
||||
|
||||
enum loader_type {
|
||||
LOADER_UNDEFINED,
|
||||
LOADER_EFI,
|
||||
@ -119,17 +118,17 @@ static BOOLEAN line_edit(
|
||||
while (!exit) {
|
||||
EFI_STATUS err;
|
||||
UINT64 key;
|
||||
UINTN i;
|
||||
UINTN j;
|
||||
|
||||
i = len - first;
|
||||
if (i >= x_max-1)
|
||||
i = x_max-1;
|
||||
CopyMem(print, line + first, i * sizeof(CHAR16));
|
||||
while (clear > 0 && i < x_max-1) {
|
||||
j = len - first;
|
||||
if (j >= x_max-1)
|
||||
j = x_max-1;
|
||||
CopyMem(print, line + first, j * sizeof(CHAR16));
|
||||
while (clear > 0 && j < x_max-1) {
|
||||
clear--;
|
||||
print[i++] = ' ';
|
||||
print[j++] = ' ';
|
||||
}
|
||||
print[i] = '\0';
|
||||
print[j] = '\0';
|
||||
|
||||
uefi_call_wrapper(ST->ConOut->SetCursorPosition, 3, ST->ConOut, 0, y_pos);
|
||||
uefi_call_wrapper(ST->ConOut->OutputString, 2, ST->ConOut, print);
|
||||
@ -213,12 +212,14 @@ static BOOLEAN line_edit(
|
||||
case KEYPRESS(EFI_ALT_PRESSED, 0, 'd'):
|
||||
/* kill-word */
|
||||
clear = 0;
|
||||
for (i = first + cursor; i < len && line[i] == ' '; i++)
|
||||
|
||||
UINTN k;
|
||||
for (k = first + cursor; k < len && line[k] == ' '; k++)
|
||||
clear++;
|
||||
for (; i < len && line[i] != ' '; i++)
|
||||
for (; k < len && line[k] != ' '; k++)
|
||||
clear++;
|
||||
|
||||
for (i = first + cursor; i + clear < len; i++)
|
||||
for (UINTN i = first + cursor; i + clear < len; i++)
|
||||
line[i] = line[i + clear];
|
||||
len -= clear;
|
||||
line[len] = '\0';
|
||||
@ -243,7 +244,7 @@ static BOOLEAN line_edit(
|
||||
}
|
||||
uefi_call_wrapper(ST->ConOut->SetCursorPosition, 3, ST->ConOut, cursor, y_pos);
|
||||
|
||||
for (i = first + cursor; i + clear < len; i++)
|
||||
for (UINTN i = first + cursor; i + clear < len; i++)
|
||||
line[i] = line[i + clear];
|
||||
len -= clear;
|
||||
line[len] = '\0';
|
||||
@ -256,7 +257,7 @@ static BOOLEAN line_edit(
|
||||
continue;
|
||||
if (first + cursor == len)
|
||||
continue;
|
||||
for (i = first + cursor; i < len; i++)
|
||||
for (UINTN i = first + cursor; i < len; i++)
|
||||
line[i] = line[i+1];
|
||||
clear = 1;
|
||||
len--;
|
||||
@ -285,7 +286,7 @@ static BOOLEAN line_edit(
|
||||
continue;
|
||||
if (first == 0 && cursor == 0)
|
||||
continue;
|
||||
for (i = first + cursor-1; i < len; i++)
|
||||
for (UINTN i = first + cursor-1; i < len; i++)
|
||||
line[i] = line[i+1];
|
||||
clear = 1;
|
||||
len--;
|
||||
@ -313,7 +314,7 @@ static BOOLEAN line_edit(
|
||||
case KEYPRESS(0, 0, 0x80) ... KEYPRESS(0, 0, 0xffff):
|
||||
if (len+1 == size)
|
||||
continue;
|
||||
for (i = len; i > first + cursor; i--)
|
||||
for (UINTN i = len; i > first + cursor; i--)
|
||||
line[i] = line[i-1];
|
||||
line[first + cursor] = KEYCHAR(key);
|
||||
len++;
|
||||
@ -331,25 +332,23 @@ static BOOLEAN line_edit(
|
||||
}
|
||||
|
||||
static UINTN entry_lookup_key(Config *config, UINTN start, CHAR16 key) {
|
||||
UINTN i;
|
||||
|
||||
if (key == 0)
|
||||
return -1;
|
||||
|
||||
/* select entry by number key */
|
||||
if (key >= '1' && key <= '9') {
|
||||
i = key - '0';
|
||||
UINTN i = key - '0';
|
||||
if (i > config->entry_count)
|
||||
i = config->entry_count;
|
||||
return i-1;
|
||||
}
|
||||
|
||||
/* find matching key in config entries */
|
||||
for (i = start; i < config->entry_count; i++)
|
||||
for (UINTN i = start; i < config->entry_count; i++)
|
||||
if (config->entries[i]->key == key)
|
||||
return i;
|
||||
|
||||
for (i = 0; i < start; i++)
|
||||
for (UINTN i = 0; i < start; i++)
|
||||
if (config->entries[i]->key == key)
|
||||
return i;
|
||||
|
||||
@ -357,11 +356,11 @@ static UINTN entry_lookup_key(Config *config, UINTN start, CHAR16 key) {
|
||||
}
|
||||
|
||||
static VOID print_status(Config *config, CHAR16 *loaded_image_path) {
|
||||
UINT64 key;
|
||||
UINTN i;
|
||||
_cleanup_freepool_ CHAR8 *bootvar = NULL, *modevar = NULL, *indvar = NULL;
|
||||
UINT64 key, indvar;
|
||||
UINTN timeout;
|
||||
BOOLEAN modevar;
|
||||
_cleanup_freepool_ CHAR16 *partstr = NULL, *defaultstr = NULL;
|
||||
UINTN x, y, size;
|
||||
UINTN x, y;
|
||||
|
||||
uefi_call_wrapper(ST->ConOut->SetAttribute, 2, ST->ConOut, EFI_LIGHTGRAY|EFI_BACKGROUND_BLACK);
|
||||
uefi_call_wrapper(ST->ConOut->ClearScreen, 1, ST->ConOut);
|
||||
@ -376,17 +375,16 @@ static VOID print_status(Config *config, CHAR16 *loaded_image_path) {
|
||||
if (uefi_call_wrapper(ST->ConOut->QueryMode, 4, ST->ConOut, ST->ConOut->Mode->Mode, &x, &y) == EFI_SUCCESS)
|
||||
Print(L"console size: %d x %d\n", x, y);
|
||||
|
||||
if (efivar_get_raw(&global_guid, L"SecureBoot", &bootvar, &size) == EFI_SUCCESS)
|
||||
Print(L"SecureBoot: %s\n", yes_no(*bootvar > 0));
|
||||
Print(L"SecureBoot: %s\n", yes_no(secure_boot_enabled()));
|
||||
|
||||
if (efivar_get_raw(&global_guid, L"SetupMode", &modevar, &size) == EFI_SUCCESS)
|
||||
Print(L"SetupMode: %s\n", *modevar > 0 ? L"setup" : L"user");
|
||||
if (efivar_get_boolean_u8(EFI_GLOBAL_GUID, L"SetupMode", &modevar) == EFI_SUCCESS)
|
||||
Print(L"SetupMode: %s\n", modevar ? L"setup" : L"user");
|
||||
|
||||
if (shim_loaded())
|
||||
Print(L"Shim: present\n");
|
||||
|
||||
if (efivar_get_raw(&global_guid, L"OsIndicationsSupported", &indvar, &size) == EFI_SUCCESS)
|
||||
Print(L"OsIndicationsSupported: %d\n", (UINT64)*indvar);
|
||||
if (efivar_get_uint64_le(EFI_GLOBAL_GUID, L"OsIndicationsSupported", &indvar) == EFI_SUCCESS)
|
||||
Print(L"OsIndicationsSupported: %d\n", indvar);
|
||||
|
||||
Print(L"\n--- press key ---\n\n");
|
||||
console_key_read(&key, TRUE);
|
||||
@ -423,20 +421,20 @@ static VOID print_status(Config *config, CHAR16 *loaded_image_path) {
|
||||
Print(L"entry EFI var idx: %d\n", config->idx_default_efivar);
|
||||
Print(L"\n");
|
||||
|
||||
if (efivar_get_int(L"LoaderConfigTimeout", &i) == EFI_SUCCESS)
|
||||
Print(L"LoaderConfigTimeout: %u\n", i);
|
||||
if (efivar_get_uint_string(LOADER_GUID, L"LoaderConfigTimeout", &timeout) == EFI_SUCCESS)
|
||||
Print(L"LoaderConfigTimeout: %u\n", timeout);
|
||||
|
||||
if (config->entry_oneshot)
|
||||
Print(L"LoaderEntryOneShot: %s\n", config->entry_oneshot);
|
||||
if (efivar_get(L"LoaderDevicePartUUID", &partstr) == EFI_SUCCESS)
|
||||
if (efivar_get(LOADER_GUID, L"LoaderDevicePartUUID", &partstr) == EFI_SUCCESS)
|
||||
Print(L"LoaderDevicePartUUID: %s\n", partstr);
|
||||
if (efivar_get(L"LoaderEntryDefault", &defaultstr) == EFI_SUCCESS)
|
||||
if (efivar_get(LOADER_GUID, L"LoaderEntryDefault", &defaultstr) == EFI_SUCCESS)
|
||||
Print(L"LoaderEntryDefault: %s\n", defaultstr);
|
||||
|
||||
Print(L"\n--- press key ---\n\n");
|
||||
console_key_read(&key, TRUE);
|
||||
|
||||
for (i = 0; i < config->entry_count; i++) {
|
||||
for (UINTN i = 0; i < config->entry_count; i++) {
|
||||
ConfigEntry *entry;
|
||||
|
||||
if (key == KEYPRESS(0, SCAN_ESC, 0) || key == KEYPRESS(0, 0, 'q'))
|
||||
@ -503,7 +501,6 @@ static BOOLEAN menu_run(
|
||||
UINTN idx_last;
|
||||
BOOLEAN refresh;
|
||||
BOOLEAN highlight;
|
||||
UINTN i;
|
||||
UINTN line_width;
|
||||
CHAR16 **lines;
|
||||
UINTN x_start;
|
||||
@ -564,7 +561,7 @@ static BOOLEAN menu_run(
|
||||
|
||||
/* length of the longest entry */
|
||||
line_width = 5;
|
||||
for (i = 0; i < config->entry_count; i++) {
|
||||
for (UINTN i = 0; i < config->entry_count; i++) {
|
||||
UINTN entry_len;
|
||||
|
||||
entry_len = StrLen(config->entries[i]->title_show);
|
||||
@ -583,14 +580,14 @@ static BOOLEAN menu_run(
|
||||
|
||||
/* menu entries title lines */
|
||||
lines = AllocatePool(sizeof(CHAR16 *) * config->entry_count);
|
||||
for (i = 0; i < config->entry_count; i++) {
|
||||
UINTN j, k;
|
||||
for (UINTN i = 0; i < config->entry_count; i++) {
|
||||
UINTN j;
|
||||
|
||||
lines[i] = AllocatePool(((x_max+1) * sizeof(CHAR16)));
|
||||
for (j = 0; j < x_start; j++)
|
||||
lines[i][j] = ' ';
|
||||
|
||||
for (k = 0; config->entries[i]->title_show[k] != '\0' && j < x_max; j++, k++)
|
||||
for (UINTN k = 0; config->entries[i]->title_show[k] != '\0' && j < x_max; j++, k++)
|
||||
lines[i][j] = config->entries[i]->title_show[k];
|
||||
|
||||
for (; j < x_max; j++)
|
||||
@ -600,15 +597,15 @@ static BOOLEAN menu_run(
|
||||
|
||||
status = NULL;
|
||||
clearline = AllocatePool((x_max+1) * sizeof(CHAR16));
|
||||
for (i = 0; i < x_max; i++)
|
||||
for (UINTN i = 0; i < x_max; i++)
|
||||
clearline[i] = ' ';
|
||||
clearline[i] = 0;
|
||||
clearline[x_max] = 0;
|
||||
|
||||
while (!exit) {
|
||||
UINT64 key;
|
||||
|
||||
if (refresh) {
|
||||
for (i = 0; i < config->entry_count; i++) {
|
||||
for (UINTN i = 0; i < config->entry_count; i++) {
|
||||
if (i < idx_first || i > idx_last)
|
||||
continue;
|
||||
uefi_call_wrapper(ST->ConOut->SetCursorPosition, 3, ST->ConOut, 0, y_start + i - idx_first);
|
||||
@ -764,12 +761,16 @@ static BOOLEAN menu_run(
|
||||
case KEYPRESS(0, 0, 'd'):
|
||||
if (config->idx_default_efivar != (INTN)idx_highlight) {
|
||||
/* store the selected entry in a persistent EFI variable */
|
||||
efivar_set(L"LoaderEntryDefault", config->entries[idx_highlight]->id, TRUE);
|
||||
efivar_set(
|
||||
LOADER_GUID,
|
||||
L"LoaderEntryDefault",
|
||||
config->entries[idx_highlight]->id,
|
||||
TRUE);
|
||||
config->idx_default_efivar = idx_highlight;
|
||||
status = StrDuplicate(L"Default boot entry selected.");
|
||||
} else {
|
||||
/* clear the default entry EFI variable */
|
||||
efivar_set(L"LoaderEntryDefault", NULL, TRUE);
|
||||
efivar_set(LOADER_GUID, L"LoaderEntryDefault", NULL, TRUE);
|
||||
config->idx_default_efivar = -1;
|
||||
status = StrDuplicate(L"Default boot entry cleared.");
|
||||
}
|
||||
@ -780,14 +781,15 @@ static BOOLEAN menu_run(
|
||||
case KEYPRESS(0, 0, 'T'):
|
||||
if (config->timeout_sec_efivar > 0) {
|
||||
config->timeout_sec_efivar--;
|
||||
efivar_set_int(L"LoaderConfigTimeout", config->timeout_sec_efivar, TRUE);
|
||||
efivar_set_uint_string(
|
||||
LOADER_GUID, L"LoaderConfigTimeout", config->timeout_sec_efivar, TRUE);
|
||||
if (config->timeout_sec_efivar > 0)
|
||||
status = PoolPrint(L"Menu timeout set to %d sec.", config->timeout_sec_efivar);
|
||||
else
|
||||
status = StrDuplicate(L"Menu disabled. Hold down key at bootup to show menu.");
|
||||
} else if (config->timeout_sec_efivar <= 0){
|
||||
config->timeout_sec_efivar = -1;
|
||||
efivar_set(L"LoaderConfigTimeout", NULL, TRUE);
|
||||
efivar_set(LOADER_GUID, L"LoaderConfigTimeout", NULL, TRUE);
|
||||
if (config->timeout_sec_config > 0)
|
||||
status = PoolPrint(L"Menu timeout of %d sec is defined by configuration file.",
|
||||
config->timeout_sec_config);
|
||||
@ -801,7 +803,7 @@ static BOOLEAN menu_run(
|
||||
if (config->timeout_sec_efivar == -1 && config->timeout_sec_config == 0)
|
||||
config->timeout_sec_efivar++;
|
||||
config->timeout_sec_efivar++;
|
||||
efivar_set_int(L"LoaderConfigTimeout", config->timeout_sec_efivar, TRUE);
|
||||
efivar_set_uint_string(LOADER_GUID, L"LoaderConfigTimeout", config->timeout_sec_efivar, TRUE);
|
||||
if (config->timeout_sec_efivar > 0)
|
||||
status = PoolPrint(L"Menu timeout set to %d sec.",
|
||||
config->timeout_sec_efivar);
|
||||
@ -863,7 +865,7 @@ static BOOLEAN menu_run(
|
||||
|
||||
*chosen_entry = config->entries[idx_highlight];
|
||||
|
||||
for (i = 0; i < config->entry_count; i++)
|
||||
for (UINTN i = 0; i < config->entry_count; i++)
|
||||
FreePool(lines[i]);
|
||||
FreePool(lines);
|
||||
FreePool(clearline);
|
||||
@ -1293,7 +1295,7 @@ static VOID config_entry_bump_counters(
|
||||
/* Let's tell the OS that we renamed this file, so that it knows what to rename to the counter-less name on
|
||||
* success */
|
||||
new_path = PoolPrint(L"%s\\%s", entry->path, entry->next_name);
|
||||
efivar_set(L"LoaderBootCountPath", new_path, FALSE);
|
||||
efivar_set(LOADER_GUID, L"LoaderBootCountPath", new_path, FALSE);
|
||||
|
||||
/* If the file we just renamed is the loader path, then let's update that. */
|
||||
if (StrCmp(entry->loader, old_path) == 0) {
|
||||
@ -1458,17 +1460,17 @@ static VOID config_load_defaults(Config *config, EFI_FILE *root_dir) {
|
||||
if (!EFI_ERROR(err))
|
||||
config_defaults_load_from_file(config, content);
|
||||
|
||||
err = efivar_get_int(L"LoaderConfigTimeout", &sec);
|
||||
err = efivar_get_uint_string(LOADER_GUID, L"LoaderConfigTimeout", &sec);
|
||||
if (!EFI_ERROR(err)) {
|
||||
config->timeout_sec_efivar = sec > INTN_MAX ? INTN_MAX : sec;
|
||||
config->timeout_sec = sec;
|
||||
} else
|
||||
config->timeout_sec_efivar = -1;
|
||||
|
||||
err = efivar_get_int(L"LoaderConfigTimeoutOneShot", &sec);
|
||||
err = efivar_get_uint_string(LOADER_GUID, L"LoaderConfigTimeoutOneShot", &sec);
|
||||
if (!EFI_ERROR(err)) {
|
||||
/* Unset variable now, after all it's "one shot". */
|
||||
(void) efivar_set(L"LoaderConfigTimeoutOneShot", NULL, TRUE);
|
||||
(void) efivar_set(LOADER_GUID, L"LoaderConfigTimeoutOneShot", NULL, TRUE);
|
||||
|
||||
config->timeout_sec = sec;
|
||||
config->force_menu = TRUE; /* force the menu when this is set */
|
||||
@ -1491,7 +1493,6 @@ static VOID config_load_entries(
|
||||
UINTN bufsize;
|
||||
EFI_FILE_INFO *f;
|
||||
_cleanup_freepool_ CHAR8 *content = NULL;
|
||||
UINTN len;
|
||||
|
||||
bufsize = sizeof(buf);
|
||||
err = uefi_call_wrapper(entries_dir->Read, 3, entries_dir, &bufsize, buf);
|
||||
@ -1504,12 +1505,9 @@ static VOID config_load_entries(
|
||||
if (f->Attribute & EFI_FILE_DIRECTORY)
|
||||
continue;
|
||||
|
||||
len = StrLen(f->FileName);
|
||||
if (len < 6)
|
||||
if (!endswith_no_case(f->FileName, L".conf"))
|
||||
continue;
|
||||
if (StriCmp(f->FileName + len - 5, L".conf") != 0)
|
||||
continue;
|
||||
if (StrnCmp(f->FileName, L"auto-", 5) == 0)
|
||||
if (startswith(f->FileName, L"auto-"))
|
||||
continue;
|
||||
|
||||
err = file_read(entries_dir, f->FileName, 0, 0, &content, NULL);
|
||||
@ -1553,14 +1551,11 @@ static INTN config_entry_compare(ConfigEntry *a, ConfigEntry *b) {
|
||||
}
|
||||
|
||||
static VOID config_sort_entries(Config *config) {
|
||||
UINTN i;
|
||||
|
||||
for (i = 1; i < config->entry_count; i++) {
|
||||
for (UINTN i = 1; i < config->entry_count; i++) {
|
||||
BOOLEAN more;
|
||||
UINTN k;
|
||||
|
||||
more = FALSE;
|
||||
for (k = 0; k < config->entry_count - i; k++) {
|
||||
for (UINTN k = 0; k < config->entry_count - i; k++) {
|
||||
ConfigEntry *entry;
|
||||
|
||||
if (config_entry_compare(config->entries[k], config->entries[k+1]) <= 0)
|
||||
@ -1577,9 +1572,7 @@ static VOID config_sort_entries(Config *config) {
|
||||
}
|
||||
|
||||
static INTN config_entry_find(Config *config, CHAR16 *id) {
|
||||
UINTN i;
|
||||
|
||||
for (i = 0; i < config->entry_count; i++)
|
||||
for (UINTN i = 0; i < config->entry_count; i++)
|
||||
if (StrCmp(config->entries[i]->id, id) == 0)
|
||||
return (INTN) i;
|
||||
|
||||
@ -1595,11 +1588,11 @@ static VOID config_default_entry_select(Config *config) {
|
||||
* The EFI variable to specify a boot entry for the next, and only the
|
||||
* next reboot. The variable is always cleared directly after it is read.
|
||||
*/
|
||||
err = efivar_get(L"LoaderEntryOneShot", &entry_oneshot);
|
||||
err = efivar_get(LOADER_GUID, L"LoaderEntryOneShot", &entry_oneshot);
|
||||
if (!EFI_ERROR(err)) {
|
||||
|
||||
config->entry_oneshot = StrDuplicate(entry_oneshot);
|
||||
efivar_set(L"LoaderEntryOneShot", NULL, TRUE);
|
||||
efivar_set(LOADER_GUID, L"LoaderEntryOneShot", NULL, TRUE);
|
||||
|
||||
i = config_entry_find(config, entry_oneshot);
|
||||
if (i >= 0) {
|
||||
@ -1614,7 +1607,7 @@ static VOID config_default_entry_select(Config *config) {
|
||||
* the 'd' key in the loader selection menu, the entry is marked with
|
||||
* an '*'.
|
||||
*/
|
||||
err = efivar_get(L"LoaderEntryDefault", &entry_default);
|
||||
err = efivar_get(LOADER_GUID, L"LoaderEntryDefault", &entry_default);
|
||||
if (!EFI_ERROR(err)) {
|
||||
|
||||
i = config_entry_find(config, entry_default);
|
||||
@ -1660,13 +1653,12 @@ static VOID config_default_entry_select(Config *config) {
|
||||
|
||||
static BOOLEAN find_nonunique(ConfigEntry **entries, UINTN entry_count) {
|
||||
BOOLEAN non_unique = FALSE;
|
||||
UINTN i, k;
|
||||
|
||||
for (i = 0; i < entry_count; i++)
|
||||
for (UINTN i = 0; i < entry_count; i++)
|
||||
entries[i]->non_unique = FALSE;
|
||||
|
||||
for (i = 0; i < entry_count; i++)
|
||||
for (k = 0; k < entry_count; k++) {
|
||||
for (UINTN i = 0; i < entry_count; i++)
|
||||
for (UINTN k = 0; k < entry_count; k++) {
|
||||
if (i == k)
|
||||
continue;
|
||||
if (StrCmp(entries[i]->title_show, entries[k]->title_show) != 0)
|
||||
@ -1680,10 +1672,8 @@ static BOOLEAN find_nonunique(ConfigEntry **entries, UINTN entry_count) {
|
||||
|
||||
/* generate a unique title, avoiding non-distinguishable menu entries */
|
||||
static VOID config_title_generate(Config *config) {
|
||||
UINTN i;
|
||||
|
||||
/* set title */
|
||||
for (i = 0; i < config->entry_count; i++) {
|
||||
for (UINTN i = 0; i < config->entry_count; i++) {
|
||||
CHAR16 *title;
|
||||
|
||||
FreePool(config->entries[i]->title_show);
|
||||
@ -1697,7 +1687,7 @@ static VOID config_title_generate(Config *config) {
|
||||
return;
|
||||
|
||||
/* add version to non-unique titles */
|
||||
for (i = 0; i < config->entry_count; i++) {
|
||||
for (UINTN i = 0; i < config->entry_count; i++) {
|
||||
CHAR16 *s;
|
||||
|
||||
if (!config->entries[i]->non_unique)
|
||||
@ -1714,7 +1704,7 @@ static VOID config_title_generate(Config *config) {
|
||||
return;
|
||||
|
||||
/* add machine-id to non-unique titles */
|
||||
for (i = 0; i < config->entry_count; i++) {
|
||||
for (UINTN i = 0; i < config->entry_count; i++) {
|
||||
CHAR16 *s;
|
||||
_cleanup_freepool_ CHAR16 *m = NULL;
|
||||
|
||||
@ -1734,7 +1724,7 @@ static VOID config_title_generate(Config *config) {
|
||||
return;
|
||||
|
||||
/* add file name to non-unique titles */
|
||||
for (i = 0; i < config->entry_count; i++) {
|
||||
for (UINTN i = 0; i < config->entry_count; i++) {
|
||||
CHAR16 *s;
|
||||
|
||||
if (!config->entries[i]->non_unique)
|
||||
@ -1826,14 +1816,10 @@ static BOOLEAN config_entry_add_loader_auto(
|
||||
|
||||
/* look for systemd-boot magic string */
|
||||
err = file_read(root_dir, loader, 0, 100*1024, &content, &len);
|
||||
if (!EFI_ERROR(err)) {
|
||||
CHAR8 *start = content;
|
||||
CHAR8 *last = content + len - sizeof(magic) - 1;
|
||||
|
||||
for (; start <= last; start++)
|
||||
if (!EFI_ERROR(err))
|
||||
for (CHAR8 *start = content; start <= content + len - sizeof(magic) - 1; start++)
|
||||
if (start[0] == magic[0] && CompareMem(start, magic, sizeof(magic) - 1) == 0)
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
/* check existence */
|
||||
@ -1862,9 +1848,7 @@ static VOID config_entry_add_osx(Config *config) {
|
||||
|
||||
err = LibLocateHandle(ByProtocol, &FileSystemProtocol, NULL, &handle_count, &handles);
|
||||
if (!EFI_ERROR(err)) {
|
||||
UINTN i;
|
||||
|
||||
for (i = 0; i < handle_count; i++) {
|
||||
for (UINTN i = 0; i < handle_count; i++) {
|
||||
EFI_FILE *root;
|
||||
BOOLEAN found;
|
||||
|
||||
@ -1906,7 +1890,6 @@ static VOID config_entry_add_linux(
|
||||
UINTN szs[ELEMENTSOF(sections)-1] = {};
|
||||
UINTN addrs[ELEMENTSOF(sections)-1] = {};
|
||||
CHAR8 *content = NULL;
|
||||
UINTN len;
|
||||
CHAR8 *line;
|
||||
UINTN pos = 0;
|
||||
CHAR8 *key, *value;
|
||||
@ -1926,12 +1909,9 @@ static VOID config_entry_add_linux(
|
||||
continue;
|
||||
if (f->Attribute & EFI_FILE_DIRECTORY)
|
||||
continue;
|
||||
len = StrLen(f->FileName);
|
||||
if (len < 5)
|
||||
if (!endswith_no_case(f->FileName, L".efi"))
|
||||
continue;
|
||||
if (StriCmp(f->FileName + len - 4, L".efi") != 0)
|
||||
continue;
|
||||
if (StrnCmp(f->FileName, L"auto-", 5) == 0)
|
||||
if (startswith(f->FileName, L"auto-"))
|
||||
continue;
|
||||
|
||||
/* look for .osrel and .cmdline sections in the .efi binary */
|
||||
@ -2020,10 +2000,8 @@ static VOID config_entry_add_linux(
|
||||
uefi_call_wrapper(linux_dir->Close, 1, linux_dir);
|
||||
}
|
||||
|
||||
/* Note that this is in GUID format, i.e. the first 32bit, and the following pair of 16bit are byteswapped. */
|
||||
static const UINT8 xbootldr_guid[16] = {
|
||||
0xff, 0xc2, 0x13, 0xbc, 0xe6, 0x59, 0x62, 0x42, 0xa3, 0x52, 0xb2, 0x75, 0xfd, 0x6f, 0x71, 0x72
|
||||
};
|
||||
#define XBOOTLDR_GUID \
|
||||
&(const EFI_GUID) { 0xbc13c2ff, 0x59e6, 0x4262, { 0xa3, 0x52, 0xb2, 0x75, 0xfd, 0x6f, 0x71, 0x72 } }
|
||||
|
||||
static EFI_DEVICE_PATH *path_parent(EFI_DEVICE_PATH *path, EFI_DEVICE_PATH *node) {
|
||||
EFI_DEVICE_PATH *parent;
|
||||
@ -2041,7 +2019,7 @@ static VOID config_load_xbootldr(
|
||||
Config *config,
|
||||
EFI_HANDLE *device) {
|
||||
|
||||
EFI_DEVICE_PATH *partition_path, *node, *disk_path, *copy;
|
||||
EFI_DEVICE_PATH *partition_path, *disk_path, *copy;
|
||||
UINT32 found_partition_number = (UINT32) -1;
|
||||
UINT64 found_partition_start = (UINT64) -1;
|
||||
UINT64 found_partition_size = (UINT64) -1;
|
||||
@ -2054,11 +2032,10 @@ static VOID config_load_xbootldr(
|
||||
if (!partition_path)
|
||||
return;
|
||||
|
||||
for (node = partition_path; !IsDevicePathEnd(node); node = NextDevicePathNode(node)) {
|
||||
for (EFI_DEVICE_PATH *node = partition_path; !IsDevicePathEnd(node); node = NextDevicePathNode(node)) {
|
||||
EFI_HANDLE disk_handle;
|
||||
EFI_BLOCK_IO *block_io;
|
||||
EFI_DEVICE_PATH *p;
|
||||
UINTN nr;
|
||||
|
||||
/* First, Let's look for the SCSI/SATA/USB/… device path node, i.e. one above the media
|
||||
* devices */
|
||||
@ -2085,7 +2062,7 @@ static VOID config_load_xbootldr(
|
||||
continue;
|
||||
|
||||
/* Try both copies of the GPT header, in case one is corrupted */
|
||||
for (nr = 0; nr < 2; nr++) {
|
||||
for (UINTN nr = 0; nr < 2; nr++) {
|
||||
_cleanup_freepool_ EFI_PARTITION_ENTRY* entries = NULL;
|
||||
union {
|
||||
EFI_PARTITION_TABLE_HEADER gpt_header;
|
||||
@ -2093,7 +2070,7 @@ static VOID config_load_xbootldr(
|
||||
} gpt_header_buffer;
|
||||
const EFI_PARTITION_TABLE_HEADER *h = &gpt_header_buffer.gpt_header;
|
||||
UINT64 where;
|
||||
UINTN i, sz;
|
||||
UINTN sz;
|
||||
UINT32 c;
|
||||
|
||||
if (nr == 0)
|
||||
@ -2163,12 +2140,12 @@ static VOID config_load_xbootldr(
|
||||
if (c != h->PartitionEntryArrayCRC32)
|
||||
continue;
|
||||
|
||||
for (i = 0; i < h->NumberOfPartitionEntries; i++) {
|
||||
for (UINTN i = 0; i < h->NumberOfPartitionEntries; i++) {
|
||||
EFI_PARTITION_ENTRY *entry;
|
||||
|
||||
entry = (EFI_PARTITION_ENTRY*) ((UINT8*) entries + h->SizeOfPartitionEntry * i);
|
||||
|
||||
if (CompareMem(&entry->PartitionTypeGUID, xbootldr_guid, 16) == 0) {
|
||||
if (CompareMem(&entry->PartitionTypeGUID, XBOOTLDR_GUID, 16) == 0) {
|
||||
UINT64 end;
|
||||
|
||||
/* Let's use memcpy(), in case the structs are not aligned (they really should be though) */
|
||||
@ -2197,7 +2174,7 @@ found:
|
||||
copy = DuplicateDevicePath(partition_path);
|
||||
|
||||
/* Patch in the data we found */
|
||||
for (node = copy; !IsDevicePathEnd(node); node = NextDevicePathNode(node)) {
|
||||
for (EFI_DEVICE_PATH *node = copy; !IsDevicePathEnd(node); node = NextDevicePathNode(node)) {
|
||||
HARDDRIVE_DEVICE_PATH *hd;
|
||||
|
||||
if (DevicePathType(node) != MEDIA_DEVICE_PATH)
|
||||
@ -2282,7 +2259,7 @@ static EFI_STATUS image_start(
|
||||
#endif
|
||||
}
|
||||
|
||||
efivar_set_time_usec(L"LoaderTimeExecUSec", 0);
|
||||
efivar_set_time_usec(LOADER_GUID, L"LoaderTimeExecUSec", 0);
|
||||
err = uefi_call_wrapper(BS->StartImage, 3, image, NULL, NULL);
|
||||
out_unload:
|
||||
uefi_call_wrapper(BS->UnloadImage, 1, image);
|
||||
@ -2290,18 +2267,16 @@ out_unload:
|
||||
}
|
||||
|
||||
static EFI_STATUS reboot_into_firmware(VOID) {
|
||||
_cleanup_freepool_ CHAR8 *b = NULL;
|
||||
UINTN size;
|
||||
UINT64 osind;
|
||||
UINT64 old, new;
|
||||
EFI_STATUS err;
|
||||
|
||||
osind = EFI_OS_INDICATIONS_BOOT_TO_FW_UI;
|
||||
new = EFI_OS_INDICATIONS_BOOT_TO_FW_UI;
|
||||
|
||||
err = efivar_get_raw(&global_guid, L"OsIndications", &b, &size);
|
||||
err = efivar_get_uint64_le(EFI_GLOBAL_GUID, L"OsIndications", &old);
|
||||
if (!EFI_ERROR(err))
|
||||
osind |= (UINT64)*b;
|
||||
new |= old;
|
||||
|
||||
err = efivar_set_raw(&global_guid, L"OsIndications", &osind, sizeof(UINT64), TRUE);
|
||||
err = efivar_set_uint64_le(EFI_GLOBAL_GUID, L"OsIndications", new, TRUE);
|
||||
if (EFI_ERROR(err))
|
||||
return err;
|
||||
|
||||
@ -2312,9 +2287,7 @@ static EFI_STATUS reboot_into_firmware(VOID) {
|
||||
}
|
||||
|
||||
static VOID config_free(Config *config) {
|
||||
UINTN i;
|
||||
|
||||
for (i = 0; i < config->entry_count; i++)
|
||||
for (UINTN i = 0; i < config->entry_count; i++)
|
||||
config_entry_free(config->entries[i]);
|
||||
FreePool(config->entries);
|
||||
FreePool(config->entry_default_pattern);
|
||||
@ -2324,15 +2297,15 @@ static VOID config_free(Config *config) {
|
||||
|
||||
static VOID config_write_entries_to_variable(Config *config) {
|
||||
_cleanup_freepool_ CHAR16 *buffer = NULL;
|
||||
UINTN i, sz = 0;
|
||||
UINTN sz = 0;
|
||||
CHAR16 *p;
|
||||
|
||||
for (i = 0; i < config->entry_count; i++)
|
||||
for (UINTN i = 0; i < config->entry_count; i++)
|
||||
sz += StrLen(config->entries[i]->id) + 1;
|
||||
|
||||
p = buffer = AllocatePool(sz * sizeof(CHAR16));
|
||||
|
||||
for (i = 0; i < config->entry_count; i++) {
|
||||
for (UINTN i = 0; i < config->entry_count; i++) {
|
||||
UINTN l;
|
||||
|
||||
l = StrLen(config->entries[i]->id) + 1;
|
||||
@ -2342,7 +2315,7 @@ static VOID config_write_entries_to_variable(Config *config) {
|
||||
}
|
||||
|
||||
/* Store the full list of discovered entries. */
|
||||
(void) efivar_set_raw(&loader_guid, L"LoaderEntries", buffer, (UINT8*) p - (UINT8*) buffer, FALSE);
|
||||
(void) efivar_set_raw(LOADER_GUID, L"LoaderEntries", buffer, (UINT8*) p - (UINT8*) buffer, FALSE);
|
||||
}
|
||||
|
||||
EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
@ -2357,8 +2330,7 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
0;
|
||||
|
||||
_cleanup_freepool_ CHAR16 *infostr = NULL, *typestr = NULL;
|
||||
CHAR8 *b;
|
||||
UINTN size;
|
||||
UINT64 osind = 0;
|
||||
EFI_LOADED_IMAGE *loaded_image;
|
||||
EFI_FILE *root_dir;
|
||||
CHAR16 *loaded_image_path;
|
||||
@ -2370,16 +2342,16 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
|
||||
InitializeLib(image, sys_table);
|
||||
init_usec = time_usec();
|
||||
efivar_set_time_usec(L"LoaderTimeInitUSec", init_usec);
|
||||
efivar_set(L"LoaderInfo", L"systemd-boot " GIT_VERSION, FALSE);
|
||||
efivar_set_time_usec(LOADER_GUID, L"LoaderTimeInitUSec", init_usec);
|
||||
efivar_set(LOADER_GUID, L"LoaderInfo", L"systemd-boot " GIT_VERSION, FALSE);
|
||||
|
||||
infostr = PoolPrint(L"%s %d.%02d", ST->FirmwareVendor, ST->FirmwareRevision >> 16, ST->FirmwareRevision & 0xffff);
|
||||
efivar_set(L"LoaderFirmwareInfo", infostr, FALSE);
|
||||
efivar_set(LOADER_GUID, L"LoaderFirmwareInfo", infostr, FALSE);
|
||||
|
||||
typestr = PoolPrint(L"UEFI %d.%02d", ST->Hdr.Revision >> 16, ST->Hdr.Revision & 0xffff);
|
||||
efivar_set(L"LoaderFirmwareType", typestr, FALSE);
|
||||
efivar_set(LOADER_GUID, L"LoaderFirmwareType", typestr, FALSE);
|
||||
|
||||
(void) efivar_set_raw(&loader_guid, L"LoaderFeatures", &loader_features, sizeof(loader_features), FALSE);
|
||||
(void) efivar_set_uint64_le(LOADER_GUID, L"LoaderFeatures", loader_features, FALSE);
|
||||
|
||||
err = uefi_call_wrapper(BS->OpenProtocol, 6, image, &LoadedImageProtocol, (VOID **)&loaded_image,
|
||||
image, NULL, EFI_OPEN_PROTOCOL_GET_PROTOCOL);
|
||||
@ -2391,7 +2363,7 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
|
||||
/* export the device path this image is started from */
|
||||
if (disk_get_part_uuid(loaded_image->DeviceHandle, uuid) == EFI_SUCCESS)
|
||||
efivar_set(L"LoaderDevicePartUUID", uuid, FALSE);
|
||||
efivar_set(LOADER_GUID, L"LoaderDevicePartUUID", uuid, FALSE);
|
||||
|
||||
root_dir = LibOpenRoot(loaded_image->DeviceHandle);
|
||||
if (!root_dir) {
|
||||
@ -2411,7 +2383,7 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
|
||||
/* the filesystem path to this image, to prevent adding ourselves to the menu */
|
||||
loaded_image_path = DevicePathToStr(loaded_image->FilePath);
|
||||
efivar_set(L"LoaderImageIdentifier", loaded_image_path, FALSE);
|
||||
efivar_set(LOADER_GUID, L"LoaderImageIdentifier", loaded_image_path, FALSE);
|
||||
|
||||
config_load_defaults(&config, root_dir);
|
||||
|
||||
@ -2436,15 +2408,12 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
L"auto-efi-default", '\0', L"EFI Default Loader", L"\\EFI\\Boot\\boot" EFI_MACHINE_TYPE_NAME ".efi");
|
||||
config_entry_add_osx(&config);
|
||||
|
||||
if (config.auto_firmware && efivar_get_raw(&global_guid, L"OsIndicationsSupported", &b, &size) == EFI_SUCCESS) {
|
||||
UINT64 osind = (UINT64)*b;
|
||||
|
||||
if (config.auto_firmware && efivar_get_uint64_le(EFI_GLOBAL_GUID, L"OsIndicationsSupported", &osind) == EFI_SUCCESS) {
|
||||
if (osind & EFI_OS_INDICATIONS_BOOT_TO_FW_UI)
|
||||
config_entry_add_call(&config,
|
||||
L"auto-reboot-to-firmware-setup",
|
||||
L"Reboot Into Firmware Interface",
|
||||
reboot_into_firmware);
|
||||
FreePool(b);
|
||||
}
|
||||
|
||||
if (config.entry_count == 0) {
|
||||
@ -2497,7 +2466,7 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
|
||||
entry = config.entries[config.idx_default];
|
||||
if (menu) {
|
||||
efivar_set_time_usec(L"LoaderTimeMenuUSec", 0);
|
||||
efivar_set_time_usec(LOADER_GUID, L"LoaderTimeMenuUSec", 0);
|
||||
uefi_call_wrapper(BS->SetWatchdogTimer, 4, 0, 0x10000, 0, NULL);
|
||||
if (!menu_run(&config, &entry, loaded_image_path))
|
||||
break;
|
||||
@ -2512,7 +2481,7 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
config_entry_bump_counters(entry, root_dir);
|
||||
|
||||
/* Export the selected boot entry to the system */
|
||||
(VOID) efivar_set(L"LoaderEntrySelected", entry->id, FALSE);
|
||||
(VOID) efivar_set(LOADER_GUID, L"LoaderEntrySelected", entry->id, FALSE);
|
||||
|
||||
/* Optionally, read a random seed off the ESP and pass it to the OS */
|
||||
(VOID) process_random_seed(root_dir, config.random_seed_mode);
|
||||
|
@ -9,8 +9,8 @@
|
||||
#define SYSTEM_FONT_WIDTH 8
|
||||
#define SYSTEM_FONT_HEIGHT 19
|
||||
|
||||
#define EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL_GUID \
|
||||
{ 0xdd9e7534, 0x7762, 0x4698, { 0x8c, 0x14, 0xf5, 0x85, 0x17, 0xa6, 0x25, 0xaa } }
|
||||
#define EFI_SIMPLE_TEXT_INPUT_EX_GUID \
|
||||
&(EFI_GUID) { 0xdd9e7534, 0x7762, 0x4698, { 0x8c, 0x14, 0xf5, 0x85, 0x17, 0xa6, 0x25, 0xaa } }
|
||||
|
||||
struct _EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL;
|
||||
|
||||
@ -67,7 +67,6 @@ typedef struct _EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL {
|
||||
} EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL;
|
||||
|
||||
EFI_STATUS console_key_read(UINT64 *key, BOOLEAN wait) {
|
||||
EFI_GUID EfiSimpleTextInputExProtocolGuid = EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL_GUID;
|
||||
static EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *TextInputEx;
|
||||
static BOOLEAN checked;
|
||||
UINTN index;
|
||||
@ -75,7 +74,7 @@ EFI_STATUS console_key_read(UINT64 *key, BOOLEAN wait) {
|
||||
EFI_STATUS err;
|
||||
|
||||
if (!checked) {
|
||||
err = LibLocateProtocol(&EfiSimpleTextInputExProtocolGuid, (VOID **)&TextInputEx);
|
||||
err = LibLocateProtocol(EFI_SIMPLE_TEXT_INPUT_EX_GUID, (VOID **)&TextInputEx);
|
||||
if (EFI_ERROR(err))
|
||||
TextInputEx = NULL;
|
||||
|
||||
|
@ -128,9 +128,8 @@ UINT32 crc32_exclude_offset(
|
||||
|
||||
const UINT8 *p = buf;
|
||||
UINT32 crc = seed;
|
||||
UINTN i;
|
||||
|
||||
for (i = 0; i < len; i++) {
|
||||
for (UINTN i = 0; i < len; i++) {
|
||||
UINT8 x = *p++;
|
||||
|
||||
if (i >= exclude_off && i < exclude_off + exclude_len)
|
||||
|
@ -13,10 +13,9 @@ EFI_STATUS disk_get_part_uuid(EFI_HANDLE *handle, CHAR16 uuid[static 37]) {
|
||||
device_path = DevicePathFromHandle(handle);
|
||||
if (device_path) {
|
||||
_cleanup_freepool_ EFI_DEVICE_PATH *paths = NULL;
|
||||
EFI_DEVICE_PATH *path;
|
||||
|
||||
paths = UnpackDevicePath(device_path);
|
||||
for (path = paths; !IsDevicePathEnd(path); path = NextDevicePathNode(path)) {
|
||||
for (EFI_DEVICE_PATH *path = paths; !IsDevicePathEnd(path); path = NextDevicePathNode(path)) {
|
||||
HARDDRIVE_DEVICE_PATH *drive;
|
||||
|
||||
if (DevicePathType(path) != MEDIA_DEVICE_PATH)
|
||||
|
@ -10,9 +10,10 @@
|
||||
#include "graphics.h"
|
||||
#include "util.h"
|
||||
|
||||
#define EFI_CONSOLE_CONTROL_GUID \
|
||||
&(EFI_GUID) { 0xf42f7782, 0x12e, 0x4c12, { 0x99, 0x56, 0x49, 0xf9, 0x43, 0x4, 0xf7, 0x21 } }
|
||||
|
||||
EFI_STATUS graphics_mode(BOOLEAN on) {
|
||||
#define EFI_CONSOLE_CONTROL_PROTOCOL_GUID \
|
||||
{ 0xf42f7782, 0x12e, 0x4c12, { 0x99, 0x56, 0x49, 0xf9, 0x43, 0x4, 0xf7, 0x21 } };
|
||||
|
||||
struct _EFI_CONSOLE_CONTROL_PROTOCOL;
|
||||
|
||||
@ -45,7 +46,6 @@ EFI_STATUS graphics_mode(BOOLEAN on) {
|
||||
EFI_CONSOLE_CONTROL_PROTOCOL_LOCK_STD_IN LockStdIn;
|
||||
} EFI_CONSOLE_CONTROL_PROTOCOL;
|
||||
|
||||
EFI_GUID ConsoleControlProtocolGuid = EFI_CONSOLE_CONTROL_PROTOCOL_GUID;
|
||||
EFI_CONSOLE_CONTROL_PROTOCOL *ConsoleControl = NULL;
|
||||
EFI_CONSOLE_CONTROL_SCREEN_MODE new;
|
||||
EFI_CONSOLE_CONTROL_SCREEN_MODE current;
|
||||
@ -53,7 +53,7 @@ EFI_STATUS graphics_mode(BOOLEAN on) {
|
||||
BOOLEAN stdin_locked;
|
||||
EFI_STATUS err;
|
||||
|
||||
err = LibLocateProtocol(&ConsoleControlProtocolGuid, (VOID **)&ConsoleControl);
|
||||
err = LibLocateProtocol(EFI_CONSOLE_CONTROL_GUID, (VOID **)&ConsoleControl);
|
||||
if (EFI_ERROR(err))
|
||||
/* console control protocol is nonstandard and might not exist. */
|
||||
return err == EFI_NOT_FOUND ? EFI_SUCCESS : err;
|
||||
|
@ -4,9 +4,11 @@
|
||||
|
||||
#include <efi.h>
|
||||
#include <efilib.h>
|
||||
|
||||
#include "measure.h"
|
||||
|
||||
#define EFI_TCG_PROTOCOL_GUID { 0xf541796d, 0xa62e, 0x4954, {0xa7, 0x75, 0x95, 0x84, 0xf6, 0x1b, 0x9c, 0xdd} }
|
||||
#define EFI_TCG_GUID \
|
||||
&(EFI_GUID) { 0xf541796d, 0xa62e, 0x4954, { 0xa7, 0x75, 0x95, 0x84, 0xf6, 0x1b, 0x9c, 0xdd } }
|
||||
|
||||
typedef struct _TCG_VERSION {
|
||||
UINT8 Major;
|
||||
@ -100,7 +102,8 @@ typedef struct _EFI_TCG {
|
||||
EFI_TCG_HASH_LOG_EXTEND_EVENT HashLogExtendEvent;
|
||||
} EFI_TCG;
|
||||
|
||||
#define EFI_TCG2_PROTOCOL_GUID {0x607f766c, 0x7455, 0x42be, { 0x93, 0x0b, 0xe4, 0xd7, 0x6d, 0xb2, 0x72, 0x0f }}
|
||||
#define EFI_TCG2_GUID \
|
||||
&(EFI_GUID) { 0x607f766c, 0x7455, 0x42be, { 0x93, 0x0b, 0xe4, 0xd7, 0x6d, 0xb2, 0x72, 0x0f } }
|
||||
|
||||
typedef struct tdEFI_TCG2_PROTOCOL EFI_TCG2_PROTOCOL;
|
||||
|
||||
@ -238,7 +241,6 @@ static EFI_STATUS tpm2_measure_to_pcr_and_event_log(const EFI_TCG2 *tcg, UINT32
|
||||
}
|
||||
|
||||
static EFI_TCG * tcg1_interface_check(void) {
|
||||
EFI_GUID tpm_guid = EFI_TCG_PROTOCOL_GUID;
|
||||
EFI_STATUS status;
|
||||
EFI_TCG *tcg;
|
||||
TCG_BOOT_SERVICE_CAPABILITY capability;
|
||||
@ -246,7 +248,7 @@ static EFI_TCG * tcg1_interface_check(void) {
|
||||
EFI_PHYSICAL_ADDRESS event_log_location;
|
||||
EFI_PHYSICAL_ADDRESS event_log_last_entry;
|
||||
|
||||
status = LibLocateProtocol(&tpm_guid, (void **) &tcg);
|
||||
status = LibLocateProtocol(EFI_TCG_GUID, (void **) &tcg);
|
||||
|
||||
if (EFI_ERROR(status))
|
||||
return NULL;
|
||||
@ -267,12 +269,11 @@ static EFI_TCG * tcg1_interface_check(void) {
|
||||
}
|
||||
|
||||
static EFI_TCG2 * tcg2_interface_check(void) {
|
||||
EFI_GUID tpm2_guid = EFI_TCG2_PROTOCOL_GUID;
|
||||
EFI_STATUS status;
|
||||
EFI_TCG2 *tcg;
|
||||
EFI_TCG2_BOOT_SERVICE_CAPABILITY capability;
|
||||
|
||||
status = LibLocateProtocol(&tpm2_guid, (void **) &tcg);
|
||||
status = LibLocateProtocol(EFI_TCG2_GUID, (void **) &tcg);
|
||||
|
||||
if (EFI_ERROR(status))
|
||||
return NULL;
|
||||
|
@ -21,6 +21,7 @@ common_sources = '''
|
||||
graphics.c
|
||||
measure.c
|
||||
pe.c
|
||||
secure-boot.c
|
||||
util.c
|
||||
'''.split()
|
||||
|
||||
@ -133,8 +134,8 @@ endif
|
||||
if have_gnu_efi
|
||||
compile_args = ['-Wall',
|
||||
'-Wextra',
|
||||
'-std=gnu90',
|
||||
'-nostdinc',
|
||||
'-std=gnu99',
|
||||
'-nostdlib',
|
||||
'-fpic',
|
||||
'-fshort-wchar',
|
||||
'-ffreestanding',
|
||||
|
@ -62,7 +62,6 @@ struct PeSectionHeader {
|
||||
EFI_STATUS pe_memory_locate_sections(CHAR8 *base, CHAR8 **sections, UINTN *addrs, UINTN *offsets, UINTN *sizes) {
|
||||
struct DosFileHeader *dos;
|
||||
struct PeHeader *pe;
|
||||
UINTN i;
|
||||
UINTN offset;
|
||||
|
||||
dos = (struct DosFileHeader *)base;
|
||||
@ -85,12 +84,11 @@ EFI_STATUS pe_memory_locate_sections(CHAR8 *base, CHAR8 **sections, UINTN *addrs
|
||||
|
||||
offset = dos->ExeHeader + sizeof(*pe) + pe->FileHeader.SizeOfOptionalHeader;
|
||||
|
||||
for (i = 0; i < pe->FileHeader.NumberOfSections; i++) {
|
||||
for (UINTN i = 0; i < pe->FileHeader.NumberOfSections; i++) {
|
||||
struct PeSectionHeader *sect;
|
||||
UINTN j;
|
||||
|
||||
sect = (struct PeSectionHeader *)&base[offset];
|
||||
for (j = 0; sections[j]; j++) {
|
||||
for (UINTN j = 0; sections[j]; j++) {
|
||||
if (CompareMem(sect->Name, sections[j], strlena(sections[j])) != 0)
|
||||
continue;
|
||||
|
||||
|
@ -5,14 +5,14 @@
|
||||
|
||||
#include "missing_efi.h"
|
||||
#include "random-seed.h"
|
||||
#include "secure-boot.h"
|
||||
#include "sha256.h"
|
||||
#include "util.h"
|
||||
#include "shim.h"
|
||||
|
||||
#define RANDOM_MAX_SIZE_MIN (32U)
|
||||
#define RANDOM_MAX_SIZE_MAX (32U*1024U)
|
||||
|
||||
static const EFI_GUID rng_protocol_guid = EFI_RNG_PROTOCOL_GUID;
|
||||
#define EFI_RNG_GUID &(EFI_GUID) EFI_RNG_PROTOCOL_GUID
|
||||
|
||||
/* SHA256 gives us 256/8=32 bytes */
|
||||
#define HASH_VALUE_SIZE 32
|
||||
@ -24,7 +24,7 @@ static EFI_STATUS acquire_rng(UINTN size, VOID **ret) {
|
||||
|
||||
/* Try to acquire the specified number of bytes from the UEFI RNG */
|
||||
|
||||
err = LibLocateProtocol((EFI_GUID*) &rng_protocol_guid, (VOID**) &rng);
|
||||
err = LibLocateProtocol(EFI_RNG_GUID, (VOID**) &rng);
|
||||
if (EFI_ERROR(err))
|
||||
return err;
|
||||
if (!rng)
|
||||
@ -86,7 +86,6 @@ static EFI_STATUS hash_many(
|
||||
VOID **ret) {
|
||||
|
||||
_cleanup_freepool_ VOID *output = NULL;
|
||||
UINTN i;
|
||||
|
||||
/* Hashes the specified parameters in counter mode, generating n hash values, with the counter in the
|
||||
* range counter_start…counter_start+n-1. */
|
||||
@ -95,7 +94,7 @@ static EFI_STATUS hash_many(
|
||||
if (!output)
|
||||
return log_oom();
|
||||
|
||||
for (i = 0; i < n; i++)
|
||||
for (UINTN i = 0; i < n; i++)
|
||||
hash_once(old_seed, rng, size,
|
||||
system_token, system_token_size,
|
||||
counter_start + i,
|
||||
@ -147,7 +146,7 @@ static EFI_STATUS acquire_system_token(VOID **ret, UINTN *ret_size) {
|
||||
EFI_STATUS err;
|
||||
UINTN size;
|
||||
|
||||
err = efivar_get_raw(&loader_guid, L"LoaderSystemToken", &data, &size);
|
||||
err = efivar_get_raw(LOADER_GUID, L"LoaderSystemToken", &data, &size);
|
||||
if (EFI_ERROR(err)) {
|
||||
if (err != EFI_NOT_FOUND)
|
||||
Print(L"Failed to read LoaderSystemToken EFI variable: %r", err);
|
||||
@ -201,9 +200,7 @@ static VOID validate_sha256(void) {
|
||||
0xaf, 0xac, 0x45, 0x03, 0x7a, 0xfe, 0xe9, 0xd1 }},
|
||||
};
|
||||
|
||||
UINTN i;
|
||||
|
||||
for (i = 0; i < ELEMENTSOF(array); i++) {
|
||||
for (UINTN i = 0; i < ELEMENTSOF(array); i++) {
|
||||
struct sha256_ctx hash;
|
||||
uint8_t result[HASH_VALUE_SIZE];
|
||||
|
||||
@ -318,7 +315,7 @@ EFI_STATUS process_random_seed(EFI_FILE *root_dir, RandomSeedMode mode) {
|
||||
}
|
||||
|
||||
/* We are good to go */
|
||||
err = efivar_set_raw(&loader_guid, L"LoaderRandomSeed", for_kernel, size, FALSE);
|
||||
err = efivar_set_raw(LOADER_GUID, L"LoaderRandomSeed", for_kernel, size, FALSE);
|
||||
if (EFI_ERROR(err)) {
|
||||
Print(L"Failed to write random seed to EFI variable: %r\n", err);
|
||||
return err;
|
||||
|
13
src/boot/efi/secure-boot.c
Normal file
13
src/boot/efi/secure-boot.c
Normal file
@ -0,0 +1,13 @@
|
||||
/* SPDX-License-Identifier: LGPL-2.1-or-later */
|
||||
|
||||
#include "secure-boot.h"
|
||||
#include "util.h"
|
||||
|
||||
BOOLEAN secure_boot_enabled(void) {
|
||||
BOOLEAN secure;
|
||||
EFI_STATUS err;
|
||||
|
||||
err = efivar_get_boolean_u8(EFI_GLOBAL_GUID, L"SecureBoot", &secure);
|
||||
|
||||
return !EFI_ERROR(err) && secure;
|
||||
}
|
6
src/boot/efi/secure-boot.h
Normal file
6
src/boot/efi/secure-boot.h
Normal file
@ -0,0 +1,6 @@
|
||||
/* SPDX-License-Identifier: LGPL-2.1-or-later */
|
||||
#pragma once
|
||||
|
||||
#include <efi.h>
|
||||
|
||||
BOOLEAN secure_boot_enabled(void);
|
@ -94,7 +94,7 @@ void sha256_init_ctx(struct sha256_ctx *ctx) {
|
||||
void *sha256_finish_ctx(struct sha256_ctx *ctx, void *resbuf) {
|
||||
/* Take yet unprocessed bytes into account. */
|
||||
UINT32 bytes = ctx->buflen;
|
||||
UINTN pad, i;
|
||||
UINTN pad;
|
||||
|
||||
/* Now count remaining bytes. */
|
||||
ctx->total64 += bytes;
|
||||
@ -111,7 +111,7 @@ void *sha256_finish_ctx(struct sha256_ctx *ctx, void *resbuf) {
|
||||
sha256_process_block (ctx->buffer, bytes + pad + 8, ctx);
|
||||
|
||||
/* Put result from CTX in first 32 bytes following RESBUF. */
|
||||
for (i = 0; i < 8; ++i)
|
||||
for (UINTN i = 0; i < 8; ++i)
|
||||
((UINT32 *) resbuf)[i] = SWAP (ctx->H[i]);
|
||||
|
||||
return resbuf;
|
||||
@ -214,7 +214,6 @@ static void sha256_process_block(const void *buffer, UINTN len, struct sha256_ct
|
||||
UINT32 f_save = f;
|
||||
UINT32 g_save = g;
|
||||
UINT32 h_save = h;
|
||||
UINTN t;
|
||||
|
||||
/* Operators defined in FIPS 180-2:4.1.2. */
|
||||
#define Ch(x, y, z) ((x & y) ^ (~x & z))
|
||||
@ -229,15 +228,15 @@ static void sha256_process_block(const void *buffer, UINTN len, struct sha256_ct
|
||||
#define CYCLIC(w, s) ((w >> s) | (w << (32 - s)))
|
||||
|
||||
/* Compute the message schedule according to FIPS 180-2:6.2.2 step 2. */
|
||||
for (t = 0; t < 16; ++t) {
|
||||
for (UINTN t = 0; t < 16; ++t) {
|
||||
W[t] = SWAP (*words);
|
||||
++words;
|
||||
}
|
||||
for (t = 16; t < 64; ++t)
|
||||
for (UINTN t = 16; t < 64; ++t)
|
||||
W[t] = R1 (W[t - 2]) + W[t - 7] + R0 (W[t - 15]) + W[t - 16];
|
||||
|
||||
/* The actual computation according to FIPS 180-2:6.2.2 step 3. */
|
||||
for (t = 0; t < 64; ++t) {
|
||||
for (UINTN t = 0; t < 64; ++t) {
|
||||
UINT32 T1 = h + S1 (e) + Ch (e, f, g) + K[t] + W[t];
|
||||
UINT32 T2 = S0 (a) + Maj (a, b, c);
|
||||
h = g;
|
||||
|
@ -30,17 +30,18 @@ struct ShimLock {
|
||||
EFI_STATUS __sysv_abi__ (*read_header) (VOID *data, UINT32 datasize, VOID *context);
|
||||
};
|
||||
|
||||
static const EFI_GUID simple_fs_guid = SIMPLE_FILE_SYSTEM_PROTOCOL;
|
||||
static const EFI_GUID global_guid = EFI_GLOBAL_VARIABLE;
|
||||
|
||||
static const EFI_GUID security_protocol_guid = { 0xa46423e3, 0x4617, 0x49f1, {0xb9, 0xff, 0xd1, 0xbf, 0xa9, 0x11, 0x58, 0x39 } };
|
||||
static const EFI_GUID security2_protocol_guid = { 0x94ab2f58, 0x1438, 0x4ef1, {0x91, 0x52, 0x18, 0x94, 0x1a, 0x3a, 0x0e, 0x68 } };
|
||||
static const EFI_GUID shim_lock_guid = { 0x605dab50, 0xe046, 0x4300, {0xab, 0xb6, 0x3d, 0xd8, 0x10, 0xdd, 0x8b, 0x23} };
|
||||
#define SIMPLE_FS_GUID &(EFI_GUID) SIMPLE_FILE_SYSTEM_PROTOCOL
|
||||
#define SECURITY_PROTOCOL_GUID \
|
||||
&(EFI_GUID) { 0xa46423e3, 0x4617, 0x49f1, { 0xb9, 0xff, 0xd1, 0xbf, 0xa9, 0x11, 0x58, 0x39 } }
|
||||
#define SECURITY_PROTOCOL2_GUID \
|
||||
&(EFI_GUID) { 0x94ab2f58, 0x1438, 0x4ef1, { 0x91, 0x52, 0x18, 0x94, 0x1a, 0x3a, 0x0e, 0x68 } }
|
||||
#define SHIM_LOCK_GUID \
|
||||
&(EFI_GUID) { 0x605dab50, 0xe046, 0x4300, { 0xab, 0xb6, 0x3d, 0xd8, 0x10, 0xdd, 0x8b, 0x23 } }
|
||||
|
||||
BOOLEAN shim_loaded(void) {
|
||||
struct ShimLock *shim_lock;
|
||||
|
||||
return uefi_call_wrapper(BS->LocateProtocol, 3, (EFI_GUID*) &shim_lock_guid, NULL, (VOID**) &shim_lock) == EFI_SUCCESS;
|
||||
return uefi_call_wrapper(BS->LocateProtocol, 3, SHIM_LOCK_GUID, NULL, (VOID**) &shim_lock) == EFI_SUCCESS;
|
||||
}
|
||||
|
||||
static BOOLEAN shim_validate(VOID *data, UINT32 size) {
|
||||
@ -49,7 +50,7 @@ static BOOLEAN shim_validate(VOID *data, UINT32 size) {
|
||||
if (!data)
|
||||
return FALSE;
|
||||
|
||||
if (uefi_call_wrapper(BS->LocateProtocol, 3, (EFI_GUID*) &shim_lock_guid, NULL, (VOID**) &shim_lock) != EFI_SUCCESS)
|
||||
if (uefi_call_wrapper(BS->LocateProtocol, 3, SHIM_LOCK_GUID, NULL, (VOID**) &shim_lock) != EFI_SUCCESS)
|
||||
return FALSE;
|
||||
|
||||
if (!shim_lock)
|
||||
@ -58,16 +59,6 @@ static BOOLEAN shim_validate(VOID *data, UINT32 size) {
|
||||
return shim_lock->shim_verify(data, size) == EFI_SUCCESS;
|
||||
}
|
||||
|
||||
BOOLEAN secure_boot_enabled(void) {
|
||||
_cleanup_freepool_ CHAR8 *b = NULL;
|
||||
UINTN size;
|
||||
|
||||
if (efivar_get_raw(&global_guid, L"SecureBoot", &b, &size) == EFI_SUCCESS)
|
||||
return *b > 0;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/*
|
||||
* See the UEFI Platform Initialization manual (Vol2: DXE) for this
|
||||
*/
|
||||
@ -157,7 +148,7 @@ static EFIAPI EFI_STATUS security_policy_authentication (const EFI_SECURITY_PROT
|
||||
|
||||
dev_path = DuplicateDevicePath((EFI_DEVICE_PATH*) device_path_const);
|
||||
|
||||
status = uefi_call_wrapper(BS->LocateDevicePath, 3, (EFI_GUID*) &simple_fs_guid, &dev_path, &h);
|
||||
status = uefi_call_wrapper(BS->LocateDevicePath, 3, SIMPLE_FS_GUID, &dev_path, &h);
|
||||
if (status != EFI_SUCCESS)
|
||||
return status;
|
||||
|
||||
@ -191,9 +182,9 @@ EFI_STATUS security_policy_install(void) {
|
||||
* to fail, since SECURITY2 was introduced in PI 1.2.1.
|
||||
* Use security2_protocol == NULL as indicator.
|
||||
*/
|
||||
uefi_call_wrapper(BS->LocateProtocol, 3, (EFI_GUID*) &security2_protocol_guid, NULL, (VOID**) &security2_protocol);
|
||||
uefi_call_wrapper(BS->LocateProtocol, 3, SECURITY_PROTOCOL2_GUID, NULL, (VOID**) &security2_protocol);
|
||||
|
||||
status = uefi_call_wrapper(BS->LocateProtocol, 3, (EFI_GUID*) &security_protocol_guid, NULL, (VOID**) &security_protocol);
|
||||
status = uefi_call_wrapper(BS->LocateProtocol, 3, SECURITY_PROTOCOL_GUID, NULL, (VOID**) &security_protocol);
|
||||
/* This one is mandatory, so there's a serious problem */
|
||||
if (status != EFI_SUCCESS)
|
||||
return status;
|
||||
|
@ -13,6 +13,4 @@
|
||||
|
||||
BOOLEAN shim_loaded(void);
|
||||
|
||||
BOOLEAN secure_boot_enabled(void);
|
||||
|
||||
EFI_STATUS security_policy_install(void);
|
||||
|
@ -151,22 +151,18 @@ static EFI_STATUS bmp_to_blt(EFI_GRAPHICS_OUTPUT_BLT_PIXEL *buf,
|
||||
struct bmp_dib *dib, struct bmp_map *map,
|
||||
UINT8 *pixmap) {
|
||||
UINT8 *in;
|
||||
UINTN y;
|
||||
|
||||
/* transform and copy pixels */
|
||||
in = pixmap;
|
||||
for (y = 0; y < dib->y; y++) {
|
||||
for (UINTN y = 0; y < dib->y; y++) {
|
||||
EFI_GRAPHICS_OUTPUT_BLT_PIXEL *out;
|
||||
UINTN row_size;
|
||||
UINTN x;
|
||||
|
||||
out = &buf[(dib->y - y - 1) * dib->x];
|
||||
for (x = 0; x < dib->x; x++, in++, out++) {
|
||||
for (UINTN x = 0; x < dib->x; x++, in++, out++) {
|
||||
switch (dib->depth) {
|
||||
case 1: {
|
||||
UINTN i;
|
||||
|
||||
for (i = 0; i < 8 && x < dib->x; i++) {
|
||||
for (UINTN i = 0; i < 8 && x < dib->x; i++) {
|
||||
out->Red = map[((*in) >> (7 - i)) & 1].red;
|
||||
out->Green = map[((*in) >> (7 - i)) & 1].green;
|
||||
out->Blue = map[((*in) >> (7 - i)) & 1].blue;
|
||||
|
@ -8,19 +8,15 @@
|
||||
#include "linux.h"
|
||||
#include "measure.h"
|
||||
#include "pe.h"
|
||||
#include "secure-boot.h"
|
||||
#include "splash.h"
|
||||
#include "util.h"
|
||||
|
||||
/* magic string to find in the binary image */
|
||||
static const char __attribute__((used)) magic[] = "#### LoaderInfo: systemd-stub " GIT_VERSION " ####";
|
||||
|
||||
static const EFI_GUID global_guid = EFI_GLOBAL_VARIABLE;
|
||||
|
||||
EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
EFI_LOADED_IMAGE *loaded_image;
|
||||
_cleanup_freepool_ CHAR8 *b = NULL;
|
||||
UINTN size;
|
||||
BOOLEAN secure = FALSE;
|
||||
CHAR8 *sections[] = {
|
||||
(CHAR8 *)".cmdline",
|
||||
(CHAR8 *)".linux",
|
||||
@ -46,10 +42,6 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
return err;
|
||||
}
|
||||
|
||||
if (efivar_get_raw(&global_guid, L"SecureBoot", &b, &size) == EFI_SUCCESS)
|
||||
if (*b > 0)
|
||||
secure = TRUE;
|
||||
|
||||
err = pe_memory_locate_sections(loaded_image->ImageBase, sections, addrs, offs, szs);
|
||||
if (EFI_ERROR(err)) {
|
||||
Print(L"Unable to locate embedded .linux section: %r ", err);
|
||||
@ -58,20 +50,20 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
}
|
||||
|
||||
if (szs[0] > 0)
|
||||
cmdline = (CHAR8 *)(loaded_image->ImageBase + addrs[0]);
|
||||
cmdline = (CHAR8 *)(loaded_image->ImageBase) + addrs[0];
|
||||
|
||||
cmdline_len = szs[0];
|
||||
|
||||
/* if we are not in secure boot mode, or none was provided, accept a custom command line and replace the built-in one */
|
||||
if ((!secure || cmdline_len == 0) && loaded_image->LoadOptionsSize > 0 && *(CHAR16 *)loaded_image->LoadOptions > 0x1F) {
|
||||
if ((!secure_boot_enabled() || cmdline_len == 0) && loaded_image->LoadOptionsSize > 0 &&
|
||||
*(CHAR16 *) loaded_image->LoadOptions > 0x1F) {
|
||||
CHAR16 *options;
|
||||
CHAR8 *line;
|
||||
UINTN i;
|
||||
|
||||
options = (CHAR16 *)loaded_image->LoadOptions;
|
||||
cmdline_len = (loaded_image->LoadOptionsSize / sizeof(CHAR16)) * sizeof(CHAR8);
|
||||
line = AllocatePool(cmdline_len);
|
||||
for (i = 0; i < cmdline_len; i++)
|
||||
for (UINTN i = 0; i < cmdline_len; i++)
|
||||
line[i] = options[i];
|
||||
cmdline = line;
|
||||
|
||||
@ -88,37 +80,37 @@ EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *sys_table) {
|
||||
}
|
||||
|
||||
/* Export the device path this image is started from, if it's not set yet */
|
||||
if (efivar_get_raw(&loader_guid, L"LoaderDevicePartUUID", NULL, NULL) != EFI_SUCCESS)
|
||||
if (efivar_get_raw(LOADER_GUID, L"LoaderDevicePartUUID", NULL, NULL) != EFI_SUCCESS)
|
||||
if (disk_get_part_uuid(loaded_image->DeviceHandle, uuid) == EFI_SUCCESS)
|
||||
efivar_set(L"LoaderDevicePartUUID", uuid, FALSE);
|
||||
efivar_set(LOADER_GUID, L"LoaderDevicePartUUID", uuid, FALSE);
|
||||
|
||||
/* if LoaderImageIdentifier is not set, assume the image with this stub was loaded directly from UEFI */
|
||||
if (efivar_get_raw(&loader_guid, L"LoaderImageIdentifier", NULL, NULL) != EFI_SUCCESS) {
|
||||
if (efivar_get_raw(LOADER_GUID, L"LoaderImageIdentifier", NULL, NULL) != EFI_SUCCESS) {
|
||||
_cleanup_freepool_ CHAR16 *s;
|
||||
|
||||
s = DevicePathToStr(loaded_image->FilePath);
|
||||
efivar_set(L"LoaderImageIdentifier", s, FALSE);
|
||||
efivar_set(LOADER_GUID, L"LoaderImageIdentifier", s, FALSE);
|
||||
}
|
||||
|
||||
/* if LoaderFirmwareInfo is not set, let's set it */
|
||||
if (efivar_get_raw(&loader_guid, L"LoaderFirmwareInfo", NULL, NULL) != EFI_SUCCESS) {
|
||||
if (efivar_get_raw(LOADER_GUID, L"LoaderFirmwareInfo", NULL, NULL) != EFI_SUCCESS) {
|
||||
_cleanup_freepool_ CHAR16 *s;
|
||||
|
||||
s = PoolPrint(L"%s %d.%02d", ST->FirmwareVendor, ST->FirmwareRevision >> 16, ST->FirmwareRevision & 0xffff);
|
||||
efivar_set(L"LoaderFirmwareInfo", s, FALSE);
|
||||
efivar_set(LOADER_GUID, L"LoaderFirmwareInfo", s, FALSE);
|
||||
}
|
||||
|
||||
/* ditto for LoaderFirmwareType */
|
||||
if (efivar_get_raw(&loader_guid, L"LoaderFirmwareType", NULL, NULL) != EFI_SUCCESS) {
|
||||
if (efivar_get_raw(LOADER_GUID, L"LoaderFirmwareType", NULL, NULL) != EFI_SUCCESS) {
|
||||
_cleanup_freepool_ CHAR16 *s;
|
||||
|
||||
s = PoolPrint(L"UEFI %d.%02d", ST->Hdr.Revision >> 16, ST->Hdr.Revision & 0xffff);
|
||||
efivar_set(L"LoaderFirmwareType", s, FALSE);
|
||||
efivar_set(LOADER_GUID, L"LoaderFirmwareType", s, FALSE);
|
||||
}
|
||||
|
||||
/* add StubInfo */
|
||||
if (efivar_get_raw(&loader_guid, L"StubInfo", NULL, NULL) != EFI_SUCCESS)
|
||||
efivar_set(L"StubInfo", L"systemd-stub " GIT_VERSION, FALSE);
|
||||
if (efivar_get_raw(LOADER_GUID, L"StubInfo", NULL, NULL) != EFI_SUCCESS)
|
||||
efivar_set(LOADER_GUID, L"StubInfo", L"systemd-stub " GIT_VERSION, FALSE);
|
||||
|
||||
if (szs[3] > 0)
|
||||
graphics_splash((UINT8 *)((UINTN)loaded_image->ImageBase + addrs[3]), szs[3], NULL);
|
||||
|
@ -5,13 +5,6 @@
|
||||
|
||||
#include "util.h"
|
||||
|
||||
/*
|
||||
* Allocated random UUID, intended to be shared across tools that implement
|
||||
* the (ESP)\loader\entries\<vendor>-<revision>.conf convention and the
|
||||
* associated EFI variables.
|
||||
*/
|
||||
const EFI_GUID loader_guid = { 0x4a67b082, 0x0a4c, 0x41cf, {0xb6, 0xc7, 0x44, 0x0b, 0x29, 0xbb, 0x8c, 0x4f} };
|
||||
|
||||
#ifdef __x86_64__
|
||||
UINT64 ticks_read(VOID) {
|
||||
UINT64 a, d;
|
||||
@ -92,24 +85,51 @@ EFI_STATUS efivar_set_raw(const EFI_GUID *vendor, const CHAR16 *name, const VOID
|
||||
return uefi_call_wrapper(RT->SetVariable, 5, (CHAR16*) name, (EFI_GUID *)vendor, flags, size, (VOID*) buf);
|
||||
}
|
||||
|
||||
EFI_STATUS efivar_set(const CHAR16 *name, const CHAR16 *value, BOOLEAN persistent) {
|
||||
return efivar_set_raw(&loader_guid, name, value, value ? (StrLen(value)+1) * sizeof(CHAR16) : 0, persistent);
|
||||
EFI_STATUS efivar_set(const EFI_GUID *vendor, const CHAR16 *name, const CHAR16 *value, BOOLEAN persistent) {
|
||||
return efivar_set_raw(
|
||||
vendor, name, value, value ? (StrLen(value) + 1) * sizeof(CHAR16) : 0, persistent);
|
||||
}
|
||||
|
||||
EFI_STATUS efivar_set_int(CHAR16 *name, UINTN i, BOOLEAN persistent) {
|
||||
EFI_STATUS efivar_set_uint_string(const EFI_GUID *vendor, CHAR16 *name, UINTN i, BOOLEAN persistent) {
|
||||
CHAR16 str[32];
|
||||
|
||||
SPrint(str, 32, L"%u", i);
|
||||
return efivar_set(name, str, persistent);
|
||||
return efivar_set(vendor, name, str, persistent);
|
||||
}
|
||||
|
||||
EFI_STATUS efivar_get(const CHAR16 *name, CHAR16 **value) {
|
||||
EFI_STATUS efivar_set_uint32_le(const EFI_GUID *vendor, CHAR16 *name, UINT32 value, BOOLEAN persistent) {
|
||||
UINT8 buf[4];
|
||||
|
||||
buf[0] = (UINT8)(value >> 0U & 0xFF);
|
||||
buf[1] = (UINT8)(value >> 8U & 0xFF);
|
||||
buf[2] = (UINT8)(value >> 16U & 0xFF);
|
||||
buf[3] = (UINT8)(value >> 24U & 0xFF);
|
||||
|
||||
return efivar_set_raw(vendor, name, buf, sizeof(buf), persistent);
|
||||
}
|
||||
|
||||
EFI_STATUS efivar_set_uint64_le(const EFI_GUID *vendor, CHAR16 *name, UINT64 value, BOOLEAN persistent) {
|
||||
UINT8 buf[8];
|
||||
|
||||
buf[0] = (UINT8)(value >> 0U & 0xFF);
|
||||
buf[1] = (UINT8)(value >> 8U & 0xFF);
|
||||
buf[2] = (UINT8)(value >> 16U & 0xFF);
|
||||
buf[3] = (UINT8)(value >> 24U & 0xFF);
|
||||
buf[4] = (UINT8)(value >> 32U & 0xFF);
|
||||
buf[5] = (UINT8)(value >> 40U & 0xFF);
|
||||
buf[6] = (UINT8)(value >> 48U & 0xFF);
|
||||
buf[7] = (UINT8)(value >> 56U & 0xFF);
|
||||
|
||||
return efivar_set_raw(vendor, name, buf, sizeof(buf), persistent);
|
||||
}
|
||||
|
||||
EFI_STATUS efivar_get(const EFI_GUID *vendor, const CHAR16 *name, CHAR16 **value) {
|
||||
_cleanup_freepool_ CHAR8 *buf = NULL;
|
||||
EFI_STATUS err;
|
||||
CHAR16 *val;
|
||||
UINTN size;
|
||||
|
||||
err = efivar_get_raw(&loader_guid, name, &buf, &size);
|
||||
err = efivar_get_raw(vendor, name, &buf, &size);
|
||||
if (EFI_ERROR(err))
|
||||
return err;
|
||||
|
||||
@ -138,17 +158,52 @@ EFI_STATUS efivar_get(const CHAR16 *name, CHAR16 **value) {
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
EFI_STATUS efivar_get_int(const CHAR16 *name, UINTN *i) {
|
||||
EFI_STATUS efivar_get_uint_string(const EFI_GUID *vendor, const CHAR16 *name, UINTN *i) {
|
||||
_cleanup_freepool_ CHAR16 *val = NULL;
|
||||
EFI_STATUS err;
|
||||
|
||||
err = efivar_get(name, &val);
|
||||
err = efivar_get(vendor, name, &val);
|
||||
if (!EFI_ERROR(err) && i)
|
||||
*i = Atoi(val);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
EFI_STATUS efivar_get_uint32_le(const EFI_GUID *vendor, const CHAR16 *name, UINT32 *ret) {
|
||||
_cleanup_freepool_ CHAR8 *buf = NULL;
|
||||
UINTN size;
|
||||
EFI_STATUS err;
|
||||
|
||||
err = efivar_get_raw(vendor, name, &buf, &size);
|
||||
if (!EFI_ERROR(err) && ret) {
|
||||
if (size != sizeof(UINT32))
|
||||
return EFI_BUFFER_TOO_SMALL;
|
||||
|
||||
*ret = (UINT32) buf[0] << 0U | (UINT32) buf[1] << 8U | (UINT32) buf[2] << 16U |
|
||||
(UINT32) buf[3] << 24U;
|
||||
}
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
EFI_STATUS efivar_get_uint64_le(const EFI_GUID *vendor, const CHAR16 *name, UINT64 *ret) {
|
||||
_cleanup_freepool_ CHAR8 *buf = NULL;
|
||||
UINTN size;
|
||||
EFI_STATUS err;
|
||||
|
||||
err = efivar_get_raw(vendor, name, &buf, &size);
|
||||
if (!EFI_ERROR(err) && ret) {
|
||||
if (size != sizeof(UINT64))
|
||||
return EFI_BUFFER_TOO_SMALL;
|
||||
|
||||
*ret = (UINT64) buf[0] << 0U | (UINT64) buf[1] << 8U | (UINT64) buf[2] << 16U |
|
||||
(UINT64) buf[3] << 24U | (UINT64) buf[4] << 32U | (UINT64) buf[5] << 40U |
|
||||
(UINT64) buf[6] << 48U | (UINT64) buf[7] << 56U;
|
||||
}
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
EFI_STATUS efivar_get_raw(const EFI_GUID *vendor, const CHAR16 *name, CHAR8 **buffer, UINTN *size) {
|
||||
_cleanup_freepool_ CHAR8 *buf = NULL;
|
||||
UINTN l;
|
||||
@ -172,7 +227,19 @@ EFI_STATUS efivar_get_raw(const EFI_GUID *vendor, const CHAR16 *name, CHAR8 **bu
|
||||
return err;
|
||||
}
|
||||
|
||||
VOID efivar_set_time_usec(CHAR16 *name, UINT64 usec) {
|
||||
EFI_STATUS efivar_get_boolean_u8(const EFI_GUID *vendor, const CHAR16 *name, BOOLEAN *ret) {
|
||||
_cleanup_freepool_ CHAR8 *b = NULL;
|
||||
UINTN size;
|
||||
EFI_STATUS err;
|
||||
|
||||
err = efivar_get_raw(vendor, name, &b, &size);
|
||||
if (!EFI_ERROR(err))
|
||||
*ret = *b > 0;
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
VOID efivar_set_time_usec(const EFI_GUID *vendor, CHAR16 *name, UINT64 usec) {
|
||||
CHAR16 str[32];
|
||||
|
||||
if (usec == 0)
|
||||
@ -181,13 +248,12 @@ VOID efivar_set_time_usec(CHAR16 *name, UINT64 usec) {
|
||||
return;
|
||||
|
||||
SPrint(str, 32, L"%ld", usec);
|
||||
efivar_set(name, str, FALSE);
|
||||
efivar_set(vendor, name, str, FALSE);
|
||||
}
|
||||
|
||||
static INTN utf8_to_16(CHAR8 *stra, CHAR16 *c) {
|
||||
CHAR16 unichar;
|
||||
UINTN len;
|
||||
UINTN i;
|
||||
|
||||
if (!(stra[0] & 0x80))
|
||||
len = 1;
|
||||
@ -225,7 +291,7 @@ static INTN utf8_to_16(CHAR8 *stra, CHAR16 *c) {
|
||||
break;
|
||||
}
|
||||
|
||||
for (i = 1; i < len; i++) {
|
||||
for (UINTN i = 1; i < len; i++) {
|
||||
if ((stra[i] & 0xc0) != 0x80)
|
||||
return -1;
|
||||
unichar <<= 6;
|
||||
@ -309,6 +375,62 @@ CHAR8 *strchra(CHAR8 *s, CHAR8 c) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
const CHAR16 *startswith(const CHAR16 *s, const CHAR16 *prefix) {
|
||||
UINTN l;
|
||||
|
||||
l = StrLen(prefix);
|
||||
if (StrnCmp(s, prefix, l) == 0)
|
||||
return s + l;
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
const CHAR16 *endswith(const CHAR16 *s, const CHAR16 *postfix) {
|
||||
UINTN sl, pl;
|
||||
|
||||
sl = StrLen(s);
|
||||
pl = StrLen(postfix);
|
||||
|
||||
if (pl == 0)
|
||||
return s + sl;
|
||||
|
||||
if (sl < pl)
|
||||
return NULL;
|
||||
|
||||
if (StrnCmp(s + sl - pl, postfix, pl) != 0)
|
||||
return NULL;
|
||||
|
||||
return s + sl - pl;
|
||||
}
|
||||
|
||||
const CHAR16 *startswith_no_case(const CHAR16 *s, const CHAR16 *prefix) {
|
||||
UINTN l;
|
||||
|
||||
l = StrLen(prefix);
|
||||
if (StriCmp(s, prefix) == 0)
|
||||
return s + l;
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
const CHAR16 *endswith_no_case(const CHAR16 *s, const CHAR16 *postfix) {
|
||||
UINTN sl, pl;
|
||||
|
||||
sl = StrLen(s);
|
||||
pl = StrLen(postfix);
|
||||
|
||||
if (pl == 0)
|
||||
return s + sl;
|
||||
|
||||
if (sl < pl)
|
||||
return NULL;
|
||||
|
||||
if (StriCmp(s + sl - pl, postfix) != 0)
|
||||
return NULL;
|
||||
|
||||
return s + sl - pl;
|
||||
}
|
||||
|
||||
EFI_STATUS file_read(EFI_FILE_HANDLE dir, const CHAR16 *name, UINTN off, UINTN size, CHAR8 **ret, UINTN *ret_size) {
|
||||
_cleanup_(FileHandleClosep) EFI_FILE_HANDLE handle = NULL;
|
||||
_cleanup_freepool_ CHAR8 *buf = NULL;
|
||||
|
@ -21,19 +21,30 @@ UINT64 ticks_read(void);
|
||||
UINT64 ticks_freq(void);
|
||||
UINT64 time_usec(void);
|
||||
|
||||
EFI_STATUS efivar_set(const CHAR16 *name, const CHAR16 *value, BOOLEAN persistent);
|
||||
EFI_STATUS efivar_set(const EFI_GUID *vendor, const CHAR16 *name, const CHAR16 *value, BOOLEAN persistent);
|
||||
EFI_STATUS efivar_set_raw(const EFI_GUID *vendor, const CHAR16 *name, const VOID *buf, UINTN size, BOOLEAN persistent);
|
||||
EFI_STATUS efivar_set_int(CHAR16 *name, UINTN i, BOOLEAN persistent);
|
||||
VOID efivar_set_time_usec(CHAR16 *name, UINT64 usec);
|
||||
EFI_STATUS efivar_set_uint_string(const EFI_GUID *vendor, CHAR16 *name, UINTN i, BOOLEAN persistent);
|
||||
EFI_STATUS efivar_set_uint32_le(const EFI_GUID *vendor, CHAR16 *NAME, UINT32 value, BOOLEAN persistent);
|
||||
EFI_STATUS efivar_set_uint64_le(const EFI_GUID *vendor, CHAR16 *name, UINT64 value, BOOLEAN persistent);
|
||||
VOID efivar_set_time_usec(const EFI_GUID *vendor, CHAR16 *name, UINT64 usec);
|
||||
|
||||
EFI_STATUS efivar_get(const CHAR16 *name, CHAR16 **value);
|
||||
EFI_STATUS efivar_get(const EFI_GUID *vendor, const CHAR16 *name, CHAR16 **value);
|
||||
EFI_STATUS efivar_get_raw(const EFI_GUID *vendor, const CHAR16 *name, CHAR8 **buffer, UINTN *size);
|
||||
EFI_STATUS efivar_get_int(const CHAR16 *name, UINTN *i);
|
||||
EFI_STATUS efivar_get_uint_string(const EFI_GUID *vendor, const CHAR16 *name, UINTN *i);
|
||||
EFI_STATUS efivar_get_uint32_le(const EFI_GUID *vendor, const CHAR16 *name, UINT32 *ret);
|
||||
EFI_STATUS efivar_get_uint64_le(const EFI_GUID *vendor, const CHAR16 *name, UINT64 *ret);
|
||||
EFI_STATUS efivar_get_boolean_u8(const EFI_GUID *vendor, const CHAR16 *name, BOOLEAN *ret);
|
||||
|
||||
CHAR8 *strchra(CHAR8 *s, CHAR8 c);
|
||||
CHAR16 *stra_to_path(CHAR8 *stra);
|
||||
CHAR16 *stra_to_str(CHAR8 *stra);
|
||||
|
||||
const CHAR16 *startswith(const CHAR16 *s, const CHAR16 *prefix);
|
||||
const CHAR16 *endswith(const CHAR16 *s, const CHAR16 *postfix);
|
||||
|
||||
const CHAR16 *startswith_no_case(const CHAR16 *s, const CHAR16 *prefix);
|
||||
const CHAR16 *endswith_no_case(const CHAR16 *s, const CHAR16 *postfix);
|
||||
|
||||
EFI_STATUS file_read(EFI_FILE_HANDLE dir, const CHAR16 *name, UINTN off, UINTN size, CHAR8 **content, UINTN *content_size);
|
||||
|
||||
static inline void FreePoolp(void *p) {
|
||||
@ -55,7 +66,14 @@ static inline void FileHandleClosep(EFI_FILE_HANDLE *handle) {
|
||||
uefi_call_wrapper((*handle)->Close, 1, *handle);
|
||||
}
|
||||
|
||||
extern const EFI_GUID loader_guid;
|
||||
/*
|
||||
* Allocated random UUID, intended to be shared across tools that implement
|
||||
* the (ESP)\loader\entries\<vendor>-<revision>.conf convention and the
|
||||
* associated EFI variables.
|
||||
*/
|
||||
#define LOADER_GUID \
|
||||
&(const EFI_GUID) { 0x4a67b082, 0x0a4c, 0x41cf, { 0xb6, 0xc7, 0x44, 0x0b, 0x29, 0xbb, 0x8c, 0x4f } }
|
||||
#define EFI_GLOBAL_GUID &(const EFI_GUID) EFI_GLOBAL_VARIABLE
|
||||
|
||||
#define UINTN_MAX (~(UINTN)0)
|
||||
#define INTN_MAX ((INTN)(UINTN_MAX>>1))
|
||||
|
Loading…
Reference in New Issue
Block a user