1*c5a8f13fSThomas Zimmermann // SPDX-License-Identifier: GPL-2.0 2*c5a8f13fSThomas Zimmermann 3*c5a8f13fSThomas Zimmermann #include <linux/efi.h> 4*c5a8f13fSThomas Zimmermann #include <linux/sysfb.h> 5*c5a8f13fSThomas Zimmermann 6*c5a8f13fSThomas Zimmermann #include <asm/efi.h> 7*c5a8f13fSThomas Zimmermann 8*c5a8f13fSThomas Zimmermann #include "efistub.h" 9*c5a8f13fSThomas Zimmermann 10*c5a8f13fSThomas Zimmermann /* 11*c5a8f13fSThomas Zimmermann * There are two ways of populating the core kernel's sysfb_primary_display 12*c5a8f13fSThomas Zimmermann * via the stub: 13*c5a8f13fSThomas Zimmermann * 14*c5a8f13fSThomas Zimmermann * - using a configuration table, which relies on the EFI init code to 15*c5a8f13fSThomas Zimmermann * locate the table and copy the contents; or 16*c5a8f13fSThomas Zimmermann * 17*c5a8f13fSThomas Zimmermann * - by linking directly to the core kernel's copy of the global symbol. 18*c5a8f13fSThomas Zimmermann * 19*c5a8f13fSThomas Zimmermann * The latter is preferred because it makes the EFIFB earlycon available very 20*c5a8f13fSThomas Zimmermann * early, but it only works if the EFI stub is part of the core kernel image 21*c5a8f13fSThomas Zimmermann * itself. The zboot decompressor can only use the configuration table 22*c5a8f13fSThomas Zimmermann * approach. 23*c5a8f13fSThomas Zimmermann */ 24*c5a8f13fSThomas Zimmermann 25*c5a8f13fSThomas Zimmermann static efi_guid_t primary_display_guid = LINUX_EFI_PRIMARY_DISPLAY_TABLE_GUID; 26*c5a8f13fSThomas Zimmermann 27*c5a8f13fSThomas Zimmermann struct sysfb_display_info *__alloc_primary_display(void) 28*c5a8f13fSThomas Zimmermann { 29*c5a8f13fSThomas Zimmermann struct sysfb_display_info *dpy; 30*c5a8f13fSThomas Zimmermann efi_status_t status; 31*c5a8f13fSThomas Zimmermann 32*c5a8f13fSThomas Zimmermann status = efi_bs_call(allocate_pool, EFI_ACPI_RECLAIM_MEMORY, 33*c5a8f13fSThomas Zimmermann sizeof(*dpy), (void **)&dpy); 34*c5a8f13fSThomas Zimmermann 35*c5a8f13fSThomas Zimmermann if (status != EFI_SUCCESS) 36*c5a8f13fSThomas Zimmermann return NULL; 37*c5a8f13fSThomas Zimmermann 38*c5a8f13fSThomas Zimmermann memset(dpy, 0, sizeof(*dpy)); 39*c5a8f13fSThomas Zimmermann 40*c5a8f13fSThomas Zimmermann status = efi_bs_call(install_configuration_table, 41*c5a8f13fSThomas Zimmermann &primary_display_guid, dpy); 42*c5a8f13fSThomas Zimmermann if (status == EFI_SUCCESS) 43*c5a8f13fSThomas Zimmermann return dpy; 44*c5a8f13fSThomas Zimmermann 45*c5a8f13fSThomas Zimmermann efi_bs_call(free_pool, dpy); 46*c5a8f13fSThomas Zimmermann return NULL; 47*c5a8f13fSThomas Zimmermann } 48*c5a8f13fSThomas Zimmermann 49*c5a8f13fSThomas Zimmermann void free_primary_display(struct sysfb_display_info *dpy) 50*c5a8f13fSThomas Zimmermann { 51*c5a8f13fSThomas Zimmermann if (!dpy) 52*c5a8f13fSThomas Zimmermann return; 53*c5a8f13fSThomas Zimmermann 54*c5a8f13fSThomas Zimmermann efi_bs_call(install_configuration_table, &primary_display_guid, NULL); 55*c5a8f13fSThomas Zimmermann efi_bs_call(free_pool, dpy); 56*c5a8f13fSThomas Zimmermann } 57