When SEV is enabled, use a bounce buffer to perform the DMA operation.
Cc: Jordan Justen <jordan.l.jus...@intel.com> Cc: Laszlo Ersek <ler...@redhat.com> Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Brijesh Singh <brijesh.si...@amd.com> --- OvmfPkg/Library/QemuFwCfgLib/QemuFwCfgLib.c | 54 +++++++++++++++++++- 1 file changed, 52 insertions(+), 2 deletions(-) diff --git a/OvmfPkg/Library/QemuFwCfgLib/QemuFwCfgLib.c b/OvmfPkg/Library/QemuFwCfgLib/QemuFwCfgLib.c index 73a19772bee1..86d8bf880e71 100644 --- a/OvmfPkg/Library/QemuFwCfgLib/QemuFwCfgLib.c +++ b/OvmfPkg/Library/QemuFwCfgLib/QemuFwCfgLib.c @@ -72,6 +72,8 @@ InternalQemuFwCfgDmaBytes ( volatile FW_CFG_DMA_ACCESS *Access; UINT32 AccessHigh, AccessLow; UINT32 Status; + UINT32 NumPages; + VOID *DmaBuffer, *BounceBuffer; ASSERT (Control == FW_CFG_DMA_CTL_WRITE || Control == FW_CFG_DMA_CTL_READ || Control == FW_CFG_DMA_CTL_SKIP); @@ -80,11 +82,44 @@ InternalQemuFwCfgDmaBytes ( return; } - Access = &LocalAccess; + // + // When SEV is enabled then allocate DMA bounce buffer + // + if (InternalQemuFwCfgSevIsEnabled ()) { + UINT32 TotalSize; + + TotalSize = sizeof (*Access); + // + // Control operation does not need buffer + // + if (Control != FW_CFG_DMA_CTL_SKIP) { + TotalSize += Size; + } + + // + // Allocate SEV DMA bounce buffer + // + NumPages = EFI_SIZE_TO_PAGES (TotalSize); + InternalQemuFwCfgSevDmaAllocateBuffer (NumPages, &BounceBuffer); + + Access = BounceBuffer; + DmaBuffer = BounceBuffer + sizeof (*Access); + + // + // Copy data from Host buffer into DMA buffer + // + if (Buffer && Control == FW_CFG_DMA_CTL_WRITE) { + CopyMem (DmaBuffer, Buffer, Size); + } + } else { + Access = &LocalAccess; + DmaBuffer = Buffer; + BounceBuffer = NULL; + } Access->Control = SwapBytes32 (Control); Access->Length = SwapBytes32 (Size); - Access->Address = SwapBytes64 ((UINTN)Buffer); + Access->Address = SwapBytes64 ((UINTN)DmaBuffer); // // Delimit the transfer from (a) modifications to Access, (b) in case of a @@ -117,6 +152,21 @@ InternalQemuFwCfgDmaBytes ( // After a read, the caller will want to use Buffer. // MemoryFence (); + + // + // If Bounce buffer was allocated then copy the data into host buffer and + // free the bounce buffer + // + if (BounceBuffer) { + // + // Copy data from DMA buffer into host buffer + // + if (Buffer && Control == FW_CFG_DMA_CTL_READ) { + CopyMem (Buffer, DmaBuffer, Size); + } + + InternalQemuFwCfgSevDmaFreeBuffer (BounceBuffer, NumPages); + } } -- 2.7.4 _______________________________________________ edk2-devel mailing list edk2-devel@lists.01.org https://lists.01.org/mailman/listinfo/edk2-devel