From 028ad656f1133bcc48348d6a7460459efe9ca57b Mon Sep 17 00:00:00 2001 From: Aaron Robinson Date: Tue, 24 Jun 2003 00:06:09 +0000 Subject: [PATCH] *** empty log message *** --- Include/Win32/CxbxKrnl/xd3d8.h | 55 ++++++- Source/Win32/Cxbx/WndMain.cpp | 2 +- Source/Win32/CxbxKrnl/D3D8.1.0.4627.inl | 85 ++++++++++ Source/Win32/CxbxKrnl/Emu.cpp | 2 +- Source/Win32/CxbxKrnl/EmuD3D8.cpp | 202 +++++++++++++++++++++--- 5 files changed, 320 insertions(+), 26 deletions(-) diff --git a/Include/Win32/CxbxKrnl/xd3d8.h b/Include/Win32/CxbxKrnl/xd3d8.h index 3d9c6ec45..425e8ce8e 100644 --- a/Include/Win32/CxbxKrnl/xd3d8.h +++ b/Include/Win32/CxbxKrnl/xd3d8.h @@ -129,6 +129,7 @@ inline D3DFORMAT EmuXB2PC_D3DFormat(X_D3DFORMAT Format) case 0x04: // Swizzled (X_D3DFMT_A4R4G4B4) return D3DFMT_A4R4G4B4; + case 0x11: // Linear (X_D3DFMT_LIN_R5G6B5) case 0x05: // Swizzled (X_D3DFMT_R5G6B5) return D3DFMT_R5G6B5; @@ -145,6 +146,7 @@ inline D3DFORMAT EmuXB2PC_D3DFormat(X_D3DFORMAT Format) case 0x2A: // Swizzled (X_D3DFMT_D24S8) return D3DFMT_D24S8; + case 0x30: // Linear (D3DFMT_LIN_D16) case 0x2C: // Swizzled (X_D3DFMT_D16) return D3DFMT_D16; } @@ -159,12 +161,17 @@ inline D3DFORMAT EmuXB2PC_D3DFormat(X_D3DFORMAT Format) // ****************************************************************** inline X_D3DFORMAT EmuPC2XB_D3DFormat(D3DFORMAT Format) { - if(Format == D3DFMT_X8R8G8B8) - return (D3DFORMAT)0x07; - else if(Format == D3DFMT_A8R8G8B8) - return (D3DFORMAT)0x06; + switch(Format) + { + case D3DFMT_D24S8: + return 0x2A; + case D3DFMT_X8R8G8B8: + return 0x07; + case D3DFMT_A8R8G8B8: + return 0x06; + } - EmuCleanup("EmuPC2XB_D3DFormat: Unknown Format"); + EmuCleanup("EmuPC2XB_D3DFormat: Unknown Format (%d)", Format); return Format; } @@ -226,6 +233,22 @@ typedef struct _X_D3DPRESENT_PARAMETERS } X_D3DPRESENT_PARAMETERS; +// ****************************************************************** +// * X_D3DVertexShader +// ****************************************************************** +struct X_D3DVertexShader +{ + union + { + DWORD UnknownA; + DWORD Handle; + }; + + DWORD UnknownB; + DWORD Flags; + DWORD UnknownC[0x59]; +}; + // ****************************************************************** // * D3DResource "Common" Masks // ****************************************************************** @@ -679,6 +702,16 @@ BOOL WINAPI EmuIDirect3DResource8_IsBusy X_D3DResource *pThis ); +// ****************************************************************** +// * func: EmuGet2DSurfaceDesc +// ****************************************************************** +VOID WINAPI EmuGet2DSurfaceDesc +( + X_D3DPixelContainer *pPixelContainer, + DWORD dwLevel, + X_D3DSURFACE_DESC *pDesc +); + // ****************************************************************** // * func: EmuIDirect3DSurface8_GetDesc // ****************************************************************** @@ -716,6 +749,18 @@ X_D3DResource * WINAPI EmuIDirect3DTexture8_GetSurfaceLevel2 UINT Level ); +// ****************************************************************** +// * func: EmuIDirect3DTexture8_LockRect +// ****************************************************************** +HRESULT WINAPI EmuIDirect3DTexture8_LockRect +( + X_D3DTexture *pThis, + UINT Level, + D3DLOCKED_RECT *pLockedRect, + CONST RECT *pRect, + DWORD Flags +); + // ****************************************************************** // * func: EmuIDirect3DTexture8_GetSurfaceLevel // ****************************************************************** diff --git a/Source/Win32/Cxbx/WndMain.cpp b/Source/Win32/Cxbx/WndMain.cpp index 284bbeb40..6af73af59 100644 --- a/Source/Win32/Cxbx/WndMain.cpp +++ b/Source/Win32/Cxbx/WndMain.cpp @@ -51,7 +51,7 @@ WndMain::WndMain(HINSTANCE x_hInstance) : Wnd(x_hInstance), m_bCreated(false), m // ****************************************************************** { m_classname = "WndMain"; - m_wndname = "Cxbx : Xbox Emulator"; + m_wndname = "Cxbx - Xbox Emulator"; m_w = 327; m_h = 253; diff --git a/Source/Win32/CxbxKrnl/D3D8.1.0.4627.inl b/Source/Win32/CxbxKrnl/D3D8.1.0.4627.inl index 892fa29bc..f141c40fc 100644 --- a/Source/Win32/CxbxKrnl/D3D8.1.0.4627.inl +++ b/Source/Win32/CxbxKrnl/D3D8.1.0.4627.inl @@ -733,6 +733,33 @@ SOOVPA<11> IDirect3DResource8_Release_1_0_4627 = } }; +// ****************************************************************** +// * Get2DSurfaceDesc +// ****************************************************************** +SOOVPA<10> Get2DSurfaceDesc_1_0_4627 = +{ + 0, // Large == 0 + 10, // Count == 10 + + { + // Get2DSurfaceDesc+0x2B : movzx edx, byte ptr [edi+0x0D] + { 0x2B, 0x0F }, // (Offset,Value)-Pair #1 + { 0x2C, 0xB6 }, // (Offset,Value)-Pair #2 + { 0x2D, 0x57 }, // (Offset,Value)-Pair #3 + { 0x2E, 0x0D }, // (Offset,Value)-Pair #4 + + // Get2DSurfaceDesc+0x52 : mov edx, [eax+0x21C0] + { 0x52, 0x8B }, // (Offset,Value)-Pair #5 + { 0x53, 0x90 }, // (Offset,Value)-Pair #6 + { 0x54, 0xC0 }, // (Offset,Value)-Pair #7 + { 0x55, 0x21 }, // (Offset,Value)-Pair #8 + + // Get2DSurfaceDesc+0xAE : retn 0x0C + { 0xAE, 0xC2 }, // (Offset,Value)-Pair #9 + { 0xAF, 0x0C }, // (Offset,Value)-Pair #10 + } +}; + // ****************************************************************** // * IDirect3DTexture8_GetSurfaceLevel2 // ****************************************************************** @@ -772,6 +799,44 @@ SOOVPA<14> IDirect3DTexture8_GetSurfaceLevel2_1_0_4627 = } }; +// ****************************************************************** +// * IDirect3DTexture8_LockRect +// ****************************************************************** +SOOVPA<17> IDirect3DTexture8_LockRect_1_0_4627 = +{ + 0, // Large == 0 + 17, // Count == 17 + + { + // IDirect3DTexture8_LockRect+0x00 : mov eax, [esp+0x14] + { 0x00, 0x8B }, // (Offset,Value)-Pair #1 + { 0x01, 0x44 }, // (Offset,Value)-Pair #2 + { 0x02, 0x24 }, // (Offset,Value)-Pair #3 + { 0x03, 0x14 }, // (Offset,Value)-Pair #4 + + // IDirect3DTexture8_LockRect+0x04 : mov ecx, [esp+0x10] + { 0x04, 0x8B }, // (Offset,Value)-Pair #5 + { 0x05, 0x4C }, // (Offset,Value)-Pair #6 + { 0x06, 0x24 }, // (Offset,Value)-Pair #7 + { 0x07, 0x10 }, // (Offset,Value)-Pair #8 + + // IDirect3DTexture8_LockRect+0x0C : push eax, push ecx, push edx, push eax, push 0 + { 0x0C, 0x50 }, // (Offset,Value)-Pair #9 + { 0x11, 0x51 }, // (Offset,Value)-Pair #10 + { 0x16, 0x52 }, // (Offset,Value)-Pair #11 + { 0x17, 0x50 }, // (Offset,Value)-Pair #12 + { 0x18, 0x6A }, // (Offset,Value)-Pair #13 + { 0x19, 0x00 }, // (Offset,Value)-Pair #14 + + // IDirect3DTexture8_LockRect+0x1B : call [addr] + { 0x1B, 0xE8 }, // (Offset,Value)-Pair #15 + + // IDirect3DTexture8_LockRect+0x1B : retn 0x14 + { 0x20, 0xC2 }, // (Offset,Value)-Pair #16 + { 0x21, 0x14 }, // (Offset,Value)-Pair #17 + } +}; + // ****************************************************************** // * D3D8_1_0_4627 // ****************************************************************** @@ -1157,6 +1222,16 @@ OOVPATable D3D8_1_0_4627[] = "EmuIDirect3DResource8_Release" #endif }, + // Get2DSurfacDesc + { + (OOVPA*)&Get2DSurfaceDesc_1_0_4627, + + xd3d8::EmuGet2DSurfaceDesc, + + #ifdef _DEBUG_TRACE + "EmuGet2DSurfaceDesc" + #endif + }, // IDirect3DSurface8::GetDesc (* unchanged since 4361 *) { (OOVPA*)&IDirect3DSurface8_GetDesc_1_0_4361, @@ -1197,6 +1272,16 @@ OOVPATable D3D8_1_0_4627[] = "EmuIDirect3DTexture8_GetSurfaceLevel2" #endif }, + // IDirect3DTexture8::LockRect + { + (OOVPA*)&IDirect3DTexture8_LockRect_1_0_4627, + + xd3d8::EmuIDirect3DTexture8_LockRect, + + #ifdef _DEBUG_TRACE + "EmuIDirect3DTexture8_LockRect" + #endif + }, }; // ****************************************************************** diff --git a/Source/Win32/CxbxKrnl/Emu.cpp b/Source/Win32/CxbxKrnl/Emu.cpp index 354c92fcb..0b1fde390 100644 --- a/Source/Win32/CxbxKrnl/Emu.cpp +++ b/Source/Win32/CxbxKrnl/Emu.cpp @@ -393,7 +393,7 @@ extern "C" CXBXKRNL_API void NTAPI EmuInit EmuSwapFS(); // XBox FS // _USE_XGMATH Disabled in mesh :[ - _asm int 3 + //_asm int 3 Entry(); diff --git a/Source/Win32/CxbxKrnl/EmuD3D8.cpp b/Source/Win32/CxbxKrnl/EmuD3D8.cpp index bb6e472d3..ff4cca8d3 100644 --- a/Source/Win32/CxbxKrnl/EmuD3D8.cpp +++ b/Source/Win32/CxbxKrnl/EmuD3D8.cpp @@ -976,6 +976,14 @@ HRESULT WINAPI xd3d8::EmuIDirect3DDevice8_CreateVertexShader } #endif + // ****************************************************************** + // * create emulated shader struct + // ****************************************************************** + X_D3DVertexShader *pD3DVertexShader = new X_D3DVertexShader(); + + // Todo: Intelligently fill out these fields as necessary + ZeroMemory(pD3DVertexShader, sizeof(X_D3DVertexShader)); + // ****************************************************************** // * redirect to windows d3d // ****************************************************************** @@ -983,10 +991,12 @@ HRESULT WINAPI xd3d8::EmuIDirect3DDevice8_CreateVertexShader ( pDeclaration, pFunction, - pHandle, - g_dwVertexShaderUsage // TODO: HACK: Xbox has extensions! + &pD3DVertexShader->Handle, + g_dwVertexShaderUsage // TODO: HACK: Xbox has extensions! ); + *pHandle = (DWORD)pD3DVertexShader; + if(FAILED(hRet)) { printf("*Warning* we're lying about the creation of a vertex shader!\n"); @@ -1199,6 +1209,13 @@ HRESULT WINAPI xd3d8::EmuIDirect3DDevice8_CreateTexture // Convert Format (Xbox->PC) D3DFORMAT PCFormat = EmuXB2PC_D3DFormat(Format); + // TODO: HACK: Devices that don't support this should somehow emulate it! + if(PCFormat == D3DFMT_D16) + { + printf("*Warning* D3DFMT_16 is an unsupported texture format!"); + PCFormat = D3DFMT_X8R8G8B8; + } + *ppTexture = new X_D3DResource(); // ****************************************************************** @@ -1207,10 +1224,13 @@ HRESULT WINAPI xd3d8::EmuIDirect3DDevice8_CreateTexture HRESULT hRet = g_pD3DDevice8->CreateTexture ( Width, Height, Levels, - 0, // TODO: Xbox Allows a border to be drawn (maybe hack this in software ;[) + Usage, // TODO: Xbox Allows a border to be drawn (maybe hack this in software ;[) PCFormat, D3DPOOL_MANAGED, &((*ppTexture)->EmuTexture8) ); + if(FAILED(hRet)) + EmuCleanup("CreateTexture FAILED!"); + EmuSwapFS(); // XBox FS return hRet; @@ -1556,10 +1576,12 @@ HRESULT WINAPI xd3d8::EmuIDirect3DResource8_Register X_D3DResource *pResource = (X_D3DResource*)pThis; + DWORD dwCommonType = pResource->Common & X_D3DCOMMON_TYPE_MASK; + // ****************************************************************** // * Determine the resource type, and initialize // ****************************************************************** - switch(pResource->Common & X_D3DCOMMON_TYPE_MASK) + switch(dwCommonType) { case X_D3DCOMMON_TYPE_VERTEXBUFFER: { @@ -1633,6 +1655,8 @@ HRESULT WINAPI xd3d8::EmuIDirect3DResource8_Register } break; + case X_D3DCOMMON_TYPE_SURFACE: + EmuCleanup("X_D3DCOMMON_TYPE_SURFACE temporarily unsupported"); case X_D3DCOMMON_TYPE_TEXTURE: { #ifdef _DEBUG_TRACE @@ -1687,15 +1711,27 @@ HRESULT WINAPI xd3d8::EmuIDirect3DResource8_Register // ****************************************************************** // * Create the happy little texture // ****************************************************************** - hRet = g_pD3DDevice8->CreateTexture - ( - dwWidth, dwHeight, dwMipMap, 0, Format, - D3DPOOL_MANAGED, &pResource->EmuTexture8 - ); + if(dwCommonType == X_D3DCOMMON_TYPE_SURFACE) + { + EmuCleanup("X_D3DCOMMON_TYPE_SURFACE temporarily unsupported"); + } + else + { + hRet = g_pD3DDevice8->CreateTexture + ( + dwWidth, dwHeight, dwMipMap, 0, Format, + D3DPOOL_MANAGED, &pResource->EmuTexture8 + ); + } // ****************************************************************** // * Copy over data (deswizzle if necessary) // ****************************************************************** + if(dwCommonType == X_D3DCOMMON_TYPE_SURFACE) + { + EmuCleanup("X_D3DCOMMON_TYPE_SURFACE temporarily unsupported"); + } + else { D3DLOCKED_RECT LockedRect; @@ -1734,14 +1770,8 @@ HRESULT WINAPI xd3d8::EmuIDirect3DResource8_Register } break; - case X_D3DCOMMON_TYPE_SURFACE: - { - EmuCleanup("IDirect3DResource8::Register -> X_D3DCOMMON_TYPE_SURFACE not yet supported"); - } - break; - default: - EmuCleanup("IDirect3DResource8::Register -> Common Type 0x%.08X not yet supported", pResource->Common & X_D3DCOMMON_TYPE_MASK); + EmuCleanup("IDirect3DResource8::Register -> Common Type 0x%.08X not yet supported", dwCommonType); } EmuSwapFS(); // XBox FS @@ -1821,6 +1851,73 @@ BOOL WINAPI xd3d8::EmuIDirect3DResource8_IsBusy return FALSE; } +// ****************************************************************** +// * func: EmuGet2DSurfaceDesc +// ****************************************************************** +VOID WINAPI xd3d8::EmuGet2DSurfaceDesc +( + X_D3DPixelContainer *pPixelContainer, + DWORD dwLevel, + X_D3DSURFACE_DESC *pDesc +) +{ + EmuSwapFS(); // Win2k/XP FS + + // ****************************************************************** + // * debug trace + // ****************************************************************** + #ifdef _DEBUG_TRACE + { + printf("EmuD3D8 (0x%X): EmuGet2DSurfaceDesc\n" + "(\n" + " pPixelContainer : 0x%.08X\n" + " dwLevel : 0x%.08X\n" + " pDesc : 0x%.08X\n" + ");\n", + GetCurrentThreadId(), pPixelContainer, dwLevel, pDesc); + } + #endif + + EmuVerifyResourceIsRegistered(pPixelContainer); + + // TODO: HACK: notice that this is only safe to wrap a Texture Get2DSurfaceDesc, + // as it makes an assumption here. If there is some way to determine if this pointer + // is a texture or a surface, it'd be alot better! + IDirect3DTexture8 *pTexture8 = pPixelContainer->EmuTexture8; + + D3DSURFACE_DESC SurfaceDesc; + + HRESULT hRet = pTexture8->GetLevelDesc(dwLevel, &SurfaceDesc); + + // ****************************************************************** + // * Rearrange into windows format (remove D3DPool) + // ****************************************************************** + { + // Convert Format (PC->Xbox) + pDesc->Format = EmuPC2XB_D3DFormat(SurfaceDesc.Format); + pDesc->Type = SurfaceDesc.Type; + + if(pDesc->Type > 7) + EmuCleanup("EmuIDirect3DSurface8_GetDesc: pDesc->Type > 7"); + + pDesc->Usage = SurfaceDesc.Usage; + pDesc->Size = SurfaceDesc.Size; + + // TODO: Convert from Xbox to PC!! + if(SurfaceDesc.MultiSampleType == D3DMULTISAMPLE_NONE) + pDesc->MultiSampleType = (xd3d8::D3DMULTISAMPLE_TYPE)0x0011; + else + EmuCleanup("EmuGet2DSurfaceDesc Unknown Multisample format! (%d)", SurfaceDesc.MultiSampleType); + + pDesc->Width = SurfaceDesc.Width; + pDesc->Height = SurfaceDesc.Height; + } + + EmuSwapFS(); // XBox FS + + return; +} + // ****************************************************************** // * func: EmuIDirect3DSurface8_GetDesc // ****************************************************************** @@ -1987,6 +2084,59 @@ xd3d8::X_D3DResource * WINAPI xd3d8::EmuIDirect3DTexture8_GetSurfaceLevel2 return pSurfaceLevel; } +// ****************************************************************** +// * func: EmuIDirect3DTexture8_LockRect +// ****************************************************************** +HRESULT WINAPI xd3d8::EmuIDirect3DTexture8_LockRect +( + X_D3DTexture *pThis, + UINT Level, + D3DLOCKED_RECT *pLockedRect, + CONST RECT *pRect, + DWORD Flags +) +{ + EmuSwapFS(); // Win2k/XP FS + + // ****************************************************************** + // * debug trace + // ****************************************************************** + #ifdef _DEBUG_TRACE + { + printf("EmuD3D8 (0x%X): EmuIDirect3DTexture8_LockRect\n" + "(\n" + " pThis : 0x%.08X\n" + " Level : 0x%.08X\n" + " pLockedRect : 0x%.08X\n" + " pRect : 0x%.08X\n" + " Flags : 0x%.08X\n" + ");\n", + GetCurrentThreadId(), pThis, Level, pLockedRect, pRect, Flags); + } + #endif + + EmuVerifyResourceIsRegistered(pThis); + + IDirect3DTexture8 *pTexture8 = pThis->EmuTexture8; + + DWORD NewFlags = 0; + + if(Flags & 0x80) + NewFlags |= D3DLOCK_READONLY; + + if(Flags & !(0x80 | 0x40)) + EmuCleanup("EmuIDirect3DTexture8_LockRect: Unknown Flags! (0x%.08X)", Flags); + + // Remove old lock(s) + pTexture8->UnlockRect(Level); + + HRESULT hRet = pTexture8->LockRect(Level, pLockedRect, pRect, NewFlags); + + EmuSwapFS(); // XBox FS + + return hRet; +} + // ****************************************************************** // * func: EmuIDirect3DTexture8_GetSurfaceLevel // ****************************************************************** @@ -3038,8 +3188,8 @@ VOID WINAPI xd3d8::EmuIDirect3DDevice8_DrawVertices EmuUpdateDeferredStates(); - if((DWORD)PrimitiveType == 0x03 || (DWORD)PrimitiveType == 0x08 || (DWORD)PrimitiveType == 0x09 || (DWORD)PrimitiveType == 0x10) - printf("Unsupported PrimitiveType! (%d)\n", (DWORD)PrimitiveType); + if((DWORD)PrimitiveType == 0x03 || (DWORD)PrimitiveType == 0x09 || (DWORD)PrimitiveType == 0x10) + printf("*Warning* unsupported PrimitiveType! (%d)\n", (DWORD)PrimitiveType); UINT PrimitiveCount = EmuD3DVertex2PrimitiveCount(PrimitiveType, VertexCount); @@ -3104,7 +3254,7 @@ VOID WINAPI xd3d8::EmuIDirect3DDevice8_DrawVerticesUP EmuUpdateDeferredStates(); - if((DWORD)PrimitiveType == 0x03 || (DWORD)PrimitiveType == 0x08 || (DWORD)PrimitiveType == 0x09 || (DWORD)PrimitiveType == 0x10) + if((DWORD)PrimitiveType == 0x03 || (DWORD)PrimitiveType == 0x09 || (DWORD)PrimitiveType == 0x10) printf("Unsupported PrimitiveType! (%d)\n", (DWORD)PrimitiveType); UINT PrimitiveCount = EmuD3DVertex2PrimitiveCount(PrimitiveType, VertexCount); @@ -3180,12 +3330,26 @@ VOID WINAPI xd3d8::EmuIDirect3DDevice8_DrawIndexedVertices // Convert from Xbox to PC enumeration D3DPRIMITIVETYPE PCPrimitiveType = EmuPrimitiveType(PrimitiveType); + IDirect3DVertexBuffer8 *pOrigVertexBuffer8 = 0; + IDirect3DVertexBuffer8 *pHackVertexBuffer8 = 0; + + uint32 nStride = 0; + + if(PrimitiveType == 8) // Quad List + { + PrimitiveCount *= 2; + nStride = EmuQuadHackA(PrimitiveCount, pOrigVertexBuffer8, pHackVertexBuffer8); + } + g_pD3DDevice8->DrawIndexedPrimitive ( PCPrimitiveType, 0, PrimitiveCount, 0, PrimitiveCount ); + if(PrimitiveType == 8) // Quad List + EmuQuadHackB(nStride, pOrigVertexBuffer8, pHackVertexBuffer8); + EmuSwapFS(); // XBox FS return;