*/
#include <freeldr.h>
+#include <debug.h>
-static PVOID FrameBuffer;
+DBG_DEFAULT_CHANNEL(UI);
+
+PVOID FrameBuffer;
+ULONG FrameBufferSize;
static ULONG ScreenWidth;
static ULONG ScreenHeight;
static ULONG BytesPerPixel;
static ULONG Delta;
+extern multiboot_info_t * MultibootInfoPtr;
#define CHAR_WIDTH 8
#define CHAR_HEIGHT 16
#define MAKE_COLOR(Red, Green, Blue) (0xff000000 | (((Red) & 0xff) << 16) | (((Green) & 0xff) << 8) | ((Blue) & 0xff))
-BOOLEAN I2CTransmitByteGetReturn(UCHAR bPicAddressI2cFormat, UCHAR bDataToWrite, ULONG *Return);
-
static VOID
XboxVideoOutputChar(UCHAR Char, unsigned X, unsigned Y, ULONG FgColor, ULONG BgColor)
{
XboxVideoOutputChar(Ch, X, Y, FgColor, BgColor);
}
-VOID
-XboxVideoInit(VOID)
+UCHAR
+NvGetCrtc(UCHAR Index)
{
- ULONG AvMode;
+ *((PUCHAR) NV2A_CRTC_REGISTER_INDEX) = Index;
+ return *((PUCHAR) NV2A_CRTC_REGISTER_VALUE);
+}
- FrameBuffer = (PVOID)((ULONG) XboxMemReserveMemory(FB_SIZE_MB) | 0xf0000000);
+ULONG
+XboxGetFramebufferSize(PVOID Offset)
+{
+ memory_map_t * MemoryMap;
+ INT Count, i;
- if (I2CTransmitByteGetReturn(0x10, 0x04, &AvMode))
+ if (!MultibootInfoPtr)
{
- if (1 == AvMode) /* HDTV */
- {
- ScreenWidth = 720;
- }
- else
- {
- /* FIXME Other possible values of AvMode:
- * 0 - AV_SCART_RGB
- * 2 - AV_VGA_SOG
- * 4 - AV_SVIDEO
- * 6 - AV_COMPOSITE
- * 7 - AV_VGA
- * other AV_COMPOSITE
- */
- ScreenWidth = 640;
- }
+ return 0;
}
- else
+
+ if (!(MultibootInfoPtr->flags & MB_INFO_FLAG_MEMORY_MAP))
{
- ScreenWidth = 640;
+ return 0;
}
- ScreenHeight = 480;
- BytesPerPixel = 4;
+ MemoryMap = (memory_map_t *)MultibootInfoPtr->mmap_addr;
+
+ if (!MemoryMap ||
+ MultibootInfoPtr->mmap_length == 0 ||
+ MultibootInfoPtr->mmap_length % sizeof(memory_map_t) != 0)
+ {
+ return 0;
+ }
+
+ Count = MultibootInfoPtr->mmap_length / sizeof(memory_map_t);
+ for (i = 0; i < Count; i++, MemoryMap++)
+ {
+ TRACE("i = %d, base_addr_low = 0x%p, MemoryMap->length_low = 0x%p\n", i, MemoryMap->base_addr_low, MemoryMap->length_low);
+
+ /* Framebuffer address offset value is coming from the GPU within
+ * memory mapped I/O address space, so we're comparing only low
+ * 28 bits of the address within actual RAM address space */
+ if (MemoryMap->base_addr_low == ((ULONG)Offset & 0x0FFFFFFF) && MemoryMap->base_addr_high == 0)
+ {
+ TRACE("Video memory found\n");
+ return MemoryMap->length_low;
+ }
+ }
+ ERR("Video memory not found!\n");
+ return 0;
+}
+
+VOID
+XboxVideoInit(VOID)
+{
+ /* Reuse framebuffer that was set up by firmware */
+ FrameBuffer = (PVOID)*((PULONG) NV2A_CRTC_FRAMEBUFFER_START);
+ /* Verify that framebuffer address is page-aligned */
+ ASSERT((ULONG_PTR)FrameBuffer % PAGE_SIZE == 0);
+
+ /* Obtain framebuffer memory size from multiboot memory map */
+ if ((FrameBufferSize = XboxGetFramebufferSize(FrameBuffer)) == 0)
+ {
+ /* Fallback to Cromwell standard which reserves high 4 MB of RAM */
+ FrameBufferSize = 4 * 1024 * 1024;
+ WARN("Could not detect framebuffer memory size, fallback to 4 MB\n");
+ }
+
+ ScreenWidth = *((PULONG) NV2A_RAMDAC_FP_HVALID_END) + 1;
+ ScreenHeight = *((PULONG) NV2A_RAMDAC_FP_VVALID_END) + 1;
+ /* Get BPP directly from NV2A CRTC (magic constants are from Cromwell) */
+ BytesPerPixel = 8 * (((NvGetCrtc(0x19) & 0xE0) << 3) | (NvGetCrtc(0x13) & 0xFF)) / ScreenWidth;
+ if (BytesPerPixel == 4)
+ {
+ ASSERT((NvGetCrtc(0x28) & 0xF) == BytesPerPixel - 1);
+ }
+ else
+ {
+ ASSERT((NvGetCrtc(0x28) & 0xF) == BytesPerPixel);
+ }
Delta = (ScreenWidth * BytesPerPixel + 3) & ~ 0x3;
- XboxVideoClearScreenColor(MAKE_COLOR(0, 0, 0), TRUE);
+ /* Verify screen resolution */
+ ASSERT(ScreenWidth > 1);
+ ASSERT(ScreenHeight > 1);
+ ASSERT(BytesPerPixel >= 1 && BytesPerPixel <= 4);
+ /* Verify that screen fits framebuffer size */
+ ASSERT(ScreenWidth * ScreenHeight * BytesPerPixel <= FrameBufferSize);
- /* Tell the nVidia controller about the framebuffer */
- *((PULONG) 0xfd600800) = (ULONG) FrameBuffer;
+ XboxVideoClearScreenColor(MAKE_COLOR(0, 0, 0), TRUE);
}
VIDEODISPLAYMODE
return (ScreenHeight - 2 * TOP_BOTTOM_LINES) / CHAR_HEIGHT * (ScreenWidth / CHAR_WIDTH) * 2;
}
+VOID
+XboxVideoGetFontsFromFirmware(PULONG RomFontPointers)
+{
+ TRACE("XboxVideoGetFontsFromFirmware(): UNIMPLEMENTED\n");
+}
+
VOID
XboxVideoSetTextCursorPosition(UCHAR X, UCHAR Y)
{
}
VOID
-XboxVideoSync()
+XboxVideoSync(VOID)
{
/* Not supported */
}
VOID
-XboxBeep()
+XboxBeep(VOID)
{
/* Call PC version */
PcBeep();
}
VOID
-XboxVideoPrepareForReactOS(IN BOOLEAN Setup)
+XboxVideoPrepareForReactOS(VOID)
{
- XboxVideoClearScreenColor(MAKE_COLOR(0, 0, 0), TRUE);
+ XboxVideoClearScreenColor(MAKE_COLOR(0, 0, 0), TRUE);
+ XboxVideoHideShowTextCursor(FALSE);
}
/* EOF */