From 45da1ec9cdb1923f20ba78391c08936973db45b2 Mon Sep 17 00:00:00 2001 From: vboxsync Date: Tue, 9 May 2023 05:28:22 +0000 Subject: Devices/Graphics: common code for 3D backend initialization and termination. bugref:9830 git-svn-id: https://www.virtualbox.org/svn/vbox/trunk@99688 cfe28804-0f27-0410-a406-dd0f0b0b656f --- src/VBox/Devices/Graphics/DevVGA-SVGA-cmd.cpp | 104 ++++++++++++++------- src/VBox/Devices/Graphics/DevVGA-SVGA-internal.h | 5 + src/VBox/Devices/Graphics/DevVGA-SVGA.cpp | 32 +++---- .../Devices/Graphics/DevVGA-SVGA3d-dx-dx11.cpp | 40 ++------ .../Devices/Graphics/DevVGA-SVGA3d-dx-shader.cpp | 9 +- src/VBox/Devices/Graphics/DevVGA-SVGA3d-ogl.cpp | 59 +----------- src/VBox/Devices/Graphics/DevVGA-SVGA3d-win.cpp | 26 +----- src/VBox/Devices/Graphics/DevVGA-SVGA3d.cpp | 97 +++++++++++++++++++ src/VBox/Devices/Graphics/DevVGA-SVGA3d.h | 5 + 9 files changed, 211 insertions(+), 166 deletions(-) diff --git a/src/VBox/Devices/Graphics/DevVGA-SVGA-cmd.cpp b/src/VBox/Devices/Graphics/DevVGA-SVGA-cmd.cpp index d58fbed8a9d..4fc1a185b1c 100644 --- a/src/VBox/Devices/Graphics/DevVGA-SVGA-cmd.cpp +++ b/src/VBox/Devices/Graphics/DevVGA-SVGA-cmd.cpp @@ -538,6 +538,7 @@ static void vmsvgaR3GboDestroy(PVMSVGAR3STATE pSvgaR3State, PVMSVGAGBO pGbo) if (RT_LIKELY(VMSVGA_IS_GBO_CREATED(pGbo))) { + RTMemFree(pGbo->pvHost); RTMemFree(pGbo->paDescriptors); RT_ZERO(*pGbo); } @@ -854,6 +855,13 @@ static int vmsvgaR3MobCreate(PVMSVGAR3STATE pSvgaR3State, } +static void vmsvgaR3MobFree(PVMSVGAR3STATE pSvgaR3State, PVMSVGAMOB pMob) +{ + vmsvgaR3GboDestroy(pSvgaR3State, &pMob->Gbo); + RTMemFree(pMob); +} + + static int vmsvgaR3MobDestroy(PVMSVGAR3STATE pSvgaR3State, SVGAMobId mobid) { /* Update the entry in the pSvgaR3State->pGboOTableMob. */ @@ -866,8 +874,7 @@ static int vmsvgaR3MobDestroy(PVMSVGAR3STATE pSvgaR3State, SVGAMobId mobid) if (pMob) { RTListNodeRemove(&pMob->nodeLRU); - vmsvgaR3GboDestroy(pSvgaR3State, &pMob->Gbo); - RTMemFree(pMob); + vmsvgaR3MobFree(pSvgaR3State, pMob); return VINF_SUCCESS; } @@ -956,8 +963,43 @@ void *vmsvgaR3MobBackingStorePtr(PVMSVGAMOB pMob, uint32_t off) return NULL; } + +static DECLCALLBACK(int) vmsvgaR3MobFreeCb(PAVLU32NODECORE pNode, void *pvUser) +{ + PVMSVGAMOB pMob = (PVMSVGAMOB)pNode; + PVMSVGAR3STATE pSvgaR3State = (PVMSVGAR3STATE)pvUser; + vmsvgaR3MobFree(pSvgaR3State, pMob); + return 0; +} + + #endif /* VBOX_WITH_VMSVGA3D */ + + +void vmsvgaR3ResetSvgaState(PVGASTATE pThis, PVGASTATECC pThisCC) +{ +#ifdef VBOX_WITH_VMSVGA3D + PVMSVGAR3STATE const pSvgaR3State = pThisCC->svga.pSvgaR3State; + RT_NOREF(pThis); + + RTAvlU32Destroy(&pSvgaR3State->MOBTree, vmsvgaR3MobFreeCb, pSvgaR3State); + RTListInit(&pSvgaR3State->MOBLRUList); + + for (unsigned i = 0; i < RT_ELEMENTS(pSvgaR3State->aGboOTables); ++i) + vmsvgaR3GboDestroy(pSvgaR3State, &pSvgaR3State->aGboOTables[i]); +#else + RT_NOREF(pThis, pThisCC); +#endif +} + + +void vmsvgaR3TerminateSvgaState(PVGASTATE pThis, PVGASTATECC pThisCC) +{ + vmsvgaR3ResetSvgaState(pThis, pThisCC); +} + + /* * Screen objects. */ @@ -973,21 +1015,35 @@ VMSVGASCREENOBJECT *vmsvgaR3GetScreenObject(PVGASTATECC pThisCC, uint32_t idScre return NULL; } -void vmsvgaR3ResetScreens(PVGASTATE pThis, PVGASTATECC pThisCC) + +int vmsvgaR3DestroyScreen(PVGASTATE pThis, PVGASTATECC pThisCC, VMSVGASCREENOBJECT *pScreen) { + pScreen->fModified = true; + pScreen->fDefined = false; + + /* Notify frontend that the screen is about to be deleted. */ + vmsvgaR3ChangeMode(pThis, pThisCC); + #ifdef VBOX_WITH_VMSVGA3D - if (pThis->svga.f3DEnabled) + if (RT_LIKELY(pThis->svga.f3DEnabled)) + vmsvga3dDestroyScreen(pThisCC, pScreen); +#endif + + RTMemFree(pScreen->pvScreenBitmap); + pScreen->pvScreenBitmap = NULL; + + return VINF_SUCCESS; +} + + +void vmsvgaR3ResetScreens(PVGASTATE pThis, PVGASTATECC pThisCC) +{ + for (uint32_t idScreen = 0; idScreen < (uint32_t)RT_ELEMENTS(pThisCC->svga.pSvgaR3State->aScreens); ++idScreen) { - for (uint32_t idScreen = 0; idScreen < (uint32_t)RT_ELEMENTS(pThisCC->svga.pSvgaR3State->aScreens); ++idScreen) - { - VMSVGASCREENOBJECT *pScreen = vmsvgaR3GetScreenObject(pThisCC, idScreen); - if (pScreen) - vmsvga3dDestroyScreen(pThisCC, pScreen); - } + VMSVGASCREENOBJECT *pScreen = vmsvgaR3GetScreenObject(pThisCC, idScreen); + if (pScreen) + vmsvgaR3DestroyScreen(pThis, pThisCC, pScreen); } -#else - RT_NOREF(pThis, pThisCC); -#endif } @@ -1798,17 +1854,7 @@ static void vmsvga3dCmdDestroyGBScreenTarget(PVGASTATE pThis, PVGASTATECC pThisC /* Screen objects and screen targets are similar, therefore we will use the same for both. */ /** @todo Generic screen object/target interface. */ VMSVGASCREENOBJECT *pScreen = &pSvgaR3State->aScreens[pCmd->stid]; - pScreen->fModified = true; - pScreen->fDefined = false; - pScreen->idScreen = pCmd->stid; - - if (RT_LIKELY(pThis->svga.f3DEnabled)) - vmsvga3dDestroyScreen(pThisCC, pScreen); - - vmsvgaR3ChangeMode(pThis, pThisCC); - - RTMemFree(pScreen->pvScreenBitmap); - pScreen->pvScreenBitmap = NULL; + vmsvgaR3DestroyScreen(pThis, pThisCC, pScreen); } } @@ -6718,15 +6764,7 @@ void vmsvgaR3CmdDestroyScreen(PVGASTATE pThis, PVGASTATECC pThisCC, SVGAFifoCmdD RT_UNTRUSTED_VALIDATED_FENCE(); VMSVGASCREENOBJECT *pScreen = &pSvgaR3State->aScreens[idScreen]; - pScreen->fModified = true; - pScreen->fDefined = false; - pScreen->idScreen = idScreen; - -#ifdef VBOX_WITH_VMSVGA3D - if (RT_LIKELY(pThis->svga.f3DEnabled)) - vmsvga3dDestroyScreen(pThisCC, pScreen); -#endif - vmsvgaR3ChangeMode(pThis, pThisCC); + vmsvgaR3DestroyScreen(pThis, pThisCC, pScreen); } diff --git a/src/VBox/Devices/Graphics/DevVGA-SVGA-internal.h b/src/VBox/Devices/Graphics/DevVGA-SVGA-internal.h index c31c824d0b4..81acf05526e 100644 --- a/src/VBox/Devices/Graphics/DevVGA-SVGA-internal.h +++ b/src/VBox/Devices/Graphics/DevVGA-SVGA-internal.h @@ -258,7 +258,12 @@ DECLCALLBACK(int) vmsvgaR3ResetGmrHandlers(PVGASTATE pThis); DECLCALLBACK(int) vmsvgaR3DeregisterGmr(PPDMDEVINS pDevIns, uint32_t gmrId); #endif +int vmsvgaR3DestroyScreen(PVGASTATE pThis, PVGASTATECC pThisCC, VMSVGASCREENOBJECT *pScreen); + void vmsvgaR3ResetScreens(PVGASTATE pThis, PVGASTATECC pThisCC); +void vmsvgaR3ResetSvgaState(PVGASTATE pThis, PVGASTATECC pThisCC); + +void vmsvgaR3TerminateSvgaState(PVGASTATE pThis, PVGASTATECC pThisCC); int vmsvgaR3ChangeMode(PVGASTATE pThis, PVGASTATECC pThisCC); int vmsvgaR3UpdateScreen(PVGASTATECC pThisCC, VMSVGASCREENOBJECT *pScreen, int x, int y, int w, int h); diff --git a/src/VBox/Devices/Graphics/DevVGA-SVGA.cpp b/src/VBox/Devices/Graphics/DevVGA-SVGA.cpp index 8e2330afe3c..5284984c9c7 100644 --- a/src/VBox/Devices/Graphics/DevVGA-SVGA.cpp +++ b/src/VBox/Devices/Graphics/DevVGA-SVGA.cpp @@ -3202,6 +3202,7 @@ static SVGACBStatus vmsvgaR3CmdBufDCStartStop(PVMSVGAR3STATE pSvgaR3State, SVGAD else { vmsvgaR3CmdBufCtxTerm(pSvgaR3State->apCmdBufCtxs[pCmd->context]); + RTMemFree(pSvgaR3State->apCmdBufCtxs[pCmd->context]); pSvgaR3State->apCmdBufCtxs[pCmd->context] = NULL; } RTCritSectLeave(&pSvgaR3State->CritSectCmdBuf); @@ -4043,13 +4044,11 @@ static void vmsvgaR3FifoHandleExtCmd(PPDMDEVINS pDevIns, PVGASTATE pThis, PVGAST vmsvgaR3ResetScreens(pThis, pThisCC); # ifdef VBOX_WITH_VMSVGA3D + /* The 3d subsystem must be reset from the fifo thread. */ if (pThis->svga.f3DEnabled) - { - /* The 3d subsystem must be reset from the fifo thread. */ - PVMSVGAR3STATE pSVGAState = pThisCC->svga.pSvgaR3State; - pSVGAState->pFuncs3D->pfnReset(pThisCC); - } + vmsvga3dReset(pThisCC); # endif + vmsvgaR3ResetSvgaState(pThis, pThisCC); break; case VMSVGA_FIFO_EXTCMD_POWEROFF: @@ -4063,15 +4062,13 @@ static void vmsvgaR3FifoHandleExtCmd(PPDMDEVINS pDevIns, PVGASTATE pThis, PVGAST case VMSVGA_FIFO_EXTCMD_TERMINATE: Log(("vmsvgaR3FifoLoop: terminate the fifo thread.\n")); Assert(pThisCC->svga.pvFIFOExtCmdParam == NULL); + # ifdef VBOX_WITH_VMSVGA3D + /* The 3d subsystem must be shut down from the fifo thread. */ if (pThis->svga.f3DEnabled) - { - /* The 3d subsystem must be shut down from the fifo thread. */ - PVMSVGAR3STATE pSVGAState = pThisCC->svga.pSvgaR3State; - if (pSVGAState->pFuncs3D && pSVGAState->pFuncs3D->pfnTerminate) - pSVGAState->pFuncs3D->pfnTerminate(pThisCC); - } + vmsvga3dTerminate(pThisCC); # endif + vmsvgaR3TerminateSvgaState(pThis, pThisCC); break; case VMSVGA_FIFO_EXTCMD_SAVESTATE: @@ -6264,6 +6261,7 @@ static void vmsvgaR3StateTerm(PVGASTATE pThis, PVGASTATECC pThisCC) for (unsigned i = 0; i < RT_ELEMENTS(pSVGAState->apCmdBufCtxs); ++i) { vmsvgaR3CmdBufCtxTerm(pSVGAState->apCmdBufCtxs[i]); + RTMemFree(pSVGAState->apCmdBufCtxs[i]); pSVGAState->apCmdBufCtxs[i] = NULL; } vmsvgaR3CmdBufCtxTerm(&pSVGAState->CmdBufCtxDC); @@ -6389,15 +6387,9 @@ static int vmsvgaR3Init3dInterfaces(PPDMDEVINS pDevIns, PVGASTATE pThis, PVGASTA if (RT_SUCCESS(rc)) { - /* 3D interface is required. */ - if (pSVGAState->pFuncs3D) - { - rc = pSVGAState->pFuncs3D->pfnInit(pDevIns, pThis, pThisCC); - if (RT_SUCCESS(rc)) - return VINF_SUCCESS; - } - else - rc = VERR_NOT_SUPPORTED; + rc = vmsvga3dInit(pDevIns, pThis, pThisCC); + if (RT_SUCCESS(rc)) + return VINF_SUCCESS; } vmsvga3dR3Free3dInterfaces(pThisCC); diff --git a/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx-dx11.cpp b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx-dx11.cpp index 20571cab8c1..8be2ba90915 100644 --- a/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx-dx11.cpp +++ b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx-dx11.cpp @@ -3247,13 +3247,9 @@ static DECLCALLBACK(int) vmsvga3dBackInit(PPDMDEVINS pDevIns, PVGASTATE pThis, P } #endif - PVMSVGA3DSTATE pState = (PVMSVGA3DSTATE)RTMemAllocZ(sizeof(VMSVGA3DSTATE)); - AssertReturn(pState, VERR_NO_MEMORY); - pThisCC->svga.p3dState = pState; - PVMSVGA3DBACKEND pBackend = (PVMSVGA3DBACKEND)RTMemAllocZ(sizeof(VMSVGA3DBACKEND)); AssertReturn(pBackend, VERR_NO_MEMORY); - pState->pBackend = pBackend; + pThisCC->svga.p3dState->pBackend = pBackend; rc = RTLdrLoadSystem(VBOX_D3D11_LIBRARY_NAME, /* fNoUnload = */ true, &pBackend->hD3D11); AssertRC(rc); @@ -3319,24 +3315,7 @@ static DECLCALLBACK(int) vmsvga3dBackPowerOn(PPDMDEVINS pDevIns, PVGASTATE pThis static DECLCALLBACK(int) vmsvga3dBackReset(PVGASTATECC pThisCC) { - PVMSVGA3DSTATE pState = pThisCC->svga.p3dState; - AssertReturn(pState, VERR_INVALID_STATE); - - /** @todo This is generic code. Must be moved to in DevVGA-SVGA3d.cpp */ - /* Destroy all leftover surfaces. */ - for (uint32_t i = 0; i < pState->cSurfaces; i++) - { - if (pState->papSurfaces[i]->id != SVGA3D_INVALID_ID) - vmsvga3dSurfaceDestroy(pThisCC, pState->papSurfaces[i]->id); - } - - /* Destroy all leftover DX contexts. */ - for (uint32_t i = 0; i < pState->cDXContexts; i++) - { - if (pState->papDXContexts[i]->cid != SVGA3D_INVALID_ID) - vmsvga3dDXDestroyContext(pThisCC, pState->papDXContexts[i]->cid); - } - + RT_NOREF(pThisCC); return VINF_SUCCESS; } @@ -3347,16 +3326,8 @@ static DECLCALLBACK(int) vmsvga3dBackTerminate(PVGASTATECC pThisCC) AssertReturn(pState, VERR_INVALID_STATE); if (pState->pBackend) - { - /* Clean up backends. For example release resources from surfaces. */ - vmsvga3dBackReset(pThisCC); - dxDeviceDestroy(pState->pBackend, &pState->pBackend->dxDevice); - RTMemFree(pState->pBackend); - pState->pBackend = NULL; - } - return VINF_SUCCESS; } @@ -5614,6 +5585,11 @@ static DECLCALLBACK(int) vmsvga3dBackDXDestroyContext(PVGASTATECC pThisCC, PVMSV for (uint32_t i = 0; i < pBackendDXContext->cStreamOutput; ++i) dxDestroyStreamOutput(&pBackendDXContext->paStreamOutput[i]); } + if (pBackendDXContext->paUnorderedAccessView) + { + for (uint32_t i = 0; i < pBackendDXContext->cUnorderedAccessView; ++i) + D3D_RELEASE(pBackendDXContext->paRenderTargetView[i].u.pUnorderedAccessView); + } RTMemFreeZ(pBackendDXContext->papBlendState, sizeof(pBackendDXContext->papBlendState[0]) * pBackendDXContext->cBlendState); RTMemFreeZ(pBackendDXContext->papDepthStencilState, sizeof(pBackendDXContext->papDepthStencilState[0]) * pBackendDXContext->cDepthStencilState); @@ -5626,6 +5602,7 @@ static DECLCALLBACK(int) vmsvga3dBackDXDestroyContext(PVGASTATECC pThisCC, PVMSV RTMemFreeZ(pBackendDXContext->paQuery, sizeof(pBackendDXContext->paQuery[0]) * pBackendDXContext->cQuery); RTMemFreeZ(pBackendDXContext->paShader, sizeof(pBackendDXContext->paShader[0]) * pBackendDXContext->cShader); RTMemFreeZ(pBackendDXContext->paStreamOutput, sizeof(pBackendDXContext->paStreamOutput[0]) * pBackendDXContext->cStreamOutput); + RTMemFreeZ(pBackendDXContext->paUnorderedAccessView, sizeof(pBackendDXContext->paUnorderedAccessView[0]) * pBackendDXContext->cUnorderedAccessView); /* Destroy backend surfaces which belong to this context. */ /** @todo The context should have a list of surfaces (and also shared resources). */ @@ -8945,6 +8922,7 @@ static int dxDefineShader(PVMSVGA3DDXCONTEXT pDXContext, SVGA3dShaderId shaderId static int dxDestroyShader(DXSHADER *pDXShader) { pDXShader->enmShaderType = SVGA3D_SHADERTYPE_INVALID; + DXShaderFree(&pDXShader->shaderInfo); D3D_RELEASE(pDXShader->pShader); RTMemFree(pDXShader->pvDXBC); pDXShader->pvDXBC = NULL; diff --git a/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx-shader.cpp b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx-shader.cpp index 3c90eae2840..e9231fc1b7d 100644 --- a/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx-shader.cpp +++ b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx-shader.cpp @@ -1270,8 +1270,13 @@ static bool dxbcByteWriterRealloc(DXBCByteWriter *w, uint32_t cbNew) } uint32_t const cbCurrent = dxbcByteWriterSize(w); - memcpy(pvNew, w->pu8ByteCodeBegin, cbCurrent); - RTMemFree(w->pu8ByteCodeBegin); + if (cbCurrent) + { + memcpy(pvNew, w->pu8ByteCodeBegin, cbCurrent); + RTMemFree(w->pu8ByteCodeBegin); + } + else + Assert(w->pu8ByteCodeBegin == NULL); w->pu8ByteCodeBegin = (uint8_t *)pvNew; w->pu8ByteCodePtr = w->pu8ByteCodeBegin + cbCurrent; diff --git a/src/VBox/Devices/Graphics/DevVGA-SVGA3d-ogl.cpp b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-ogl.cpp index 687a1170e78..d0be0f9b066 100644 --- a/src/VBox/Devices/Graphics/DevVGA-SVGA3d-ogl.cpp +++ b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-ogl.cpp @@ -608,7 +608,7 @@ static DECLCALLBACK(bool) vmsvga3dShaderIfGetNextExtension(PVBOXVMSVGASHADERIF p static DECLCALLBACK(int) vmsvga3dBackInit(PPDMDEVINS pDevIns, PVGASTATE pThis, PVGASTATECC pThisCC) { int rc; - RT_NOREF(pDevIns, pThis); + RT_NOREF(pDevIns, pThis, pThisCC); AssertCompile(GL_TRUE == 1); AssertCompile(GL_FALSE == 0); @@ -641,12 +641,6 @@ static DECLCALLBACK(int) vmsvga3dBackInit(PPDMDEVINS pDevIns, PVGASTATE pThis, P } #endif - /* - * Allocate the state. - */ - pThisCC->svga.p3dState = (PVMSVGA3DSTATE)RTMemAllocZ(sizeof(VMSVGA3DSTATE)); - AssertReturn(pThisCC->svga.p3dState, VERR_NO_MEMORY); - #ifdef RT_OS_WINDOWS /* Create event semaphore and async IO thread. */ PVMSVGA3DSTATE pState = pThisCC->svga.p3dState; @@ -664,8 +658,6 @@ static DECLCALLBACK(int) vmsvga3dBackInit(PPDMDEVINS pDevIns, PVGASTATE pThis, P } else LogRel(("VMSVGA3d: RTSemEventCreate failed: %Rrc\n", rc)); - RTMemFree(pThisCC->svga.p3dState); - pThisCC->svga.p3dState = NULL; return rc; #else return VINF_SUCCESS; @@ -1182,20 +1174,6 @@ static DECLCALLBACK(int) vmsvga3dBackReset(PVGASTATECC pThisCC) PVMSVGA3DSTATE pState = pThisCC->svga.p3dState; AssertReturn(pThisCC->svga.p3dState, VERR_NO_MEMORY); - /* Destroy all leftover surfaces. */ - for (uint32_t i = 0; i < pState->cSurfaces; i++) - { - if (pState->papSurfaces[i]->id != SVGA3D_INVALID_ID) - vmsvga3dSurfaceDestroy(pThisCC, pState->papSurfaces[i]->id); - } - - /* Destroy all leftover contexts. */ - for (uint32_t i = 0; i < pState->cContexts; i++) - { - if (pState->papContexts[i]->id != SVGA3D_INVALID_ID) - vmsvga3dBackContextDestroy(pThisCC, pState->papContexts[i]->id); - } - if (pState->SharedCtx.id == VMSVGA3D_SHARED_CTX_ID) vmsvga3dContextDestroyOgl(pThisCC, &pState->SharedCtx, VMSVGA3D_SHARED_CTX_ID); @@ -1208,9 +1186,6 @@ static DECLCALLBACK(int) vmsvga3dBackTerminate(PVGASTATECC pThisCC) AssertReturn(pState, VERR_WRONG_ORDER); int rc; - rc = vmsvga3dBackReset(pThisCC); - AssertRCReturn(rc, rc); - /* Terminate the shader library. */ rc = ShaderDestroyLib(); AssertRC(rc); @@ -1239,36 +1214,6 @@ static DECLCALLBACK(int) vmsvga3dBackTerminate(PVGASTATECC pThisCC) #endif pState->pszOtherExtensions = NULL; - /* Free all leftover surface states. */ - for (uint32_t i = 0; i < pState->cSurfaces; i++) - { - AssertPtr(pState->papSurfaces[i]); - RTMemFree(pState->papSurfaces[i]); - pState->papSurfaces[i] = NULL; - } - - /* Destroy all leftover contexts. */ - for (uint32_t i = 0; i < pState->cContexts; i++) - { - AssertPtr(pState->papContexts[i]); - RTMemFree(pState->papContexts[i]); - pState->papContexts[i] = NULL; - } - - if (pState->papSurfaces) - { - RTMemFree(pState->papSurfaces); - pState->papSurfaces = NULL; - } - - if (pState->papContexts) - { - RTMemFree(pState->papContexts); - pState->papContexts = NULL; - } - - pThisCC->svga.p3dState = NULL; - RTMemFree(pState); return VINF_SUCCESS; } @@ -6714,7 +6659,7 @@ static int vmsvga3dSetVertexAttrib(PVMSVGA3DSTATE pState, GLuint index, SVGA3dVe /** @todo Test */ /* "Three-component, signed, 10 10 10 format normalized and expanded to (v[0]/511.0, v[1]/511.0, v[2]/511.0, 1)." */ uint32_t const u32 = *(uint32_t *)pv; - GLfloat const v[4] = { (u32 & 0x3ff) / 511.0f, ((u32 >> 10) & 0x3ff) / 511.0f, ((u32 >> 20) & 0x3ff) / 511.0f, 1.0f }; + GLfloat const v[4] = { (float)(u32 & 0x3ff) / 511.0f, (float)((u32 >> 10) & 0x3ff) / 511.0f, (float)((u32 >> 20) & 0x3ff) / 511.0f, 1.0f }; pState->ext.glVertexAttrib4fv(index, v); break; } diff --git a/src/VBox/Devices/Graphics/DevVGA-SVGA3d-win.cpp b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-win.cpp index 79fb913991b..bc762350c99 100644 --- a/src/VBox/Devices/Graphics/DevVGA-SVGA3d-win.cpp +++ b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-win.cpp @@ -200,9 +200,7 @@ static DECLCALLBACK(int) vmsvga3dBackInit(PPDMDEVINS pDevIns, PVGASTATE pThis, P { RT_NOREF(pDevIns, pThis); - PVMSVGA3DSTATE pState; - pThisCC->svga.p3dState = pState = (PVMSVGA3DSTATE)RTMemAllocZ(sizeof(VMSVGA3DSTATE)); - AssertReturn(pThisCC->svga.p3dState, VERR_NO_MEMORY); + PVMSVGA3DSTATE pState = pThisCC->svga.p3dState; /* Create event semaphore. */ int rc = RTSemEventCreate(&pState->WndRequestSem); @@ -310,22 +308,7 @@ static DECLCALLBACK(int) vmsvga3dBackPowerOn(PPDMDEVINS pDevIns, PVGASTATE pThis static DECLCALLBACK(int) vmsvga3dBackReset(PVGASTATECC pThisCC) { - PVMSVGA3DSTATE pState = pThisCC->svga.p3dState; - AssertReturn(pThisCC->svga.p3dState, VERR_NO_MEMORY); - - /* Destroy all leftover surfaces. */ - for (uint32_t i = 0; i < pState->cSurfaces; i++) - { - if (pState->papSurfaces[i]->id != SVGA3D_INVALID_ID) - vmsvga3dSurfaceDestroy(pThisCC, pState->papSurfaces[i]->id); - } - - /* Destroy all leftover contexts. */ - for (uint32_t i = 0; i < pState->cContexts; i++) - { - if (pState->papContexts[i]->id != SVGA3D_INVALID_ID) - vmsvga3dBackContextDestroy(pThisCC, pState->papContexts[i]->id); - } + RT_NOREF(pThisCC); return VINF_SUCCESS; } @@ -334,11 +317,8 @@ static DECLCALLBACK(int) vmsvga3dBackTerminate(PVGASTATECC pThisCC) PVMSVGA3DSTATE pState = pThisCC->svga.p3dState; AssertReturn(pThisCC->svga.p3dState, VERR_NO_MEMORY); - int rc = vmsvga3dBackReset(pThisCC); - AssertRCReturn(rc, rc); - /* Terminate the window creation thread. */ - rc = vmsvga3dSendThreadMessage(pState->pWindowThread, pState->WndRequestSem, WM_VMSVGA3D_EXIT, 0, 0); + int rc = vmsvga3dSendThreadMessage(pState->pWindowThread, pState->WndRequestSem, WM_VMSVGA3D_EXIT, 0, 0); AssertRCReturn(rc, rc); RTSemEventDestroy(pState->WndRequestSem); diff --git a/src/VBox/Devices/Graphics/DevVGA-SVGA3d.cpp b/src/VBox/Devices/Graphics/DevVGA-SVGA3d.cpp index 0b154345984..8019b3461db 100644 --- a/src/VBox/Devices/Graphics/DevVGA-SVGA3d.cpp +++ b/src/VBox/Devices/Graphics/DevVGA-SVGA3d.cpp @@ -1814,3 +1814,100 @@ bool vmsvga3dIsLegacyBackend(PVGASTATECC pThisCC) return pSvgaR3State->pFuncsDX == NULL; } + +void vmsvga3dReset(PVGASTATECC pThisCC) +{ + /* Deal with data from PVMSVGA3DSTATE */ + PVMSVGA3DSTATE p3dState = pThisCC->svga.p3dState; + Assert(pThisCC->svga.p3dState); + + if ((pThisCC->svga.p3dState)) + { + /* Destroy all leftover surfaces. */ + for (uint32_t i = 0; i < p3dState->cSurfaces; i++) + { + if (p3dState->papSurfaces[i]->id != SVGA3D_INVALID_ID) + vmsvga3dSurfaceDestroy(pThisCC, p3dState->papSurfaces[i]->id); + RTMemFree(p3dState->papSurfaces[i]); + p3dState->papSurfaces[i] = NULL; + } + RTMemFree(p3dState->papSurfaces); + p3dState->papSurfaces = NULL; + p3dState->cSurfaces = 0; + + /* Destroy all leftover contexts. */ + for (uint32_t i = 0; i < p3dState->cContexts; i++) + { + if (p3dState->papContexts[i]->id != SVGA3D_INVALID_ID) + vmsvga3dContextDestroy(pThisCC, p3dState->papContexts[i]->id); + RTMemFree(p3dState->papContexts[i]); + p3dState->papContexts[i] = NULL; + } + RTMemFree(p3dState->papContexts); + p3dState->papContexts = NULL; + p3dState->cContexts = 0; + + if (!vmsvga3dIsLegacyBackend(pThisCC)) + { + /* Destroy all leftover DX contexts. */ + for (uint32_t i = 0; i < p3dState->cDXContexts; i++) + { + if (p3dState->papDXContexts[i]->cid != SVGA3D_INVALID_ID) + vmsvga3dDXDestroyContext(pThisCC, p3dState->papDXContexts[i]->cid); + RTMemFree(p3dState->papDXContexts[i]); + p3dState->papDXContexts[i] = NULL; + } + RTMemFree(p3dState->papDXContexts); + p3dState->papDXContexts = NULL; + p3dState->cDXContexts = 0; + } + } + + /* Reset the backend. */ + PVMSVGAR3STATE pSvgaR3State = pThisCC->svga.pSvgaR3State; + if (pSvgaR3State->pFuncs3D && pSvgaR3State->pFuncs3D->pfnReset) + pSvgaR3State->pFuncs3D->pfnReset(pThisCC); +} + + +void vmsvga3dTerminate(PVGASTATECC pThisCC) +{ + /* Clean up backend. */ + vmsvga3dReset(pThisCC); + + /* Deal with data from PVMSVGA3DSTATE */ + PVMSVGA3DSTATE p3dState = pThisCC->svga.p3dState; + AssertReturnVoid(p3dState); + + /* Terminate the backend. */ + PVMSVGAR3STATE pSvgaR3State = pThisCC->svga.pSvgaR3State; + if (pSvgaR3State->pFuncs3D && pSvgaR3State->pFuncs3D->pfnTerminate) + pSvgaR3State->pFuncs3D->pfnTerminate(pThisCC); + + RTMemFree(p3dState->pBackend); + p3dState->pBackend = NULL; + + RTMemFree(p3dState); + pThisCC->svga.p3dState = NULL; +} + + +int vmsvga3dInit(PPDMDEVINS pDevIns, PVGASTATE pThis, PVGASTATECC pThisCC) +{ + PVMSVGAR3STATE pSvgaR3State = pThisCC->svga.pSvgaR3State; + + /* 3D interface is required. */ + AssertReturn(pSvgaR3State->pFuncs3D && pSvgaR3State->pFuncs3D->pfnInit, VERR_NOT_SUPPORTED); + + PVMSVGA3DSTATE p3dState = (PVMSVGA3DSTATE)RTMemAllocZ(sizeof(VMSVGA3DSTATE)); + AssertReturn(p3dState, VERR_NO_MEMORY); + pThisCC->svga.p3dState = p3dState; + + int rc = pSvgaR3State->pFuncs3D->pfnInit(pDevIns, pThis, pThisCC); + if (RT_SUCCESS(rc)) + return VINF_SUCCESS; + + pThisCC->svga.p3dState = NULL; + RTMemFree(p3dState); + return rc; +} diff --git a/src/VBox/Devices/Graphics/DevVGA-SVGA3d.h b/src/VBox/Devices/Graphics/DevVGA-SVGA3d.h index 3c666956b9d..41bec0fc29d 100644 --- a/src/VBox/Devices/Graphics/DevVGA-SVGA3d.h +++ b/src/VBox/Devices/Graphics/DevVGA-SVGA3d.h @@ -94,6 +94,11 @@ typedef struct VMSVGA3D_MAPPED_SURFACE void *pvData; } VMSVGA3D_MAPPED_SURFACE; +void vmsvga3dReset(PVGASTATECC pThisCC); +void vmsvga3dTerminate(PVGASTATECC pThisCC); + +int vmsvga3dInit(PPDMDEVINS pDevIns, PVGASTATE pThis, PVGASTATECC pThisCC); + /* Write render targets to bitmaps. */ //#define DUMP_BITMAPS void vmsvga3dMapWriteBmpFile(VMSVGA3D_MAPPED_SURFACE const *pMap, char const *pszPrefix); -- cgit v1.2.1