X-Git-Url: https://git.proxmox.com/?p=mirror_edk2.git;a=blobdiff_plain;f=OvmfPkg%2FAmdSevDxe%2FAmdSevDxe.c;h=c697580ad5b885915c064a13536efd682ebf0d30;hp=065d7381b35bfb9866c530a458697d1717b90c6d;hb=5e2e5647b9fba569b7ba5ede0a77d06ae3c16504;hpb=c16d4e35d1d68d78178c96ad46d5e55ff3a44332 diff --git a/OvmfPkg/AmdSevDxe/AmdSevDxe.c b/OvmfPkg/AmdSevDxe/AmdSevDxe.c index 065d7381b3..c697580ad5 100644 --- a/OvmfPkg/AmdSevDxe/AmdSevDxe.c +++ b/OvmfPkg/AmdSevDxe/AmdSevDxe.c @@ -16,15 +16,13 @@ **/ -#include - #include -#include #include -#include -#include +#include #include #include +#include +#include EFI_STATUS EFIAPI @@ -73,5 +71,55 @@ AmdSevDxeEntryPoint ( FreePool (AllDescMap); } + // + // When SMM is enabled, clear the C-bit from SMM Saved State Area + // + // NOTES: The SavedStateArea address cleared here is before SMBASE + // relocation. Currently, we do not clear the SavedStateArea address after + // SMBASE is relocated due to the following reasons: + // + // 1) Guest BIOS never access the relocated SavedStateArea. + // + // 2) The C-bit works on page-aligned address, but the SavedStateArea + // address is not a page-aligned. Theoretically, we could roundup the address + // and clear the C-bit of aligned address but looking carefully we found + // that some portion of the page contains code -- which will causes a bigger + // issues for SEV guest. When SEV is enabled, all the code must be encrypted + // otherwise hardware will cause trap. + // + // We restore the C-bit for this SMM Saved State Area after SMBASE relocation + // is completed (See OvmfPkg/Library/SmmCpuFeaturesLib/SmmCpuFeaturesLib.c). + // + if (FeaturePcdGet (PcdSmmSmramRequire)) { + UINTN MapPagesBase; + UINTN MapPagesCount; + + Status = MemEncryptSevLocateInitialSmramSaveStateMapPages ( + &MapPagesBase, + &MapPagesCount + ); + ASSERT_EFI_ERROR (Status); + + // + // Although these pages were set aside (i.e., allocated) by PlatformPei, we + // could be after a warm reboot from the OS. Don't leak any stale OS data + // to the hypervisor. + // + ZeroMem ((VOID *)MapPagesBase, EFI_PAGES_TO_SIZE (MapPagesCount)); + + Status = MemEncryptSevClearPageEncMask ( + 0, // Cr3BaseAddress -- use current CR3 + MapPagesBase, // BaseAddress + MapPagesCount, // NumPages + TRUE // Flush + ); + if (EFI_ERROR (Status)) { + DEBUG ((DEBUG_ERROR, "%a: MemEncryptSevClearPageEncMask(): %r\n", + __FUNCTION__, Status)); + ASSERT (FALSE); + CpuDeadLoop (); + } + } + return EFI_SUCCESS; }