1*732ea9dbSArd Biesheuvel // SPDX-License-Identifier: GPL-2.0 2*732ea9dbSArd Biesheuvel 3*732ea9dbSArd Biesheuvel #include <linux/efi.h> 4*732ea9dbSArd Biesheuvel #include <asm/efi.h> 5*732ea9dbSArd Biesheuvel 6*732ea9dbSArd Biesheuvel #include "efistub.h" 7*732ea9dbSArd Biesheuvel 8*732ea9dbSArd Biesheuvel /* 9*732ea9dbSArd Biesheuvel * There are two ways of populating the core kernel's struct screen_info via the stub: 10*732ea9dbSArd Biesheuvel * - using a configuration table, like below, which relies on the EFI init code 11*732ea9dbSArd Biesheuvel * to locate the table and copy the contents; 12*732ea9dbSArd Biesheuvel * - by linking directly to the core kernel's copy of the global symbol. 13*732ea9dbSArd Biesheuvel * 14*732ea9dbSArd Biesheuvel * The latter is preferred because it makes the EFIFB earlycon available very 15*732ea9dbSArd Biesheuvel * early, but it only works if the EFI stub is part of the core kernel image 16*732ea9dbSArd Biesheuvel * itself. The zboot decompressor can only use the configuration table 17*732ea9dbSArd Biesheuvel * approach. 18*732ea9dbSArd Biesheuvel * 19*732ea9dbSArd Biesheuvel * In order to support both methods from the same build of the EFI stub 20*732ea9dbSArd Biesheuvel * library, provide this dummy global definition of struct screen_info. If it 21*732ea9dbSArd Biesheuvel * is required to satisfy a link dependency, it means we need to override the 22*732ea9dbSArd Biesheuvel * __weak alloc and free methods with the ones below, and those will be pulled 23*732ea9dbSArd Biesheuvel * in as well. 24*732ea9dbSArd Biesheuvel */ 25*732ea9dbSArd Biesheuvel struct screen_info screen_info; 26*732ea9dbSArd Biesheuvel 27*732ea9dbSArd Biesheuvel static efi_guid_t screen_info_guid = LINUX_EFI_SCREEN_INFO_TABLE_GUID; 28*732ea9dbSArd Biesheuvel 29*732ea9dbSArd Biesheuvel struct screen_info *alloc_screen_info(void) 30*732ea9dbSArd Biesheuvel { 31*732ea9dbSArd Biesheuvel struct screen_info *si; 32*732ea9dbSArd Biesheuvel efi_status_t status; 33*732ea9dbSArd Biesheuvel 34*732ea9dbSArd Biesheuvel status = efi_bs_call(allocate_pool, EFI_ACPI_RECLAIM_MEMORY, 35*732ea9dbSArd Biesheuvel sizeof(*si), (void **)&si); 36*732ea9dbSArd Biesheuvel 37*732ea9dbSArd Biesheuvel if (status != EFI_SUCCESS) 38*732ea9dbSArd Biesheuvel return NULL; 39*732ea9dbSArd Biesheuvel 40*732ea9dbSArd Biesheuvel status = efi_bs_call(install_configuration_table, 41*732ea9dbSArd Biesheuvel &screen_info_guid, si); 42*732ea9dbSArd Biesheuvel if (status == EFI_SUCCESS) 43*732ea9dbSArd Biesheuvel return si; 44*732ea9dbSArd Biesheuvel 45*732ea9dbSArd Biesheuvel efi_bs_call(free_pool, si); 46*732ea9dbSArd Biesheuvel return NULL; 47*732ea9dbSArd Biesheuvel } 48*732ea9dbSArd Biesheuvel 49*732ea9dbSArd Biesheuvel void free_screen_info(struct screen_info *si) 50*732ea9dbSArd Biesheuvel { 51*732ea9dbSArd Biesheuvel if (!si) 52*732ea9dbSArd Biesheuvel return; 53*732ea9dbSArd Biesheuvel 54*732ea9dbSArd Biesheuvel efi_bs_call(install_configuration_table, &screen_info_guid, NULL); 55*732ea9dbSArd Biesheuvel efi_bs_call(free_pool, si); 56*732ea9dbSArd Biesheuvel } 57