\r
**/\r
\r
+#include <IndustryStandard/VmwareSvga.h>\r
#include "Qemu.h"\r
\r
\r
/// Table of supported video modes\r
///\r
QEMU_VIDEO_CIRRUS_MODES QemuVideoCirrusModes[] = {\r
-// { 640, 480, 8, 60, Crtc_640_480_256_60, Seq_640_480_256_60, 0xe3 },\r
-// { 800, 600, 8, 60, Crtc_800_600_256_60, Seq_800_600_256_60, 0xef },\r
- { 640, 480, 32, 60, Crtc_640_480_32bpp_60, Seq_640_480_32bpp_60, 0xef },\r
- { 800, 600, 32, 60, Crtc_800_600_32bpp_60, Seq_800_600_32bpp_60, 0xef },\r
-// { 1024, 768, 8, 60, Crtc_1024_768_256_60, Seq_1024_768_256_60, 0xef }\r
- { 1024, 768, 24, 60, Crtc_1024_768_24bpp_60, Seq_1024_768_24bpp_60, 0xef }\r
-// { 1024, 768, 32, 60, Crtc_1024_768_32bpp_60, Seq_1024_768_32bpp_60, 0xef }\r
-// { 960, 720, 32, 60, Crtc_960_720_32bpp_60, Seq_1024_768_32bpp_60, 0xef }\r
+// { 640, 480, 8, Crtc_640_480_256_60, Seq_640_480_256_60, 0xe3 },\r
+// { 800, 600, 8, Crtc_800_600_256_60, Seq_800_600_256_60, 0xef },\r
+ { 640, 480, 32, Crtc_640_480_32bpp_60, Seq_640_480_32bpp_60, 0xef },\r
+ { 800, 600, 32, Crtc_800_600_32bpp_60, Seq_800_600_32bpp_60, 0xef },\r
+// { 1024, 768, 8, Crtc_1024_768_256_60, Seq_1024_768_256_60, 0xef }\r
+ { 1024, 768, 24, Crtc_1024_768_24bpp_60, Seq_1024_768_24bpp_60, 0xef }\r
+// { 1024, 768, 32, Crtc_1024_768_32bpp_60, Seq_1024_768_32bpp_60, 0xef }\r
+// { 960, 720, 32, Crtc_960_720_32bpp_60, Seq_1024_768_32bpp_60, 0xef }\r
};\r
\r
#define QEMU_VIDEO_CIRRUS_MODE_COUNT \\r
- (sizeof (QemuVideoCirrusModes) / sizeof (QemuVideoCirrusModes[0]))\r
+ (ARRAY_SIZE (QemuVideoCirrusModes))\r
\r
/**\r
Construct the valid video modes for QemuVideo.\r
};\r
\r
#define QEMU_VIDEO_BOCHS_MODE_COUNT \\r
- (sizeof (QemuVideoBochsModes) / sizeof (QemuVideoBochsModes[0]))\r
+ (ARRAY_SIZE (QemuVideoBochsModes))\r
\r
EFI_STATUS\r
QemuVideoBochsModeSetup (\r
AvailableFbSize = BochsRead (Private, VBE_DISPI_INDEX_VIDEO_MEMORY_64K);\r
AvailableFbSize *= SIZE_64KB;\r
}\r
- DEBUG ((EFI_D_VERBOSE, "%a: AvailableFbSize=0x%x\n", __FUNCTION__,\r
+ DEBUG ((EFI_D_INFO, "%a: AvailableFbSize=0x%x\n", __FUNCTION__,\r
AvailableFbSize));\r
\r
//\r
return EFI_SUCCESS;\r
}\r
\r
+EFI_STATUS\r
+QemuVideoVmwareSvgaModeSetup (\r
+ QEMU_VIDEO_PRIVATE_DATA *Private\r
+ )\r
+{\r
+ EFI_STATUS Status;\r
+ UINT32 FbSize;\r
+ UINT32 MaxWidth, MaxHeight;\r
+ UINT32 Capabilities;\r
+ UINT32 BitsPerPixel;\r
+ UINT32 Index;\r
+ QEMU_VIDEO_MODE_DATA *ModeData;\r
+ QEMU_VIDEO_BOCHS_MODES *VideoMode;\r
+ EFI_GRAPHICS_OUTPUT_MODE_INFORMATION *ModeInfo;\r
+\r
+ VmwareSvgaWrite (Private, VmwareSvgaRegEnable, 0);\r
+\r
+ Private->ModeData =\r
+ AllocatePool (sizeof (Private->ModeData[0]) * QEMU_VIDEO_BOCHS_MODE_COUNT);\r
+ if (Private->ModeData == NULL) {\r
+ Status = EFI_OUT_OF_RESOURCES;\r
+ goto ModeDataAllocError;\r
+ }\r
+\r
+ Private->VmwareSvgaModeInfo =\r
+ AllocatePool (\r
+ sizeof (Private->VmwareSvgaModeInfo[0]) * QEMU_VIDEO_BOCHS_MODE_COUNT\r
+ );\r
+ if (Private->VmwareSvgaModeInfo == NULL) {\r
+ Status = EFI_OUT_OF_RESOURCES;\r
+ goto ModeInfoAllocError;\r
+ }\r
+\r
+ FbSize = VmwareSvgaRead (Private, VmwareSvgaRegFbSize);\r
+ MaxWidth = VmwareSvgaRead (Private, VmwareSvgaRegMaxWidth);\r
+ MaxHeight = VmwareSvgaRead (Private, VmwareSvgaRegMaxHeight);\r
+ Capabilities = VmwareSvgaRead (Private, VmwareSvgaRegCapabilities);\r
+ if ((Capabilities & VMWARE_SVGA_CAP_8BIT_EMULATION) != 0) {\r
+ BitsPerPixel = VmwareSvgaRead (\r
+ Private,\r
+ VmwareSvgaRegHostBitsPerPixel\r
+ );\r
+ VmwareSvgaWrite (\r
+ Private,\r
+ VmwareSvgaRegBitsPerPixel,\r
+ BitsPerPixel\r
+ );\r
+ } else {\r
+ BitsPerPixel = VmwareSvgaRead (\r
+ Private,\r
+ VmwareSvgaRegBitsPerPixel\r
+ );\r
+ }\r
+\r
+ if (FbSize == 0 ||\r
+ MaxWidth == 0 ||\r
+ MaxHeight == 0 ||\r
+ BitsPerPixel == 0 ||\r
+ BitsPerPixel % 8 != 0) {\r
+ Status = EFI_DEVICE_ERROR;\r
+ goto Rollback;\r
+ }\r
+\r
+ ModeData = Private->ModeData;\r
+ ModeInfo = Private->VmwareSvgaModeInfo;\r
+ VideoMode = &QemuVideoBochsModes[0];\r
+ for (Index = 0; Index < QEMU_VIDEO_BOCHS_MODE_COUNT; Index++) {\r
+ UINTN RequiredFbSize;\r
+\r
+ RequiredFbSize = (UINTN) VideoMode->Width * VideoMode->Height *\r
+ (BitsPerPixel / 8);\r
+ if (RequiredFbSize <= FbSize &&\r
+ VideoMode->Width <= MaxWidth &&\r
+ VideoMode->Height <= MaxHeight) {\r
+ UINT32 BytesPerLine;\r
+ UINT32 RedMask, GreenMask, BlueMask, PixelMask;\r
+\r
+ VmwareSvgaWrite (\r
+ Private,\r
+ VmwareSvgaRegWidth,\r
+ VideoMode->Width\r
+ );\r
+ VmwareSvgaWrite (\r
+ Private,\r
+ VmwareSvgaRegHeight,\r
+ VideoMode->Height\r
+ );\r
+\r
+ ModeData->InternalModeIndex = Index;\r
+ ModeData->HorizontalResolution = VideoMode->Width;\r
+ ModeData->VerticalResolution = VideoMode->Height;\r
+ ModeData->ColorDepth = BitsPerPixel;\r
+\r
+ //\r
+ // Setting VmwareSvgaRegWidth/VmwareSvgaRegHeight actually changes\r
+ // the device's display mode, so we save all properties of each mode up\r
+ // front to avoid inadvertent mode changes later.\r
+ //\r
+ ModeInfo->Version = 0;\r
+ ModeInfo->HorizontalResolution = ModeData->HorizontalResolution;\r
+ ModeInfo->VerticalResolution = ModeData->VerticalResolution;\r
+\r
+ ModeInfo->PixelFormat = PixelBitMask;\r
+\r
+ RedMask = VmwareSvgaRead (Private, VmwareSvgaRegRedMask);\r
+ ModeInfo->PixelInformation.RedMask = RedMask;\r
+\r
+ GreenMask = VmwareSvgaRead (Private, VmwareSvgaRegGreenMask);\r
+ ModeInfo->PixelInformation.GreenMask = GreenMask;\r
+\r
+ BlueMask = VmwareSvgaRead (Private, VmwareSvgaRegBlueMask);\r
+ ModeInfo->PixelInformation.BlueMask = BlueMask;\r
+\r
+ //\r
+ // Reserved mask is whatever bits in the pixel not containing RGB data,\r
+ // so start with binary 1s for every bit in the pixel, then mask off\r
+ // bits already used for RGB. Special case 32 to avoid undefined\r
+ // behaviour in the shift.\r
+ //\r
+ if (BitsPerPixel == 32) {\r
+ if (BlueMask == 0xff && GreenMask == 0xff00 && RedMask == 0xff0000) {\r
+ ModeInfo->PixelFormat = PixelBlueGreenRedReserved8BitPerColor;\r
+ } else if (BlueMask == 0xff0000 &&\r
+ GreenMask == 0xff00 &&\r
+ RedMask == 0xff) {\r
+ ModeInfo->PixelFormat = PixelRedGreenBlueReserved8BitPerColor;\r
+ }\r
+ PixelMask = MAX_UINT32;\r
+ } else {\r
+ PixelMask = (1u << BitsPerPixel) - 1;\r
+ }\r
+ ModeInfo->PixelInformation.ReservedMask =\r
+ PixelMask & ~(RedMask | GreenMask | BlueMask);\r
+\r
+ BytesPerLine = VmwareSvgaRead (Private, VmwareSvgaRegBytesPerLine);\r
+ ModeInfo->PixelsPerScanLine = BytesPerLine / (BitsPerPixel / 8);\r
+\r
+ ModeData++;\r
+ ModeInfo++;\r
+ }\r
+ VideoMode++;\r
+ }\r
+ Private->MaxMode = ModeData - Private->ModeData;\r
+ return EFI_SUCCESS;\r
+\r
+Rollback:\r
+ FreePool (Private->VmwareSvgaModeInfo);\r
+ Private->VmwareSvgaModeInfo = NULL;\r
+\r
+ModeInfoAllocError:\r
+ FreePool (Private->ModeData);\r
+ Private->ModeData = NULL;\r
+\r
+ModeDataAllocError:\r
+ return Status;\r
+}\r