1
0
Fork 0
mirror of synced 2025-03-06 20:59:54 +01:00
linux/drivers/firmware/efi/libstub/efi-stub-entry.c
Arnd Bergmann b8466fe82b efi: move screen_info into efi init code
After the vga console no longer relies on global screen_info, there are
only two remaining use cases:

 - on the x86 architecture, it is used for multiple boot methods
   (bzImage, EFI, Xen, kexec) to commucate the initial VGA or framebuffer
   settings to a number of device drivers.

 - on other architectures, it is only used as part of the EFI stub,
   and only for the three sysfb framebuffers (simpledrm, simplefb, efifb).

Remove the duplicate data structure definitions by moving it into the
efi-init.c file that sets it up initially for the EFI case, leaving x86
as an exception that retains its own definition for non-EFI boots.

The added #ifdefs here are optional, I added them to further limit the
reach of screen_info to configurations that have at least one of the
users enabled.

Reviewed-by: Ard Biesheuvel <ardb@kernel.org>
Reviewed-by: Javier Martinez Canillas <javierm@redhat.com>
Acked-by: Helge Deller <deller@gmx.de>
Signed-off-by: Arnd Bergmann <arnd@arndb.de>
Link: https://lore.kernel.org/r/20231017093947.3627976-1-arnd@kernel.org
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
2023-10-17 16:33:39 +02:00

84 lines
2.1 KiB
C

// SPDX-License-Identifier: GPL-2.0-only
#include <linux/efi.h>
#include <linux/screen_info.h>
#include <asm/efi.h>
#include "efistub.h"
static unsigned long screen_info_offset;
struct screen_info *alloc_screen_info(void)
{
if (IS_ENABLED(CONFIG_ARM))
return __alloc_screen_info();
if (IS_ENABLED(CONFIG_X86) ||
IS_ENABLED(CONFIG_EFI_EARLYCON) ||
IS_ENABLED(CONFIG_SYSFB))
return (void *)&screen_info + screen_info_offset;
return NULL;
}
/*
* EFI entry point for the generic EFI stub used by ARM, arm64, RISC-V and
* LoongArch. This is the entrypoint that is described in the PE/COFF header
* of the core kernel.
*/
efi_status_t __efiapi efi_pe_entry(efi_handle_t handle,
efi_system_table_t *systab)
{
efi_loaded_image_t *image;
efi_status_t status;
unsigned long image_addr;
unsigned long image_size = 0;
/* addr/point and size pairs for memory management*/
char *cmdline_ptr = NULL;
efi_guid_t loaded_image_proto = LOADED_IMAGE_PROTOCOL_GUID;
unsigned long reserve_addr = 0;
unsigned long reserve_size = 0;
WRITE_ONCE(efi_system_table, systab);
/* Check if we were booted by the EFI firmware */
if (efi_system_table->hdr.signature != EFI_SYSTEM_TABLE_SIGNATURE)
return EFI_INVALID_PARAMETER;
/*
* Get a handle to the loaded image protocol. This is used to get
* information about the running image, such as size and the command
* line.
*/
status = efi_bs_call(handle_protocol, handle, &loaded_image_proto,
(void *)&image);
if (status != EFI_SUCCESS) {
efi_err("Failed to get loaded image protocol\n");
return status;
}
status = efi_handle_cmdline(image, &cmdline_ptr);
if (status != EFI_SUCCESS)
return status;
efi_info("Booting Linux Kernel...\n");
status = handle_kernel_image(&image_addr, &image_size,
&reserve_addr,
&reserve_size,
image, handle);
if (status != EFI_SUCCESS) {
efi_err("Failed to relocate kernel\n");
return status;
}
screen_info_offset = image_addr - (unsigned long)image->image_base;
status = efi_stub_common(handle, image, image_addr, cmdline_ptr);
efi_free(image_size, image_addr);
efi_free(reserve_size, reserve_addr);
return status;
}