XenHypercallLib has two clients at the moment: XenBusDxe and XenConsoleSerialPortLib. Currently, when XenBusDxe starts on a non-Xen X86 platform (ie. as part of OVMF not running on Xen), the X86XenHypercallLib instance built into it fails to initialize, which triggers an ASSERT() in auto-generated code.
Instead, let's call XenHypercallIsAvailable() in the driver's entry point, and exit cleanly when the driver is started on a non-Xen platform. Modify the constructor of XenConsoleSerialPortLib similarly; we shouldn't proceed if Xen is not available. In practice this check should never fail, because XenConsoleSerialPortLib is only used on ARM, and ArmXenHypercallLib is always available; but nonetheless we should be pedantic. Reported-by: Gabriel L. Somlo <gso...@gmail.com> Suggested-by: Jordan Justen <jordan.l.jus...@intel.com> Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Laszlo Ersek <ler...@redhat.com> --- OvmfPkg/Library/XenConsoleSerialPortLib/XenConsoleSerialPortLib.c | 4 ++++ OvmfPkg/Library/XenHypercallLib/X86XenHypercall.c | 8 +++++++- OvmfPkg/XenBusDxe/XenBusDxe.c | 5 +++++ 3 files changed, 16 insertions(+), 1 deletion(-) diff --git a/OvmfPkg/Library/XenConsoleSerialPortLib/XenConsoleSerialPortLib.c b/OvmfPkg/Library/XenConsoleSerialPortLib/XenConsoleSerialPortLib.c index 9802235..467cb27 100644 --- a/OvmfPkg/Library/XenConsoleSerialPortLib/XenConsoleSerialPortLib.c +++ b/OvmfPkg/Library/XenConsoleSerialPortLib/XenConsoleSerialPortLib.c @@ -40,6 +40,10 @@ SerialPortInitialize ( VOID ) { + if (! XenHypercallIsAvailable ()) { + return RETURN_NOT_FOUND; + } + if (!mXenConsoleInterface) { mXenConsoleEventChain.port = (UINT32)XenHypercallHvmGetParam (HVM_PARAM_CONSOLE_EVTCHN); mXenConsoleInterface = (struct xencons_interface *)(UINTN) diff --git a/OvmfPkg/Library/XenHypercallLib/X86XenHypercall.c b/OvmfPkg/Library/XenHypercallLib/X86XenHypercall.c index 67892bc..7cb7f46 100644 --- a/OvmfPkg/Library/XenHypercallLib/X86XenHypercall.c +++ b/OvmfPkg/Library/XenHypercallLib/X86XenHypercall.c @@ -65,7 +65,13 @@ XenHypercallLibInit ( GuidHob = GetFirstGuidHob (&gEfiXenInfoGuid); if (GuidHob == NULL) { - return RETURN_NOT_FOUND; + // + // We don't fail library construction, since that has catastrophic + // consequences for client modules (whereas those modules may easily be + // running on a non-Xen platform). Instead, XenHypercallIsAvailable() above + // will return FALSE. + // + return RETURN_SUCCESS; } XenInfo = (EFI_XEN_INFO *) GET_GUID_HOB_DATA (GuidHob); HyperPage = XenInfo->HyperPages; diff --git a/OvmfPkg/XenBusDxe/XenBusDxe.c b/OvmfPkg/XenBusDxe/XenBusDxe.c index 2c4a086..439b060 100644 --- a/OvmfPkg/XenBusDxe/XenBusDxe.c +++ b/OvmfPkg/XenBusDxe/XenBusDxe.c @@ -165,6 +165,7 @@ XenBusDxeUnload ( @param SystemTable A pointer to the EFI System Table. @retval EFI_SUCCESS The operation completed successfully. + @retval EFI_ABORTED Xen hypercalls are not available. @retval Others An unexpected error occurred. **/ EFI_STATUS @@ -176,6 +177,10 @@ XenBusDxeDriverEntryPoint ( { EFI_STATUS Status; + if (! XenHypercallIsAvailable ()) { + return EFI_ABORTED; + } + // // Install UEFI Driver Model protocol(s). // -- 1.8.3.1 ------------------------------------------------------------------------------ Dive into the World of Parallel Programming The Go Parallel Website, sponsored by Intel and developed in partnership with Slashdot Media, is your hub for all things parallel software development, from weekly thought leadership blogs to news, videos, case studies, tutorials and more. Take a look and join the conversation now. http://goparallel.sourceforge.net/ _______________________________________________ edk2-devel mailing list edk2-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/edk2-devel