VirtualBox

Changeset 57151 in vbox for trunk/src/VBox/Devices/Graphics


Ignore:
Timestamp:
Aug 2, 2015 7:46:25 PM (9 years ago)
Author:
vboxsync
Message:

VMSVGA3d: Started reworking 3d command handling code to avoid duplicating code and ending up with slightly different versions. E.g. the input validation is the same regardless of the backend.

Location:
trunk/src/VBox/Devices/Graphics
Files:
1 added
7 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Devices/Graphics/DevVGA-SVGA.cpp

    r57149 r57151  
    30543054
    30553055                        cMipLevels = (pHdr->size - sizeof(*pCmd)) / sizeof(SVGA3dSize);
    3056                         rc = vmsvga3dSurfaceDefine(pThis, pCmd->sid, (uint32_t)pCmd->surfaceFlags, pCmd->format, pCmd->face, 0, SVGA3D_TEX_FILTER_NONE, cMipLevels, (SVGA3dSize *)(pCmd + 1));
     3056                        rc = vmsvga3dSurfaceDefine(pThis, pCmd->sid, (uint32_t)pCmd->surfaceFlags, pCmd->format, pCmd->face, 0,
     3057                                                   SVGA3D_TEX_FILTER_NONE, cMipLevels, (SVGA3dSize *)(pCmd + 1));
    30573058#  ifdef DEBUG_GMR_ACCESS
    30583059                        VMR3ReqCallWait(PDMDevHlpGetVM(pThis->pDevInsR3), VMCPUID_ANY, (PFNRT)vmsvgaResetGMRHandlers, 1, pThis);
     
    30683069
    30693070                        cMipLevels = (pHdr->size - sizeof(*pCmd)) / sizeof(SVGA3dSize);
    3070                         rc = vmsvga3dSurfaceDefine(pThis, pCmd->sid, pCmd->surfaceFlags, pCmd->format, pCmd->face, pCmd->multisampleCount, pCmd->autogenFilter, cMipLevels, (SVGA3dSize *)(pCmd + 1));
     3071                        rc = vmsvga3dSurfaceDefine(pThis, pCmd->sid, pCmd->surfaceFlags, pCmd->format, pCmd->face,
     3072                                                   pCmd->multisampleCount, pCmd->autogenFilter,
     3073                                                   cMipLevels, (SVGA3dSize *)(pCmd + 1));
    30713074                        break;
    30723075                    }
     
    30963099                        VMSVGAFIFO_CHECK_3D_CMD_MIN_SIZE_BREAK(sizeof(*pCmd));
    30973100
    3098                         rc = vmsvga3dSurfaceStretchBlt(pThis, pCmd->dest, pCmd->boxDest, pCmd->src, pCmd->boxSrc, pCmd->mode);
     3101                        rc = vmsvga3dSurfaceStretchBlt(pThis, &pCmd->dest, &pCmd->boxDest, &pCmd->src, &pCmd->boxSrc, pCmd->mode);
    30993102                        break;
    31003103                    }
  • trunk/src/VBox/Devices/Graphics/DevVGA-SVGA3d-info.cpp

    r57150 r57151  
    321321                            /* Set row length and alignment of the output data. */
    322322                            VMSVGAPACKPARAMS SavedParams;
    323                             vmsvga3dSetPackParams(pState, pContext, pSurface, &SavedParams);
     323                            vmsvga3dOglSetPackParams(pState, pContext, pSurface, &SavedParams);
    324324
    325325                            glGetTexImage(GL_TEXTURE_2D,
     
    330330                            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    331331
    332                             vmsvga3dRestorePackParams(pState, pContext, pSurface, &SavedParams);
     332                            vmsvga3dOglRestorePackParams(pState, pContext, pSurface, &SavedParams);
    333333
    334334                            /* Restore the old active texture. */
  • trunk/src/VBox/Devices/Graphics/DevVGA-SVGA3d-internal.h

    r57149 r57151  
    609609};
    610610#endif
     611
     612/** Mask we frequently apply to VMSVGA3DSURFACE::flags for decing what kind
     613 * of surface we're dealing. */
     614#define VMSVGA3D_SURFACE_HINT_SWITCH_MASK \
     615    (   SVGA3D_SURFACE_HINT_INDEXBUFFER  | SVGA3D_SURFACE_HINT_VERTEXBUFFER \
     616      | SVGA3D_SURFACE_HINT_TEXTURE      | SVGA3D_SURFACE_HINT_RENDERTARGET \
     617      | SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_CUBEMAP )
     618
     619/** @def VMSVGA3DSURFACE_HAS_HW_SURFACE
     620 * Checks whether the surface has a host hardware/library surface.
     621 * @returns true/false
     622 * @param   a_pSurface      The VMSVGA3d surface.
     623 */
     624#ifdef VMSVGA3D_DIRECT3D
     625# define VMSVGA3DSURFACE_HAS_HW_SURFACE(a_pSurface) ((a_pSurface)->u.pSurface != NULL)
     626#else
     627# define VMSVGA3DSURFACE_HAS_HW_SURFACE(a_pSurface) ((a_pSurface)->oglId.texture != OPENGL_INVALID_ID)
     628#endif
     629
    611630
    612631
     
    966985
    967986
     987#ifdef VMSVGA3D_DIRECT3D
     988D3DFORMAT vmsvga3dSurfaceFormat2D3D(SVGA3dSurfaceFormat format);
     989D3DMULTISAMPLE_TYPE vmsvga3dMultipeSampleCount2D3D(uint32_t multisampleCount);
     990DECLCALLBACK(int) vmsvga3dSharedSurfaceDestroyTree(PAVLU32NODECORE pNode, void *pvParam);
     991int vmsvga3dSurfaceFlush(PVGASTATE pThis, PVMSVGA3DSURFACE pSurface);
     992#endif /* VMSVGA3D_DIRECT3D */
     993
     994
    968995#ifdef VMSVGA3D_OPENGL
    969996/** Save and setup everything. */
     
    9771004    GLint       iAlignment;
    9781005    GLint       cxRow;
    979 #ifdef VMSVGA3D_PARANOID_TEXTURE_PACKING
     1006# ifdef VMSVGA3D_PARANOID_TEXTURE_PACKING
    9801007    GLint       cyImage;
    9811008    GLboolean   fSwapBytes;
     
    9841011    GLint       cSkipPixels;
    9851012    GLint       cSkipImages;
    986 #endif
     1013# endif
    9871014} VMSVGAPACKPARAMS;
    9881015/** Pointer to saved texture packing parameters. */
     
    9911018typedef VMSVGAPACKPARAMS const *PCVMSVGAPACKPARAMS;
    9921019
    993 void vmsvga3dSetPackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface, PVMSVGAPACKPARAMS pSave);
    994 void vmsvga3dRestorePackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
     1020void vmsvga3dOglSetPackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
     1021                              PVMSVGAPACKPARAMS pSave);
     1022void vmsvga3dOglRestorePackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
    9951023                               PCVMSVGAPACKPARAMS pSave);
     1024void vmsvga3dOglSetUnpackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
     1025                                PVMSVGAPACKPARAMS pSave);
     1026void vmsvga3dOglRestoreUnpackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
     1027                                    PCVMSVGAPACKPARAMS pSave);
    9961028
    9971029/** @name VMSVGA3D_DEF_CTX_F_XXX - vmsvga3dContextDefineOgl flags.
     
    10001032 * When set, it's created using the alternative profile.  The latter is only
    10011033 * allowed if the VBOX_VMSVGA3D_DUAL_OPENGL_PROFILE is set.  */
    1002 #define VMSVGA3D_DEF_CTX_F_OTHER_PROFILE    RT_BIT_32(0)
     1034# define VMSVGA3D_DEF_CTX_F_OTHER_PROFILE   RT_BIT_32(0)
    10031035/** Defining the shared context.  */
    1004 #define VMSVGA3D_DEF_CTX_F_SHARED_CTX       RT_BIT_32(1)
     1036# define VMSVGA3D_DEF_CTX_F_SHARED_CTX      RT_BIT_32(1)
    10051037/** Defining the init time context (EMT).  */
    1006 #define VMSVGA3D_DEF_CTX_F_INIT             RT_BIT_32(2)
     1038# define VMSVGA3D_DEF_CTX_F_INIT            RT_BIT_32(2)
    10071039/** @} */
    10081040int  vmsvga3dContextDefineOgl(PVGASTATE pThis, uint32_t cid, uint32_t fFlags);
     1041void vmsvga3dSurfaceFormat2OGL(PVMSVGA3DSURFACE pSurface, SVGA3dSurfaceFormat format);
     1042
    10091043#endif /* VMSVGA3D_OPENGL */
    10101044
     
    10151049
    10161050
    1017 #endif
    1018 
     1051
     1052/* Command implementation workers. */
     1053void vmsvga3dBackSurfaceDestroy(PVMSVGA3DSTATE pState, PVMSVGA3DSURFACE pSurface);
     1054int  vmsvga3dBackSurfaceStretchBlt(PVGASTATE pThis, PVMSVGA3DSTATE pState,
     1055                                   PVMSVGA3DSURFACE pDstSurface, uint32_t uDstMipmap, SVGA3dBox const *pDstBox,
     1056                                   PVMSVGA3DSURFACE pSrcSurface, uint32_t uSrcMipmap, SVGA3dBox const *pSrcBox,
     1057                                   SVGA3dStretchBltMode enmMode, PVMSVGA3DCONTEXT pContext);
     1058int  vmsvga3dBackSurfaceDMACopyBox(PVGASTATE pThis, PVMSVGA3DSTATE pState, PVMSVGA3DSURFACE pSurface, uint32_t uHostMimap,
     1059                                   SVGAGuestPtr GuestPtr, uint32_t cbSrcPitch, SVGA3dTransferType transfer,
     1060                                   SVGA3dCopyBox const *pBox, PVMSVGA3DCONTEXT pContext, int rc, int iBox);
     1061
     1062int  vmsvga3dBackCreateTexture(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, uint32_t idAssociatedContext,
     1063                               PVMSVGA3DSURFACE pSurface);
     1064
     1065#endif
     1066
  • trunk/src/VBox/Devices/Graphics/DevVGA-SVGA3d-ogl.cpp

    r57149 r57151  
    161161*   Internal Functions                                                         *
    162162*******************************************************************************/
    163 static int  vmsvga3dCreateTexture(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, uint32_t idAssociatedContext, PVMSVGA3DSURFACE pSurface);
    164163static int  vmsvga3dContextDestroyOgl(PVGASTATE pThis, PVMSVGA3DCONTEXT pContext, uint32_t cid);
    165164static void vmsvgaColor2GLFloatArray(uint32_t color, GLfloat *pRed, GLfloat *pGreen, GLfloat *pBlue, GLfloat *pAlpha);
     
    14871486 *           help from wined3dformat_from_d3dformat().
    14881487 */
    1489 static void vmsvga3dSurfaceFormat2OGL(PVMSVGA3DSURFACE pSurface, SVGA3dSurfaceFormat format)
     1488void vmsvga3dSurfaceFormat2OGL(PVMSVGA3DSURFACE pSurface, SVGA3dSurfaceFormat format)
    14901489{
    14911490    switch (format)
     
    18111810#endif
    18121811
    1813 int vmsvga3dSurfaceDefine(PVGASTATE pThis, uint32_t sid, uint32_t surfaceFlags, SVGA3dSurfaceFormat format,
    1814                           SVGA3dSurfaceFace face[SVGA3D_MAX_SURFACE_FACES], uint32_t multisampleCount,
    1815                           SVGA3dTextureFilter autogenFilter, uint32_t cMipLevels, SVGA3dSize *pMipLevelSize)
    1816 {
    1817     PVMSVGA3DSURFACE pSurface;
    1818     PVMSVGA3DSTATE   pState = pThis->svga.p3dState;
    1819     AssertReturn(pState, VERR_NO_MEMORY);
    1820 
    1821     Log(("vmsvga3dSurfaceDefine: sid=%x surfaceFlags=%x format=%s (%x) multiSampleCount=%d autogenFilter=%d, cMipLevels=%d size=(%d,%d,%d)\n",
    1822          sid, surfaceFlags, vmsvgaLookupEnum((int)format, &g_SVGA3dSurfaceFormat2String), format, multisampleCount, autogenFilter, cMipLevels, pMipLevelSize->width, pMipLevelSize->height, pMipLevelSize->depth));
    1823 
    1824     AssertReturn(sid < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
    1825     AssertReturn(cMipLevels >= 1, VERR_INVALID_PARAMETER);
    1826     /* Assuming all faces have the same nr of mipmaps. */
    1827     AssertReturn(!(surfaceFlags & SVGA3D_SURFACE_CUBEMAP) || cMipLevels == face[0].numMipLevels * 6, VERR_INVALID_PARAMETER);
    1828     AssertReturn((surfaceFlags & SVGA3D_SURFACE_CUBEMAP) || cMipLevels == face[0].numMipLevels, VERR_INVALID_PARAMETER);
    1829 
    1830     if (sid >= pState->cSurfaces)
    1831     {
    1832         /* Grow the array. */
    1833         uint32_t cNew = RT_ALIGN(sid + 15, 16);
    1834         void *pvNew = RTMemRealloc(pState->papSurfaces, sizeof(pState->papSurfaces[0]) * cNew);
    1835         AssertReturn(pvNew, VERR_NO_MEMORY);
    1836         pState->papSurfaces = (PVMSVGA3DSURFACE *)pvNew;
    1837         while (pState->cSurfaces < cNew)
    1838         {
    1839             pSurface = (PVMSVGA3DSURFACE)RTMemAllocZ(sizeof(*pSurface));
    1840             AssertReturn(pSurface, VERR_NO_MEMORY);
    1841             pSurface->id = SVGA3D_INVALID_ID;
    1842             pState->papSurfaces[pState->cSurfaces++] = pSurface;
    1843         }
    1844     }
    1845     pSurface = pState->papSurfaces[sid];
    1846 
    1847     /* If one already exists with this id, then destroy it now. */
    1848     if (pSurface->id != SVGA3D_INVALID_ID)
    1849         vmsvga3dSurfaceDestroy(pThis, sid);
    1850 
    1851     memset(pSurface, 0, sizeof(*pSurface));
    1852     pSurface->id                    = sid;
    1853 #ifdef VMSVGA3D_OGL_WITH_SHARED_CTX
    1854     pSurface->idWeakContextAssociation = SVGA3D_INVALID_ID;
     1812/**
     1813 * Destroy backend specific surface bits (part of SVGA_3D_CMD_SURFACE_DESTROY).
     1814 *
     1815 * @param   pState              The VMSVGA3d state.
     1816 * @param   pSurface            The surface being destroyed.
     1817 */
     1818void vmsvga3dBackSurfaceDestroy(PVMSVGA3DSTATE pState, PVMSVGA3DSURFACE pSurface)
     1819{
     1820#if defined(VMSVGA3D_OGL_WITH_SHARED_CTX)
     1821    PVMSVGA3DCONTEXT pContext = &pState->SharedCtx;
     1822    VMSVGA3D_SET_CURRENT_CONTEXT(pState, pContext);
    18551823#else
    1856     pSurface->idAssociatedContext   = SVGA3D_INVALID_ID;
    1857 #endif
    1858     vmsvga3dSurfaceFormat2OGL(pSurface, format);
    1859 
    1860     pSurface->oglId.buffer = OPENGL_INVALID_ID;
    1861 
    1862     /* The surface type is sort of undefined now, even though the hints and format can help to clear that up.
    1863      * In some case we'll have to wait until the surface is used to create the D3D object.
    1864      */
    1865     switch (format)
    1866     {
    1867     case SVGA3D_Z_D32:
    1868     case SVGA3D_Z_D16:
    1869     case SVGA3D_Z_D24S8:
    1870     case SVGA3D_Z_D15S1:
    1871     case SVGA3D_Z_D24X8:
    1872     case SVGA3D_Z_DF16:
    1873     case SVGA3D_Z_DF24:
    1874     case SVGA3D_Z_D24S8_INT:
    1875         surfaceFlags |= SVGA3D_SURFACE_HINT_DEPTHSTENCIL;
    1876         break;
    1877 
    1878     /* Texture compression formats */
    1879     case SVGA3D_DXT1:
    1880     case SVGA3D_DXT2:
    1881     case SVGA3D_DXT3:
    1882     case SVGA3D_DXT4:
    1883     case SVGA3D_DXT5:
    1884     /* Bump-map formats */
    1885     case SVGA3D_BUMPU8V8:
    1886     case SVGA3D_BUMPL6V5U5:
    1887     case SVGA3D_BUMPX8L8V8U8:
    1888     case SVGA3D_BUMPL8V8U8:
    1889     case SVGA3D_V8U8:
    1890     case SVGA3D_Q8W8V8U8:
    1891     case SVGA3D_CxV8U8:
    1892     case SVGA3D_X8L8V8U8:
    1893     case SVGA3D_A2W10V10U10:
    1894     case SVGA3D_V16U16:
    1895     /* Typical render target formats; we should allow render target buffers to be used as textures. */
    1896     case SVGA3D_X8R8G8B8:
    1897     case SVGA3D_A8R8G8B8:
    1898     case SVGA3D_R5G6B5:
    1899     case SVGA3D_X1R5G5B5:
    1900     case SVGA3D_A1R5G5B5:
    1901     case SVGA3D_A4R4G4B4:
    1902         surfaceFlags |= SVGA3D_SURFACE_HINT_TEXTURE;
    1903         break;
    1904 
    1905     case SVGA3D_LUMINANCE8:
    1906     case SVGA3D_LUMINANCE4_ALPHA4:
    1907     case SVGA3D_LUMINANCE16:
    1908     case SVGA3D_LUMINANCE8_ALPHA8:
    1909     case SVGA3D_ARGB_S10E5:   /* 16-bit floating-point ARGB */
    1910     case SVGA3D_ARGB_S23E8:   /* 32-bit floating-point ARGB */
    1911     case SVGA3D_A2R10G10B10:
    1912     case SVGA3D_ALPHA8:
    1913     case SVGA3D_R_S10E5:
    1914     case SVGA3D_R_S23E8:
    1915     case SVGA3D_RG_S10E5:
    1916     case SVGA3D_RG_S23E8:
    1917     case SVGA3D_G16R16:
    1918     case SVGA3D_A16B16G16R16:
    1919     case SVGA3D_UYVY:
    1920     case SVGA3D_YUY2:
    1921     case SVGA3D_NV12:
    1922     case SVGA3D_AYUV:
    1923     case SVGA3D_BC4_UNORM:
    1924     case SVGA3D_BC5_UNORM:
    1925         break;
    1926 
    1927     /*
    1928      * Any surface can be used as a buffer object, but SVGA3D_BUFFER is
    1929      * the most efficient format to use when creating new surfaces
    1930      * expressly for index or vertex data.
    1931      */
    1932     case SVGA3D_BUFFER:
     1824    /** @todo stricter checks for associated context */
     1825    PVMSVGA3DCONTEXT pContext;
     1826    uint32_t cid = pSurface->idAssociatedContext;
     1827    if (    cid <= pState->cContexts
     1828        &&  pState->papContexts[cid]->id == cid)
     1829    {
     1830        pContext = pState->papContexts[cid];
     1831        VMSVGA3D_SET_CURRENT_CONTEXT(pState, pContext);
     1832    }
     1833    /* If there is a GL buffer or something associated with the surface, we
     1834       really need something here, so pick any active context. */
     1835    else if (pSurface->oglId.buffer != OPENGL_INVALID_ID)
     1836    {
     1837        for (cid = 0; cid < pState->cContexts; cid++)
     1838        {
     1839            if (pState->papContexts[cid]->id == cid)
     1840            {
     1841                pContext = pState->papContexts[cid];
     1842                VMSVGA3D_SET_CURRENT_CONTEXT(pState, pContext);
     1843                break;
     1844            }
     1845        }
     1846        AssertReturn(pContext, VERR_INTERNAL_ERROR); /* otherwise crashes/fails; create temp context if this ever triggers! */
     1847    }
     1848#endif
     1849
     1850    switch (pSurface->flags & VMSVGA3D_SURFACE_HINT_SWITCH_MASK)
     1851    {
     1852    case SVGA3D_SURFACE_CUBEMAP:
     1853        AssertFailed(); /** @todo */
     1854        break;
     1855
     1856    case SVGA3D_SURFACE_HINT_INDEXBUFFER:
     1857    case SVGA3D_SURFACE_HINT_VERTEXBUFFER:
     1858        if (pSurface->oglId.buffer != OPENGL_INVALID_ID)
     1859        {
     1860            pState->ext.glDeleteBuffers(1, &pSurface->oglId.buffer);
     1861            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     1862        }
     1863        break;
     1864
     1865    case SVGA3D_SURFACE_HINT_TEXTURE:
     1866    case SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET:
     1867        if (pSurface->oglId.texture != OPENGL_INVALID_ID)
     1868        {
     1869            glDeleteTextures(1, &pSurface->oglId.texture);
     1870            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     1871        }
     1872        break;
     1873
     1874    case SVGA3D_SURFACE_HINT_RENDERTARGET:
     1875    case SVGA3D_SURFACE_HINT_DEPTHSTENCIL:
     1876    case SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_HINT_TEXTURE:    /** @todo actual texture surface not supported */
     1877        if (pSurface->oglId.renderbuffer != OPENGL_INVALID_ID)
     1878        {
     1879            pState->ext.glDeleteRenderbuffers(1, &pSurface->oglId.renderbuffer);
     1880            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     1881        }
    19331882        break;
    19341883
    19351884    default:
    1936         break;
    1937     }
    1938 
    1939     pSurface->flags             = surfaceFlags;
    1940     pSurface->format            = format;
    1941     memcpy(pSurface->faces, face, sizeof(pSurface->faces));
    1942     pSurface->cFaces            = 1;        /* check for cube maps later */
    1943     pSurface->multiSampleCount  = multisampleCount;
    1944     pSurface->autogenFilter     = autogenFilter;
    1945     Assert(autogenFilter != SVGA3D_TEX_FILTER_FLATCUBIC);
    1946     Assert(autogenFilter != SVGA3D_TEX_FILTER_GAUSSIANCUBIC);
    1947     pSurface->pMipmapLevels     = (PVMSVGA3DMIPMAPLEVEL)RTMemAllocZ(cMipLevels * sizeof(VMSVGA3DMIPMAPLEVEL));
    1948     AssertReturn(pSurface->pMipmapLevels, VERR_NO_MEMORY);
    1949 
    1950     for (uint32_t i=0; i < cMipLevels; i++)
    1951         pSurface->pMipmapLevels[i].size = pMipLevelSize[i];
    1952 
    1953     pSurface->cbBlock = vmsvga3dSurfaceFormatSize(format);
    1954 
    1955     switch (surfaceFlags & (SVGA3D_SURFACE_HINT_INDEXBUFFER | SVGA3D_SURFACE_HINT_VERTEXBUFFER | SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET | SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_CUBEMAP))
    1956     {
    1957     case SVGA3D_SURFACE_CUBEMAP:
    1958         Log(("SVGA3D_SURFACE_CUBEMAP\n"));
    1959         pSurface->cFaces = 6;
    1960         break;
    1961 
    1962     case SVGA3D_SURFACE_HINT_INDEXBUFFER:
    1963         Log(("SVGA3D_SURFACE_HINT_INDEXBUFFER\n"));
    1964         /* else type unknown at this time; postpone buffer creation */
    1965         break;
    1966 
    1967     case SVGA3D_SURFACE_HINT_VERTEXBUFFER:
    1968         Log(("SVGA3D_SURFACE_HINT_VERTEXBUFFER\n"));
    1969         /* Type unknown at this time; postpone buffer creation */
    1970         break;
    1971 
    1972     case SVGA3D_SURFACE_HINT_TEXTURE:
    1973         Log(("SVGA3D_SURFACE_HINT_TEXTURE\n"));
    1974         break;
    1975 
    1976     case SVGA3D_SURFACE_HINT_RENDERTARGET:
    1977         Log(("SVGA3D_SURFACE_HINT_RENDERTARGET\n"));
    1978         break;
    1979 
    1980     case SVGA3D_SURFACE_HINT_DEPTHSTENCIL:
    1981         Log(("SVGA3D_SURFACE_HINT_DEPTHSTENCIL\n"));
    1982         break;
    1983 
    1984     default:
    1985         /* Unknown; decide later. */
    1986         break;
    1987     }
    1988 
    1989     /* Allocate buffer to hold the surface data until we can move it into a D3D object */
    1990     for (uint32_t iFace=0; iFace < pSurface->cFaces; iFace++)
    1991     {
    1992         for (uint32_t i=0; i < pSurface->faces[iFace].numMipLevels; i++)
    1993         {
    1994             uint32_t idx = i + iFace * pSurface->faces[0].numMipLevels;
    1995 
    1996             Log(("vmsvga3dSurfaceDefine: face %d mip level %d (%d,%d,%d)\n", iFace, i, pSurface->pMipmapLevels[idx].size.width, pSurface->pMipmapLevels[idx].size.height, pSurface->pMipmapLevels[idx].size.depth));
    1997             Log(("vmsvga3dSurfaceDefine: cbPitch=%x cbBlock=%x \n", pSurface->cbBlock * pSurface->pMipmapLevels[idx].size.width, pSurface->cbBlock));
    1998 
    1999             pSurface->pMipmapLevels[idx].cbSurfacePitch = pSurface->cbBlock * pSurface->pMipmapLevels[idx].size.width;
    2000             pSurface->pMipmapLevels[idx].cbSurface      = pSurface->pMipmapLevels[idx].cbSurfacePitch * pSurface->pMipmapLevels[idx].size.height * pSurface->pMipmapLevels[idx].size.depth;
    2001             pSurface->pMipmapLevels[idx].pSurfaceData   = RTMemAllocZ(pSurface->pMipmapLevels[idx].cbSurface);
    2002             AssertReturn(pSurface->pMipmapLevels[idx].pSurfaceData, VERR_NO_MEMORY);
    2003         }
    2004     }
    2005     return VINF_SUCCESS;
    2006 }
    2007 
    2008 int vmsvga3dSurfaceDestroy(PVGASTATE pThis, uint32_t sid)
    2009 {
    2010     PVMSVGA3DSTATE pState = pThis->svga.p3dState;
    2011     AssertReturn(pState, VERR_NO_MEMORY);
    2012 
    2013     if (    sid < pState->cSurfaces
    2014         &&  pState->papSurfaces[sid]->id == sid)
    2015     {
    2016         PVMSVGA3DSURFACE pSurface = pState->papSurfaces[sid];
    2017         PVMSVGA3DCONTEXT pContext;
    2018 
    2019         Log(("vmsvga3dSurfaceDestroy id %x\n", sid));
    2020 
    2021 #if 1 /* Windows is doing this, guess it makes sense here as well... */
    2022         /* Check all contexts if this surface is used as a render target or active texture. */
    2023         for (uint32_t cid = 0; cid < pState->cContexts; cid++)
    2024         {
    2025             pContext = pState->papContexts[cid];
    2026             if (pContext->id == cid)
    2027             {
    2028                 for (uint32_t i = 0; i < RT_ELEMENTS(pContext->aSidActiveTexture); i++)
    2029                     if (pContext->aSidActiveTexture[i] == sid)
    2030                         pContext->aSidActiveTexture[i] = SVGA3D_INVALID_ID;
    2031                 if (pContext->sidRenderTarget == sid)
    2032                     pContext->sidRenderTarget = SVGA3D_INVALID_ID;
    2033             }
    2034         }
    2035 #endif
    2036 
    2037 #ifdef VMSVGA3D_OGL_WITH_SHARED_CTX
    2038         pContext = &pState->SharedCtx;
    2039         VMSVGA3D_SET_CURRENT_CONTEXT(pState, pContext);
    2040 #else
    2041         /* @todo stricter checks for associated context */
    2042         uint32_t cid = pSurface->idAssociatedContext;
    2043         if (    cid <= pState->cContexts
    2044             &&  pState->papContexts[cid]->id == cid)
    2045         {
    2046             pContext = pState->papContexts[cid];
    2047             VMSVGA3D_SET_CURRENT_CONTEXT(pState, pContext);
    2048         }
    2049         /* If there is a GL buffer or something associated with the surface, we
    2050            really need something here, so pick any active context. */
    2051         else if (pSurface->oglId.buffer != OPENGL_INVALID_ID)
    2052         {
    2053             for (cid = 0; cid < pState->cContexts; cid++)
    2054             {
    2055                 if (pState->papContexts[cid]->id == cid)
    2056                 {
    2057                     pContext = pState->papContexts[cid];
    2058                     VMSVGA3D_SET_CURRENT_CONTEXT(pState, pContext);
    2059                     break;
    2060                 }
    2061             }
    2062             AssertReturn(pContext, VERR_INTERNAL_ERROR); /* otherwise crashes/fails; create temp context if this ever triggers! */
    2063         }
    2064 #endif
    2065 
    2066         switch (pSurface->flags & (SVGA3D_SURFACE_HINT_INDEXBUFFER | SVGA3D_SURFACE_HINT_VERTEXBUFFER | SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET | SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_CUBEMAP))
    2067         {
    2068         case SVGA3D_SURFACE_CUBEMAP:
    2069             AssertFailed(); /* @todo */
    2070             break;
    2071 
    2072         case SVGA3D_SURFACE_HINT_INDEXBUFFER:
    2073         case SVGA3D_SURFACE_HINT_VERTEXBUFFER:
    2074             if (pSurface->oglId.buffer != OPENGL_INVALID_ID)
    2075             {
    2076                 pState->ext.glDeleteBuffers(1, &pSurface->oglId.buffer);
    2077                 VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
    2078             }
    2079             break;
    2080 
    2081         case SVGA3D_SURFACE_HINT_TEXTURE:
    2082         case SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET:
    2083             if (pSurface->oglId.texture != OPENGL_INVALID_ID)
    2084             {
    2085                 glDeleteTextures(1, &pSurface->oglId.texture);
    2086                 VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
    2087             }
    2088             break;
    2089 
    2090         case SVGA3D_SURFACE_HINT_RENDERTARGET:
    2091         case SVGA3D_SURFACE_HINT_DEPTHSTENCIL:
    2092         case SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_HINT_TEXTURE:    /* @todo actual texture surface not supported */
    2093             if (pSurface->oglId.renderbuffer != OPENGL_INVALID_ID)
    2094             {
    2095                 pState->ext.glDeleteRenderbuffers(1, &pSurface->oglId.renderbuffer);
    2096                 VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
    2097             }
    2098             break;
    2099 
    2100         default:
    2101             break;
    2102         }
    2103 
    2104         if (pSurface->pMipmapLevels)
    2105         {
    2106             for (uint32_t face=0; face < pSurface->cFaces; face++)
    2107             {
    2108                 for (uint32_t i=0; i < pSurface->faces[face].numMipLevels; i++)
    2109                 {
    2110                     uint32_t idx = i + face * pSurface->faces[0].numMipLevels;
    2111                     if (pSurface->pMipmapLevels[idx].pSurfaceData)
    2112                         RTMemFree(pSurface->pMipmapLevels[idx].pSurfaceData);
    2113                 }
    2114             }
    2115             RTMemFree(pSurface->pMipmapLevels);
    2116         }
    2117 
    2118         memset(pSurface, 0, sizeof(*pSurface));
    2119         pSurface->id = SVGA3D_INVALID_ID;
    2120     }
    2121     else
    2122         AssertFailedReturn(VERR_INVALID_PARAMETER);
    2123 
    2124     return VINF_SUCCESS;
    2125 }
     1885        AssertMsg(!VMSVGA3DSURFACE_HAS_HW_SURFACE(pSurface), ("type=%x\n", (pSurface->flags & VMSVGA3D_SURFACE_HINT_SWITCH_MASK)));
     1886        break;
     1887    }
     1888}
     1889
    21261890
    21271891int vmsvga3dSurfaceCopy(PVGASTATE pThis, SVGA3dSurfaceImageId dest, SVGA3dSurfaceImageId src, uint32_t cCopyBoxes, SVGA3dCopyBox *pBox)
     
    21331897
    21341898    AssertReturn(pState, VERR_NO_MEMORY);
    2135     AssertReturn(sidSrc < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
     1899    Assert(sidSrc < SVGA3D_MAX_SURFACE_IDS);
    21361900    AssertReturn(sidSrc < pState->cSurfaces && pState->papSurfaces[sidSrc]->id == sidSrc, VERR_INVALID_PARAMETER);
    2137     AssertReturn(sidDest < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
     1901    Assert(sidDest < SVGA3D_MAX_SURFACE_IDS);
    21381902    AssertReturn(sidDest < pState->cSurfaces && pState->papSurfaces[sidDest]->id == sidDest, VERR_INVALID_PARAMETER);
    21391903
     
    21561920        destBox.z = pBox[i].z; /* XXX initializing destBox.z again? What about pBox[i].d and destBox.d? */
    21571921
    2158         rc = vmsvga3dSurfaceStretchBlt(pThis, dest, destBox, src, srcBox, SVGA3D_STRETCH_BLT_LINEAR);
     1922        rc = vmsvga3dSurfaceStretchBlt(pThis, &dest, &destBox, &src, &srcBox, SVGA3D_STRETCH_BLT_LINEAR);
    21591923        AssertRCReturn(rc, rc);
    21601924    }
     
    21721936 * @param   pSave               Where to save stuff.
    21731937 */
    2174 static void vmsvga3dSetUnpackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
    2175                                     PVMSVGAPACKPARAMS pSave)
     1938void vmsvga3dOglSetUnpackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
     1939                                PVMSVGAPACKPARAMS pSave)
    21761940{
    21771941    /*
     
    22472011 * @param   pSave               Where stuff was saved.
    22482012 */
    2249 static void vmsvga3dRestoreUnpackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
    2250                                         PCVMSVGAPACKPARAMS pSave)
     2013void vmsvga3dOglRestoreUnpackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
     2014                                    PCVMSVGAPACKPARAMS pSave)
    22512015{
    22522016    NOREF(pSurface);
     
    22722036
    22732037
    2274 /* Create D3D texture object for the specified surface. */
    2275 static int vmsvga3dCreateTexture(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, uint32_t idAssociatedContext,
    2276                                  PVMSVGA3DSURFACE pSurface)
     2038/**
     2039 * Create D3D/OpenGL texture object for the specified surface.
     2040 *
     2041 * Surfaces are created when needed.
     2042 *
     2043 * @param   pState              The VMSVGA3d state.
     2044 * @param   pContext            The context.
     2045 * @param   idAssociatedContext Probably the same as pContext->id.
     2046 * @param   pSurface            The surface to create the texture for.
     2047 */
     2048int vmsvga3dBackCreateTexture(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, uint32_t idAssociatedContext,
     2049                              PVMSVGA3DSURFACE pSurface)
    22772050{
    22782051    GLint activeTexture = 0;
     
    22962069    /* Set the unpacking parameters. */
    22972070    VMSVGAPACKPARAMS SavedParams;
    2298     vmsvga3dSetUnpackParams(pState, pContext, pSurface, &SavedParams);
     2071    vmsvga3dOglSetUnpackParams(pState, pContext, pSurface, &SavedParams);
    22992072
    23002073    /* Set the mipmap base and max level paramters. */
     
    23052078
    23062079    if (pSurface->fDirty)
    2307         Log(("vmsvga3dCreateTexture: sync dirty texture\n"));
     2080        Log(("vmsvga3dBackCreateTexture: sync dirty texture\n"));
    23082081
    23092082    /* Always allocate and initialize all mipmap levels; non-initialized mipmap levels used as render targets cause failures. */
     
    23142087            corruption issues (launchpad, background, search field, login). */
    23152088        if (pSurface->pMipmapLevels[i].fDirty)
    2316             Log(("vmsvga3dCreateTexture: sync dirty texture mipmap level %d (pitch %x)\n", i, pSurface->pMipmapLevels[i].cbSurfacePitch));
     2089            Log(("vmsvga3dBackCreateTexture: sync dirty texture mipmap level %d (pitch %x)\n", i, pSurface->pMipmapLevels[i].cbSurfacePitch));
    23172090
    23182091        glTexImage2D(GL_TEXTURE_2D,
     
    23332106
    23342107    /* Restore unpacking parameters. */
    2335     vmsvga3dRestoreUnpackParams(pState, pContext, pSurface, &SavedParams);
     2108    vmsvga3dOglRestoreUnpackParams(pState, pContext, pSurface, &SavedParams);
    23362109
    23372110    /* Restore the old active texture. */
     
    23412114    pSurface->flags              |= SVGA3D_SURFACE_HINT_TEXTURE;
    23422115#ifndef VMSVGA3D_OGL_WITH_SHARED_CTX
    2343     LogFlow(("vmsvga3dCreateTexture: sid=%x idAssociatedContext %#x -> %#x; oglId.texture=%#x\n",
     2116    LogFlow(("vmsvga3dBackCreateTexture: sid=%x idAssociatedContext %#x -> %#x; oglId.texture=%#x\n",
    23442117             pSurface->id, pSurface->idAssociatedContext, idAssociatedContext, pSurface->oglId.texture));
    23452118    pSurface->idAssociatedContext = idAssociatedContext;
     
    23532126}
    23542127
    2355 int vmsvga3dSurfaceStretchBlt(PVGASTATE pThis, SVGA3dSurfaceImageId dest, SVGA3dBox destBox,
    2356                               SVGA3dSurfaceImageId src, SVGA3dBox srcBox, SVGA3dStretchBltMode mode)
    2357 {
    2358     PVMSVGA3DSTATE      pState = pThis->svga.p3dState;
    2359     PVMSVGA3DSURFACE    pSurfaceSrc;
    2360     uint32_t            sidSrc = src.sid;
    2361     PVMSVGA3DSURFACE    pSurfaceDest;
    2362     uint32_t            sidDest = dest.sid;
    2363     int                 rc = VINF_SUCCESS;
    2364     uint32_t            cid;
    2365     PVMSVGA3DCONTEXT    pContext;
    2366 
    2367     AssertReturn(pState, VERR_NO_MEMORY);
    2368     AssertReturn(sidSrc < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
    2369     AssertReturn(sidSrc < pState->cSurfaces && pState->papSurfaces[sidSrc]->id == sidSrc, VERR_INVALID_PARAMETER);
    2370     AssertReturn(sidDest < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
    2371     AssertReturn(sidDest < pState->cSurfaces && pState->papSurfaces[sidDest]->id == sidDest, VERR_INVALID_PARAMETER);
    2372 
    2373     pSurfaceSrc  = pState->papSurfaces[sidSrc];
    2374     pSurfaceDest = pState->papSurfaces[sidDest];
    2375     AssertReturn(pSurfaceSrc->faces[0].numMipLevels > src.mipmap, VERR_INVALID_PARAMETER);
    2376     AssertReturn(pSurfaceDest->faces[0].numMipLevels > dest.mipmap, VERR_INVALID_PARAMETER);
    2377 
    2378 #ifdef VMSVGA3D_OGL_WITH_SHARED_CTX
    2379     Log(("vmsvga3dSurfaceStretchBlt: src sid=%x (%d,%d)(%d,%d) dest sid=%x (%d,%d)(%d,%d) mode=%x\n",
    2380          src.sid, srcBox.x, srcBox.y, srcBox.x + srcBox.w, srcBox.y + srcBox.h,
    2381          dest.sid, destBox.x, destBox.y, destBox.x + destBox.w, destBox.y + destBox.h, mode));
    2382     cid = SVGA3D_INVALID_ID;
    2383     pContext = &pState->SharedCtx;
    2384     VMSVGA3D_SET_CURRENT_CONTEXT(pState, pContext);
    2385 #else
    2386     Log(("vmsvga3dSurfaceStretchBlt: src sid=%x cid=%x (%d,%d)(%d,%d) dest sid=%x cid=%x (%d,%d)(%d,%d) mode=%x\n",
    2387          src.sid, pSurfaceSrc->idAssociatedContext, srcBox.x, srcBox.y, srcBox.x + srcBox.w, srcBox.y + srcBox.h,
    2388          dest.sid, pSurfaceDest->idAssociatedContext, destBox.x, destBox.y, destBox.x + destBox.w, destBox.y + destBox.h, mode));
    2389 
    2390     /* @todo stricter checks for associated context */
    2391     cid = pSurfaceDest->idAssociatedContext;
    2392     if (cid == SVGA3D_INVALID_ID)
    2393         cid = pSurfaceSrc->idAssociatedContext;
    2394 
    2395     if (    cid >= pState->cContexts
    2396         ||  pState->papContexts[cid]->id != cid)
    2397     {
    2398         Log(("vmsvga3dSurfaceStretchBlt invalid context id!\n"));
    2399         AssertFailedReturn(VERR_INVALID_PARAMETER);
    2400     }
    2401     pContext = pState->papContexts[cid];
    2402     VMSVGA3D_SET_CURRENT_CONTEXT(pState, pContext);
    2403 #endif
    2404 
    2405     if (pSurfaceSrc->oglId.texture == OPENGL_INVALID_ID)
    2406     {
    2407         /* Unknown surface type; turn it into a texture, which can be used for other purposes too. */
    2408         Log(("vmsvga3dSurfaceStretchBlt: unknown src surface id=%x type=%d format=%d -> create texture\n", sidSrc, pSurfaceSrc->flags, pSurfaceSrc->format));
    2409         rc = vmsvga3dCreateTexture(pState, pContext, cid, pSurfaceSrc);
    2410         AssertRCReturn(rc, rc);
    2411     }
    2412 
    2413     if (pSurfaceDest->oglId.texture == OPENGL_INVALID_ID)
    2414     {
    2415         /* Unknown surface type; turn it into a texture, which can be used for other purposes too. */
    2416         Log(("vmsvga3dSurfaceStretchBlt: unknown dest surface id=%x type=%d format=%d -> create texture\n", sidDest, pSurfaceDest->flags, pSurfaceDest->format));
    2417         rc = vmsvga3dCreateTexture(pState, pContext, cid, pSurfaceDest);
    2418         AssertRCReturn(rc, rc);
    2419     }
    2420 
     2128
     2129/**
     2130 * Backend worker for implementing SVGA_3D_CMD_SURFACE_STRETCHBLT.
     2131 *
     2132 * @returns VBox status code.
     2133 * @param   pThis               The VGA device instance.
     2134 * @param   pState              The VMSVGA3d state.
     2135 * @param   pDstSurface         The destination host surface.
     2136 * @param   uDstMipmap          The destination mipmap level (valid).
     2137 * @param   pDstBox             The destination box.
     2138 * @param   pSrcSurface         The source host surface.
     2139 * @param   uSrcMipmap          The source mimap level (valid).
     2140 * @param   pSrcBox             The source box.
     2141 * @param   enmMode             The strecht blt mode .
     2142 * @param   pContext            The VMSVGA3d context (already current for OGL).
     2143 */
     2144int vmsvga3dBackSurfaceStretchBlt(PVGASTATE pThis, PVMSVGA3DSTATE pState,
     2145                                  PVMSVGA3DSURFACE pDstSurface, uint32_t uDstMipmap, SVGA3dBox const *pDstBox,
     2146                                  PVMSVGA3DSURFACE pSrcSurface, uint32_t uSrcMipmap, SVGA3dBox const *pSrcBox,
     2147                                  SVGA3dStretchBltMode enmMode, PVMSVGA3DCONTEXT pContext)
     2148{
    24212149    /* Activate the read and draw framebuffer objects. */
    24222150    pState->ext.glBindFramebuffer(GL_READ_FRAMEBUFFER, pContext->idReadFramebuffer);
     
    24272155    /* Bind the source and destination objects to the right place. */
    24282156    pState->ext.glFramebufferTexture2D(GL_READ_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D,
    2429                                        pSurfaceSrc->oglId.texture, src.mipmap);
     2157                                       pSrcSurface->oglId.texture, uSrcMipmap);
    24302158    VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
    24312159    pState->ext.glFramebufferTexture2D(GL_DRAW_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D,
    2432                                        pSurfaceDest->oglId.texture, dest.mipmap);
     2160                                       pDstSurface->oglId.texture, uDstMipmap);
    24332161    VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
    24342162
    2435     Log(("src conv. (%d,%d)(%d,%d); dest conv (%d,%d)(%d,%d)\n", srcBox.x, D3D_TO_OGL_Y_COORD(pSurfaceSrc, srcBox.y + srcBox.h),
    2436          srcBox.x + srcBox.w, D3D_TO_OGL_Y_COORD(pSurfaceSrc, srcBox.y), destBox.x, D3D_TO_OGL_Y_COORD(pSurfaceDest, destBox.y + destBox.h),
    2437          destBox.x + destBox.w, D3D_TO_OGL_Y_COORD(pSurfaceDest, destBox.y)));
    2438 
    2439     pState->ext.glBlitFramebuffer(srcBox.x,
     2163    Log(("src conv. (%d,%d)(%d,%d); dest conv (%d,%d)(%d,%d)\n", pSrcBox->x, D3D_TO_OGL_Y_COORD(pSrcSurface, pSrcBox->y + pSrcBox->h),
     2164         pSrcBox->x + pSrcBox->w, D3D_TO_OGL_Y_COORD(pSrcSurface, pSrcBox->y), pDstBox->x, D3D_TO_OGL_Y_COORD(pDstSurface, pDstBox->y + pDstBox->h),
     2165         pDstBox->x + pDstBox->w, D3D_TO_OGL_Y_COORD(pDstSurface, pDstBox->y)));
     2166
     2167    pState->ext.glBlitFramebuffer(pSrcBox->x,
    24402168#ifdef MANUAL_FLIP_SURFACE_DATA
    2441                                   D3D_TO_OGL_Y_COORD(pSurfaceSrc, srcBox.y + srcBox.h),    /* inclusive */
     2169                                  D3D_TO_OGL_Y_COORD(pSrcSurface, pSrcBox->y + pSrcBox->h), /* inclusive */
    24422170#else
    2443                                   srcBox.y,
    2444 #endif
    2445                                   srcBox.x + srcBox.w,                                      /* exclusive. */
     2171                                  pSrcBox->y,
     2172#endif
     2173                                  pSrcBox->x + pSrcBox->w,                                  /* exclusive. */
    24462174#ifdef MANUAL_FLIP_SURFACE_DATA
    2447                                   D3D_TO_OGL_Y_COORD(pSurfaceSrc, srcBox.y),                /* exclusive */
     2175                                  D3D_TO_OGL_Y_COORD(pSrcSurface, pSrcBox->y),              /* exclusive */
    24482176#else
    2449                                   srcBox.y + srcBox.h,
    2450 #endif
    2451                                   destBox.x,
     2177                                  pSrcBox->y + pSrcBox->h,
     2178#endif
     2179                                  pDstBox->x,
    24522180#ifdef MANUAL_FLIP_SURFACE_DATA
    2453                                   D3D_TO_OGL_Y_COORD(pSurfaceDest, destBox.y + destBox.h), /* inclusive. */
     2181                                  D3D_TO_OGL_Y_COORD(pDstSurface, pDstBox->y + pDstBox->h), /* inclusive. */
    24542182#else
    2455                                   destBox.y,
    2456 #endif
    2457                                   destBox.x + destBox.w,                                    /* exclusive. */
     2183                                  pDstBox->y,
     2184#endif
     2185                                  pDstBox->x + pDstBox->w,                                  /* exclusive. */
    24582186#ifdef MANUAL_FLIP_SURFACE_DATA
    2459                                   D3D_TO_OGL_Y_COORD(pSurfaceDest, destBox.y),              /* exclusive */
     2187                                  D3D_TO_OGL_Y_COORD(pDstSurface, pDstBox->y),              /* exclusive */
    24602188#else
    2461                                   destBox.y + destBox.h,
     2189                                  pDstBox->y + pDstBox->h,
    24622190#endif
    24632191                                  GL_COLOR_BUFFER_BIT,
    2464                                   (mode == SVGA3D_STRETCH_BLT_POINT) ? GL_NEAREST : GL_LINEAR);
     2192                                  (enmMode == SVGA3D_STRETCH_BLT_POINT) ? GL_NEAREST : GL_LINEAR);
    24652193    VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
    24662194
     
    24812209 * @param   pSave               Where to save stuff.
    24822210 */
    2483 void vmsvga3dSetPackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface, PVMSVGAPACKPARAMS pSave)
     2211void vmsvga3dOglSetPackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
     2212                              PVMSVGAPACKPARAMS pSave)
    24842213{
    24852214    /*
     
    25552284 * @param   pSave               Where stuff was saved.
    25562285 */
    2557 void vmsvga3dRestorePackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
    2558                                PCVMSVGAPACKPARAMS pSave)
     2286void vmsvga3dOglRestorePackParams(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface,
     2287                                  PCVMSVGAPACKPARAMS pSave)
    25592288{
    25602289    NOREF(pSurface);
     
    25802309
    25812310
    2582 int vmsvga3dSurfaceDMA(PVGASTATE pThis, SVGA3dGuestImage guest, SVGA3dSurfaceImageId host, SVGA3dTransferType transfer,
    2583                        uint32_t cCopyBoxes, SVGA3dCopyBox *pBoxes)
    2584 {
    2585     PVMSVGA3DSTATE          pState = pThis->svga.p3dState;
    2586     PVMSVGA3DSURFACE        pSurface;
    2587     PVMSVGA3DMIPMAPLEVEL    pMipLevel;
    2588     uint32_t                sid = host.sid;
    2589     int                     rc = VINF_SUCCESS;
    2590 
    2591     AssertReturn(pState, VERR_NO_MEMORY);
    2592     AssertReturn(sid < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
    2593     AssertReturn(sid < pState->cSurfaces && pState->papSurfaces[sid]->id == sid, VERR_INVALID_PARAMETER);
    2594 
    2595     pSurface = pState->papSurfaces[sid];
    2596     AssertReturn(pSurface->faces[0].numMipLevels > host.mipmap, VERR_INVALID_PARAMETER);
    2597     pMipLevel = &pSurface->pMipmapLevels[host.mipmap];
    2598 
    2599     if (pSurface->flags & SVGA3D_SURFACE_HINT_TEXTURE)
    2600         Log(("vmsvga3dSurfaceDMA TEXTURE guestptr gmr=%x offset=%x pitch=%x host sid=%x face=%d mipmap=%d transfer=%s cCopyBoxes=%d\n", guest.ptr.gmrId, guest.ptr.offset, guest.pitch, host.sid, host.face, host.mipmap, (transfer == SVGA3D_WRITE_HOST_VRAM) ? "READ" : "WRITE", cCopyBoxes));
    2601     else
    2602         Log(("vmsvga3dSurfaceDMA guestptr gmr=%x offset=%x pitch=%x host sid=%x face=%d mipmap=%d transfer=%s cCopyBoxes=%d\n", guest.ptr.gmrId, guest.ptr.offset, guest.pitch, host.sid, host.face, host.mipmap, (transfer == SVGA3D_WRITE_HOST_VRAM) ? "READ" : "WRITE", cCopyBoxes));
    2603 
    2604     if (pSurface->oglId.texture == OPENGL_INVALID_ID)
    2605     {
    2606         AssertReturn(pSurface->pMipmapLevels[host.mipmap].pSurfaceData, VERR_INTERNAL_ERROR);
    2607 
    2608         for (unsigned i = 0; i < cCopyBoxes; i++)
    2609         {
    2610             unsigned uDestOffset;
    2611             unsigned cbSrcPitch;
    2612             uint8_t *pBufferStart;
    2613 
    2614             Log(("Copy box %d (%d,%d,%d)(%d,%d,%d) dest (%d,%d)\n", i, pBoxes[i].srcx, pBoxes[i].srcy, pBoxes[i].srcz, pBoxes[i].w, pBoxes[i].h, pBoxes[i].d, pBoxes[i].x, pBoxes[i].y));
    2615             /* Apparently we're supposed to clip it (gmr test sample) */
    2616             if (pBoxes[i].x + pBoxes[i].w > pMipLevel->size.width)
    2617                 pBoxes[i].w = pMipLevel->size.width - pBoxes[i].x;
    2618             if (pBoxes[i].y + pBoxes[i].h > pMipLevel->size.height)
    2619                 pBoxes[i].h = pMipLevel->size.height - pBoxes[i].y;
    2620             if (pBoxes[i].z + pBoxes[i].d > pMipLevel->size.depth)
    2621                 pBoxes[i].d = pMipLevel->size.depth - pBoxes[i].z;
    2622 
    2623             if (    !pBoxes[i].w
    2624                 ||  !pBoxes[i].h
    2625                 ||  !pBoxes[i].d
    2626                 ||   pBoxes[i].x > pMipLevel->size.width
    2627                 ||   pBoxes[i].y > pMipLevel->size.height
    2628                 ||   pBoxes[i].z > pMipLevel->size.depth)
     2311/**
     2312 * Backend worker for implementing SVGA_3D_CMD_SURFACE_DMA that copies one box.
     2313 *
     2314 * @returns Failure status code or @a rc.
     2315 * @param   pThis               The VGA device instance data.
     2316 * @param   pState              The VMSVGA3d state.
     2317 * @param   pSurface            The host surface.
     2318 * @param   uHostMipmap         The host mipmap level (valid).
     2319 * @param   GuestPtr            The guest pointer.
     2320 * @param   cbSrcPitch          The guest (?) pitch.
     2321 * @param   transfer            The transfer direction.
     2322 * @param   pBox                The box to copy.
     2323 * @param   pContext            The context (for OpenGL).
     2324 * @param   rc                  The current rc for all boxes.
     2325 * @param   iBox                The current box number (for Direct 3D).
     2326 */
     2327int vmsvga3dBackSurfaceDMACopyBox(PVGASTATE pThis, PVMSVGA3DSTATE pState, PVMSVGA3DSURFACE pSurface, uint32_t uHostMipmap,
     2328                                  SVGAGuestPtr GuestPtr, uint32_t cbSrcPitch, SVGA3dTransferType transfer,
     2329                                  SVGA3dCopyBox const *pBox, PVMSVGA3DCONTEXT pContext, int rc, int iBox)
     2330{
     2331    PVMSVGA3DMIPMAPLEVEL pMipLevel = &pSurface->pMipmapLevels[uHostMipmap];
     2332
     2333    switch (pSurface->flags & VMSVGA3D_SURFACE_HINT_SWITCH_MASK)
     2334    {
     2335    case SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET:
     2336    case SVGA3D_SURFACE_HINT_TEXTURE:
     2337    case SVGA3D_SURFACE_HINT_RENDERTARGET:
     2338    {
     2339        uint32_t cbSurfacePitch;
     2340        uint8_t *pDoubleBuffer, *pBufferStart;
     2341        unsigned uDestOffset = 0;
     2342
     2343        pDoubleBuffer = (uint8_t *)RTMemAlloc(pMipLevel->cbSurface);
     2344        AssertReturn(pDoubleBuffer, VERR_NO_MEMORY);
     2345
     2346        if (transfer == SVGA3D_READ_HOST_VRAM)
     2347        {
     2348            GLint activeTexture;
     2349
     2350            /* Must bind texture to the current context in order to read it. */
     2351            glGetIntegerv(GL_TEXTURE_BINDING_2D, &activeTexture);
     2352            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     2353
     2354            glBindTexture(GL_TEXTURE_2D, pSurface->oglId.texture);
     2355            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     2356
     2357            /* Set row length and alignment of the input data. */
     2358            VMSVGAPACKPARAMS SavedParams;
     2359            vmsvga3dOglSetPackParams(pState, pContext, pSurface, &SavedParams);
     2360
     2361            glGetTexImage(GL_TEXTURE_2D,
     2362                          uHostMipmap,
     2363                          pSurface->formatGL,
     2364                          pSurface->typeGL,
     2365                          pDoubleBuffer);
     2366            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     2367
     2368            vmsvga3dOglRestorePackParams(pState, pContext, pSurface, &SavedParams);
     2369
     2370            /* Restore the old active texture. */
     2371            glBindTexture(GL_TEXTURE_2D, activeTexture);
     2372            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     2373
     2374            uDestOffset = pBox->x * pSurface->cbBlock + pBox->y * pMipLevel->cbSurfacePitch;
     2375            AssertReturnStmt(   uDestOffset + pBox->w * pSurface->cbBlock + (pBox->h - 1) * pMipLevel->cbSurfacePitch
     2376                             <= pMipLevel->cbSurface,
     2377                             RTMemFree(pDoubleBuffer),
     2378                             VERR_INTERNAL_ERROR);
     2379
     2380            cbSurfacePitch = pMipLevel->cbSurfacePitch;
     2381
     2382#ifdef MANUAL_FLIP_SURFACE_DATA
     2383            pBufferStart =   pDoubleBuffer
     2384                           + pBox->x * pSurface->cbBlock
     2385                           + pMipLevel->cbSurface - pBox->y * cbSurfacePitch
     2386                           - cbSurfacePitch;      /* flip image during copy */
     2387#else
     2388            pBufferStart = pDoubleBuffer + uDestOffset;
     2389#endif
     2390        }
     2391        else
     2392        {
     2393            cbSurfacePitch = pBox->w * pSurface->cbBlock;
     2394#ifdef MANUAL_FLIP_SURFACE_DATA
     2395            pBufferStart = pDoubleBuffer + cbSurfacePitch * pBox->h - cbSurfacePitch;      /* flip image during copy */
     2396#else
     2397            pBufferStart = pDoubleBuffer;
     2398#endif
     2399        }
     2400
     2401        rc = vmsvgaGMRTransfer(pThis,
     2402                               transfer,
     2403                               pBufferStart,
     2404#ifdef MANUAL_FLIP_SURFACE_DATA
     2405                               -(int32_t)cbSurfacePitch,
     2406#else
     2407                               (int32_t)cbSurfacePitch,
     2408#endif
     2409                               GuestPtr,
     2410                               pBox->srcx * pSurface->cbBlock + pBox->srcy * cbSrcPitch,
     2411                               cbSrcPitch,
     2412                               pBox->w * pSurface->cbBlock,
     2413                               pBox->h);
     2414        AssertRC(rc);
     2415
     2416        /* Update the opengl surface data. */
     2417        if (transfer == SVGA3D_WRITE_HOST_VRAM)
     2418        {
     2419            GLint activeTexture = 0;
     2420
     2421            glGetIntegerv(GL_TEXTURE_BINDING_2D, &activeTexture);
     2422            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     2423
     2424            /* Must bind texture to the current context in order to change it. */
     2425            glBindTexture(GL_TEXTURE_2D, pSurface->oglId.texture);
     2426            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     2427
     2428            Log(("vmsvga3dSurfaceDMA: copy texture mipmap level %d (pitch %x)\n", uHostMipmap, pMipLevel->cbSurfacePitch));
     2429
     2430            /* Set row length and alignment of the input data. */
     2431            VMSVGAPACKPARAMS SavedParams;
     2432            vmsvga3dOglSetUnpackParams(pState, pContext, pSurface, &SavedParams); /** @todo do we need to set ROW_LENGTH to w here? */
     2433
     2434            glTexSubImage2D(GL_TEXTURE_2D,
     2435                            uHostMipmap,
     2436                            pBox->x,
     2437                            pBox->y,
     2438                            pBox->w,
     2439                            pBox->h,
     2440                            pSurface->formatGL,
     2441                            pSurface->typeGL,
     2442                            pDoubleBuffer);
     2443
     2444            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     2445
     2446            /* Restore old values. */
     2447            vmsvga3dOglRestoreUnpackParams(pState, pContext, pSurface, &SavedParams);
     2448
     2449            /* Restore the old active texture. */
     2450            glBindTexture(GL_TEXTURE_2D, activeTexture);
     2451            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
     2452        }
     2453
     2454        Log4(("first line:\n%.*Rhxd\n", pBox->w * pSurface->cbBlock, pDoubleBuffer));
     2455
     2456        /* Free the double buffer. */
     2457        RTMemFree(pDoubleBuffer);
     2458        break;
     2459    }
     2460
     2461    case SVGA3D_SURFACE_HINT_DEPTHSTENCIL:
     2462        AssertFailed(); /* @todo */
     2463        break;
     2464
     2465    case SVGA3D_SURFACE_HINT_VERTEXBUFFER:
     2466    case SVGA3D_SURFACE_HINT_INDEXBUFFER:
     2467    {
     2468        Assert(pBox->h == 1);
     2469
     2470        VMSVGA3D_CLEAR_GL_ERRORS();
     2471        pState->ext.glBindBuffer(GL_ARRAY_BUFFER, pSurface->oglId.buffer);
     2472        if (VMSVGA3D_GL_IS_SUCCESS(pContext))
     2473        {
     2474            GLenum enmGlTransfer = (transfer == SVGA3D_READ_HOST_VRAM) ? GL_READ_ONLY : GL_WRITE_ONLY;
     2475            uint8_t *pbData = (uint8_t *)pState->ext.glMapBuffer(GL_ARRAY_BUFFER, enmGlTransfer);
     2476            if (RT_LIKELY(pbData != NULL))
    26292477            {
    2630                 Log(("Empty box; skip\n"));
    2631                 continue;
    2632             }
    2633 
    2634             uDestOffset = pBoxes[i].x * pSurface->cbBlock + pBoxes[i].y * pMipLevel->cbSurfacePitch + pBoxes[i].z * pMipLevel->size.height * pMipLevel->cbSurfacePitch;
    2635             AssertReturn(uDestOffset + pBoxes[i].w * pSurface->cbBlock * pBoxes[i].h * pBoxes[i].d <= pMipLevel->cbSurface, VERR_INTERNAL_ERROR);
    2636 
    2637             cbSrcPitch = (guest.pitch == 0) ? pBoxes[i].w * pSurface->cbBlock : guest.pitch;
    2638 #ifdef MANUAL_FLIP_SURFACE_DATA
    2639             pBufferStart =    (uint8_t *)pMipLevel->pSurfaceData
    2640                             + pBoxes[i].x * pSurface->cbBlock
    2641                             + pMipLevel->cbSurface - pBoxes[i].y * pMipLevel->cbSurfacePitch
    2642                             - pMipLevel->cbSurfacePitch;      /* flip image during copy */
    2643 #else
    2644             pBufferStart = (uint8_t *)pMipLevel->pSurfaceData + uDestOffset;
    2645 #endif
    2646             rc = vmsvgaGMRTransfer(pThis,
    2647                                    transfer,
    2648                                    pBufferStart,
    2649 #ifdef MANUAL_FLIP_SURFACE_DATA
    2650                                    -(int32_t)pMipLevel->cbSurfacePitch,
    2651 #else
    2652                                    (int32_t)pMipLevel->cbSurfacePitch,
    2653 #endif
    2654                                    guest.ptr,
    2655                                    pBoxes[i].srcx * pSurface->cbBlock + (pBoxes[i].srcy + pBoxes[i].srcz * pBoxes[i].h) * cbSrcPitch,
    2656                                    cbSrcPitch,
    2657                                    pBoxes[i].w * pSurface->cbBlock,
    2658                                    pBoxes[i].d * pBoxes[i].h);
    2659 
    2660             Log4(("first line:\n%.*Rhxd\n", pMipLevel->cbSurface, pMipLevel->pSurfaceData));
    2661 
    2662             AssertRC(rc);
    2663         }
    2664         pSurface->pMipmapLevels[host.mipmap].fDirty = true;
    2665         pSurface->fDirty = true;
    2666     }
    2667     else
    2668     {
    2669 #ifdef VMSVGA3D_OGL_WITH_SHARED_CTX
    2670         PVMSVGA3DCONTEXT pContext = &pState->SharedCtx;
    2671 #else
    2672         /* @todo stricter checks for associated context */
    2673         uint32_t cid = pSurface->idAssociatedContext;
    2674         if (    cid >= pState->cContexts
    2675             ||  pState->papContexts[cid]->id != cid)
    2676         {
    2677             Log(("vmsvga3dSurfaceDMA invalid context id (%x - %x)!\n", cid, (cid >= pState->cContexts) ? -1 : pState->papContexts[cid]->id));
    2678             AssertFailedReturn(VERR_INVALID_PARAMETER);
    2679         }
    2680         PVMSVGA3DCONTEXT pContext = pState->papContexts[cid];
    2681 #endif
    2682         VMSVGA3D_SET_CURRENT_CONTEXT(pState, pContext);
    2683 
    2684         for (unsigned i = 0; i < cCopyBoxes; i++)
    2685         {
    2686             bool fVertex = false;
    2687             unsigned cbSrcPitch;
    2688 
    2689             /* Apparently we're supposed to clip it (gmr test sample) */
    2690             if (pBoxes[i].x + pBoxes[i].w > pMipLevel->size.width)
    2691                 pBoxes[i].w = pMipLevel->size.width - pBoxes[i].x;
    2692             if (pBoxes[i].y + pBoxes[i].h > pMipLevel->size.height)
    2693                 pBoxes[i].h = pMipLevel->size.height - pBoxes[i].y;
    2694             if (pBoxes[i].z + pBoxes[i].d > pMipLevel->size.depth)
    2695                 pBoxes[i].d = pMipLevel->size.depth - pBoxes[i].z;
    2696 
    2697             Assert((pBoxes[i].d == 1 || pBoxes[i].d == 0) && pBoxes[i].z == 0);
    2698 
    2699             if (    !pBoxes[i].w
    2700                 ||  !pBoxes[i].h
    2701                 ||   pBoxes[i].x > pMipLevel->size.width
    2702                 ||   pBoxes[i].y > pMipLevel->size.height)
    2703             {
    2704                 Log(("Empty box; skip\n"));
    2705                 continue;
    2706             }
    2707 
    2708             Log(("Copy box %d (%d,%d,%d)(%d,%d,%d) dest (%d,%d)\n", i, pBoxes[i].srcx, pBoxes[i].srcy, pBoxes[i].srcz, pBoxes[i].w, pBoxes[i].h, pBoxes[i].d, pBoxes[i].x, pBoxes[i].y));
    2709 
    2710             cbSrcPitch = (guest.pitch == 0) ? pBoxes[i].w * pSurface->cbBlock : guest.pitch;
    2711 
    2712             switch (pSurface->flags & (SVGA3D_SURFACE_HINT_INDEXBUFFER | SVGA3D_SURFACE_HINT_VERTEXBUFFER | SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET | SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_CUBEMAP))
    2713             {
    2714             case SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET:
    2715             case SVGA3D_SURFACE_HINT_TEXTURE:
    2716             case SVGA3D_SURFACE_HINT_RENDERTARGET:
    2717             {
    2718                 uint32_t cbSurfacePitch;
    2719                 uint8_t *pDoubleBuffer, *pBufferStart;
    2720                 unsigned uDestOffset = 0;
    2721 
    2722                 pDoubleBuffer = (uint8_t *)RTMemAlloc(pMipLevel->cbSurface);
    2723                 AssertReturn(pDoubleBuffer, VERR_NO_MEMORY);
    2724 
    2725                 if (transfer == SVGA3D_READ_HOST_VRAM)
     2478#if defined(VBOX_STRICT) && defined(RT_OS_DARWIN)
     2479                GLint cbStrictBufSize;
     2480                glGetBufferParameteriv(GL_ARRAY_BUFFER, GL_BUFFER_SIZE, &cbStrictBufSize);
     2481                Assert(VMSVGA3D_GL_IS_SUCCESS(pContext));
     2482# ifdef VMSVGA3D_OGL_WITH_SHARED_CTX
     2483                AssertMsg(cbStrictBufSize >= (int32_t)pMipLevel->cbSurface,
     2484                          ("cbStrictBufSize=%#x cbSurface=%#x pContext->id=%#x\n", (uint32_t)cbStrictBufSize, pMipLevel->cbSurface, pContext->id));
     2485# else
     2486                AssertMsg(cbStrictBufSize >= (int32_t)pMipLevel->cbSurface,
     2487                          ("cbStrictBufSize=%#x cbSurface=%#x isAssociatedContext=%#x pContext->id=%#x\n", (uint32_t)cbStrictBufSize, pMipLevel->cbSurface, pSurface->idAssociatedContext, pContext->id));
     2488# endif
     2489#endif
     2490
     2491                unsigned offDst = pBox->x * pSurface->cbBlock + pBox->y * pMipLevel->cbSurfacePitch;
     2492                if (RT_LIKELY(   offDst + pBox->w * pSurface->cbBlock  + (pBox->h - 1) * pMipLevel->cbSurfacePitch
     2493                              <= pMipLevel->cbSurface))
    27262494                {
    2727                     GLint activeTexture;
    2728 
    2729                     /* Must bind texture to the current context in order to read it. */
    2730                     glGetIntegerv(GL_TEXTURE_BINDING_2D, &activeTexture);
    2731                     VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    2732 
    2733                     glBindTexture(GL_TEXTURE_2D, pSurface->oglId.texture);
    2734                     VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    2735 
    2736                     /* Set row length and alignment of the input data. */
    2737                     VMSVGAPACKPARAMS SavedParams;
    2738                     vmsvga3dSetPackParams(pState, pContext, pSurface, &SavedParams);
    2739 
    2740                     glGetTexImage(GL_TEXTURE_2D,
    2741                                   host.mipmap,
    2742                                   pSurface->formatGL,
    2743                                   pSurface->typeGL,
    2744                                   pDoubleBuffer);
    2745                     VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    2746 
    2747                     vmsvga3dRestorePackParams(pState, pContext, pSurface, &SavedParams);
    2748 
    2749                     /* Restore the old active texture. */
    2750                     glBindTexture(GL_TEXTURE_2D, activeTexture);
    2751                     VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    2752 
    2753                     uDestOffset = pBoxes[i].x * pSurface->cbBlock + pBoxes[i].y * pMipLevel->cbSurfacePitch;
    2754                     AssertReturnStmt(   uDestOffset + pBoxes[i].w * pSurface->cbBlock + (pBoxes[i].h - 1) * pMipLevel->cbSurfacePitch
    2755                                      <= pMipLevel->cbSurface,
    2756                                      RTMemFree(pDoubleBuffer),
    2757                                      VERR_INTERNAL_ERROR);
    2758 
    2759                     cbSurfacePitch = pMipLevel->cbSurfacePitch;
    2760 
    2761 #ifdef MANUAL_FLIP_SURFACE_DATA
    2762                     pBufferStart =   pDoubleBuffer
    2763                                    + pBoxes[i].x * pSurface->cbBlock
    2764                                    + pMipLevel->cbSurface - pBoxes[i].y * cbSurfacePitch
    2765                                    - cbSurfacePitch;      /* flip image during copy */
    2766 #else
    2767                     pBufferStart = pDoubleBuffer + uDestOffset;
    2768 #endif
     2495                    Log(("Lock %s memory for rectangle (%d,%d)(%d,%d)\n", (pSurface->flags & VMSVGA3D_SURFACE_HINT_SWITCH_MASK) == SVGA3D_SURFACE_HINT_VERTEXBUFFER ? "vertex" : "index",
     2496                         pBox->x, pBox->y, pBox->x + pBox->w, pBox->y + pBox->h));
     2497
     2498                    rc = vmsvgaGMRTransfer(pThis,
     2499                                           transfer,
     2500                                           pbData + offDst,
     2501                                           pMipLevel->cbSurfacePitch,
     2502                                           GuestPtr,
     2503                                           pBox->srcx * pSurface->cbBlock + pBox->srcy * cbSrcPitch,
     2504                                           cbSrcPitch,
     2505                                           pBox->w * pSurface->cbBlock,
     2506                                           pBox->h);
     2507                    AssertRC(rc);
     2508
     2509                    Log4(("first line:\n%.*Rhxd\n", cbSrcPitch, pbData));
    27692510                }
    27702511                else
    27712512                {
    2772                     cbSurfacePitch = pBoxes[i].w * pSurface->cbBlock;
    2773 #ifdef MANUAL_FLIP_SURFACE_DATA
    2774                     pBufferStart = pDoubleBuffer + cbSurfacePitch * pBoxes[i].h - cbSurfacePitch;      /* flip image during copy */
    2775 #else
    2776                     pBufferStart = pDoubleBuffer;
    2777 #endif
     2513                    AssertFailed();
     2514                    rc = VERR_INTERNAL_ERROR;
    27782515                }
    27792516
    2780                 rc = vmsvgaGMRTransfer(pThis,
    2781                                        transfer,
    2782                                        pBufferStart,
    2783 #ifdef MANUAL_FLIP_SURFACE_DATA
    2784                                        -(int32_t)cbSurfacePitch,
    2785 #else
    2786                                        (int32_t)cbSurfacePitch,
    2787 #endif
    2788                                        guest.ptr,
    2789                                        pBoxes[i].srcx * pSurface->cbBlock + pBoxes[i].srcy * cbSrcPitch,
    2790                                        cbSrcPitch,
    2791                                        pBoxes[i].w * pSurface->cbBlock,
    2792                                        pBoxes[i].h);
    2793                 AssertRC(rc);
    2794 
    2795                 /* Update the opengl surface data. */
    2796                 if (transfer == SVGA3D_WRITE_HOST_VRAM)
    2797                 {
    2798                     GLint activeTexture = 0;
    2799 
    2800                     glGetIntegerv(GL_TEXTURE_BINDING_2D, &activeTexture);
    2801                     VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    2802 
    2803                     /* Must bind texture to the current context in order to change it. */
    2804                     glBindTexture(GL_TEXTURE_2D, pSurface->oglId.texture);
    2805                     VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    2806 
    2807                     Log(("vmsvga3dSurfaceDMA: copy texture mipmap level %d (pitch %x)\n", host.mipmap, pMipLevel->cbSurfacePitch));
    2808 
    2809                     /* Set row length and alignment of the input data. */
    2810                     VMSVGAPACKPARAMS SavedParams;
    2811                     vmsvga3dSetUnpackParams(pState, pContext, pSurface, &SavedParams); /** @todo do we need to set ROW_LENGTH to w here? */
    2812 
    2813                     glTexSubImage2D(GL_TEXTURE_2D,
    2814                                     host.mipmap,
    2815                                     pBoxes[i].x,
    2816                                     pBoxes[i].y,
    2817                                     pBoxes[i].w,
    2818                                     pBoxes[i].h,
    2819                                     pSurface->formatGL,
    2820                                     pSurface->typeGL,
    2821                                     pDoubleBuffer);
    2822 
    2823                     VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    2824 
    2825                     /* Restore old values. */
    2826                     vmsvga3dRestoreUnpackParams(pState, pContext, pSurface, &SavedParams);
    2827 
    2828                     /* Restore the old active texture. */
    2829                     glBindTexture(GL_TEXTURE_2D, activeTexture);
    2830                     VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    2831                 }
    2832 
    2833                 Log4(("first line:\n%.*Rhxd\n", pBoxes[i].w * pSurface->cbBlock, pDoubleBuffer));
    2834 
    2835                 /* Free the double buffer. */
    2836                 RTMemFree(pDoubleBuffer);
    2837                 break;
     2517                pState->ext.glUnmapBuffer(GL_ARRAY_BUFFER);
     2518                VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
    28382519            }
    2839 
    2840             case SVGA3D_SURFACE_HINT_DEPTHSTENCIL:
    2841                 AssertFailed(); /* @todo */
    2842                 break;
    2843 
    2844             case SVGA3D_SURFACE_HINT_VERTEXBUFFER:
    2845             case SVGA3D_SURFACE_HINT_INDEXBUFFER:
    2846             {
    2847                 Assert(pBoxes[i].h == 1);
    2848 
    2849                 VMSVGA3D_CLEAR_GL_ERRORS();
    2850                 pState->ext.glBindBuffer(GL_ARRAY_BUFFER, pSurface->oglId.buffer);
    2851                 if (VMSVGA3D_GL_IS_SUCCESS(pContext))
    2852                 {
    2853                     GLenum enmGlTransfer = (transfer == SVGA3D_READ_HOST_VRAM) ? GL_READ_ONLY : GL_WRITE_ONLY;
    2854                     uint8_t *pbData = (uint8_t *)pState->ext.glMapBuffer(GL_ARRAY_BUFFER, enmGlTransfer);
    2855                     if (RT_LIKELY(pbData != NULL))
    2856                     {
    2857 #if defined(VBOX_STRICT) && defined(RT_OS_DARWIN)
    2858                         GLint cbStrictBufSize;
    2859                         glGetBufferParameteriv(GL_ARRAY_BUFFER, GL_BUFFER_SIZE, &cbStrictBufSize);
    2860                         Assert(VMSVGA3D_GL_IS_SUCCESS(pContext));
    2861 # ifdef VMSVGA3D_OGL_WITH_SHARED_CTX
    2862                         AssertMsg(cbStrictBufSize >= (int32_t)pMipLevel->cbSurface,
    2863                                   ("cbStrictBufSize=%#x cbSurface=%#x pContext->id=%#x\n", (uint32_t)cbStrictBufSize, pMipLevel->cbSurface, pContext->id));
    2864 # else
    2865                         AssertMsg(cbStrictBufSize >= (int32_t)pMipLevel->cbSurface,
    2866                                   ("cbStrictBufSize=%#x cbSurface=%#x isAssociatedContext=%#x pContext->id=%#x\n", (uint32_t)cbStrictBufSize, pMipLevel->cbSurface, pSurface->idAssociatedContext, pContext->id));
    2867 # endif
    2868 #endif
    2869 
    2870                         unsigned offDst = pBoxes[i].x * pSurface->cbBlock + pBoxes[i].y * pMipLevel->cbSurfacePitch;
    2871                         if (RT_LIKELY(   offDst + pBoxes[i].w * pSurface->cbBlock  + (pBoxes[i].h - 1) * pMipLevel->cbSurfacePitch
    2872                                       <= pMipLevel->cbSurface))
    2873                         {
    2874                             Log(("Lock %s memory for rectangle (%d,%d)(%d,%d)\n", (fVertex) ? "vertex" : "index",
    2875                                  pBoxes[i].x, pBoxes[i].y, pBoxes[i].x + pBoxes[i].w, pBoxes[i].y + pBoxes[i].h));
    2876 
    2877                             rc = vmsvgaGMRTransfer(pThis,
    2878                                                    transfer,
    2879                                                    pbData + offDst,
    2880                                                    pMipLevel->cbSurfacePitch,
    2881                                                    guest.ptr,
    2882                                                    pBoxes[i].srcx * pSurface->cbBlock + pBoxes[i].srcy * cbSrcPitch,
    2883                                                    cbSrcPitch,
    2884                                                    pBoxes[i].w * pSurface->cbBlock,
    2885                                                    pBoxes[i].h);
    2886                             AssertRC(rc);
    2887 
    2888                             Log4(("first line:\n%.*Rhxd\n", cbSrcPitch, pbData));
    2889                         }
    2890                         else
    2891                         {
    2892                             AssertFailed();
    2893                             rc = VERR_INTERNAL_ERROR;
    2894                         }
    2895 
    2896                         pState->ext.glUnmapBuffer(GL_ARRAY_BUFFER);
    2897                         VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
    2898                     }
    2899                     else
    2900                         VMSVGA3D_GL_GET_AND_COMPLAIN(pState, pContext, ("glMapBuffer(GL_ARRAY_BUFFER, %#x) -> NULL\n", enmGlTransfer));
    2901                 }
    2902                 else
    2903                     VMSVGA3D_GL_COMPLAIN(pState, pContext, ("glBindBuffer(GL_ARRAY_BUFFER, %#x)\n", pSurface->oglId.buffer));
    2904                 pState->ext.glBindBuffer(GL_ARRAY_BUFFER, 0);
    2905                 VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
    2906                 break;
    2907             }
    2908 
    2909             default:
    2910                 AssertFailed();
    2911                 break;
    2912             }
    2913         }
    2914     }
     2520            else
     2521                VMSVGA3D_GL_GET_AND_COMPLAIN(pState, pContext, ("glMapBuffer(GL_ARRAY_BUFFER, %#x) -> NULL\n", enmGlTransfer));
     2522        }
     2523        else
     2524            VMSVGA3D_GL_COMPLAIN(pState, pContext, ("glBindBuffer(GL_ARRAY_BUFFER, %#x)\n", pSurface->oglId.buffer));
     2525        pState->ext.glBindBuffer(GL_ARRAY_BUFFER, 0);
     2526        VMSVGA3D_CHECK_LAST_ERROR(pState, pContext);
     2527        break;
     2528    }
     2529
     2530    default:
     2531        AssertFailed();
     2532        break;
     2533    }
     2534
    29152535    return rc;
    29162536}
     2537
    29172538
    29182539int vmsvga3dSurfaceBlitToScreen(PVGASTATE pThis, uint32_t dest, SVGASignedRect destRect, SVGA3dSurfaceImageId src, SVGASignedRect srcRect, uint32_t cRects, SVGASignedRect *pRect)
     
    30392660        /* Unknown surface type; turn it into a texture. */
    30402661        Log(("vmsvga3dGenerateMipmaps: unknown src surface id=%x type=%d format=%d -> create texture\n", sid, pSurface->flags, pSurface->format));
    3041         rc = vmsvga3dCreateTexture(pState, pContext, cid, pSurface);
     2662        rc = vmsvga3dBackCreateTexture(pState, pContext, cid, pSurface);
    30422663        AssertRCReturn(rc, rc);
    30432664    }
     
    51974818        {
    51984819            Log(("vmsvga3dSetRenderTarget: create texture to be used as render target; surface id=%x type=%d format=%d -> create texture\n", target.sid, pRenderTarget->flags, pRenderTarget->format));
    5199             int rc = vmsvga3dCreateTexture(pState, pContext, cid, pRenderTarget);
     4820            int rc = vmsvga3dBackCreateTexture(pState, pContext, cid, pRenderTarget);
    52004821            AssertRCReturn(rc, rc);
    52014822        }
     
    55145135#endif
    55155136                    Log(("CreateTexture (%d,%d) level=%d\n", pSurface->pMipmapLevels[0].size.width, pSurface->pMipmapLevels[0].size.height, pSurface->faces[0].numMipLevels));
    5516                     int rc = vmsvga3dCreateTexture(pState, pContext, cid, pSurface);
     5137                    int rc = vmsvga3dBackCreateTexture(pState, pContext, cid, pSurface);
    55175138                    AssertRCReturn(rc, rc);
    55185139                }
  • trunk/src/VBox/Devices/Graphics/DevVGA-SVGA3d-savedstate.cpp

    r57149 r57151  
    793793                            /* Set row length and alignment of the output data. */
    794794                            VMSVGAPACKPARAMS SavedParams;
    795                             vmsvga3dSetPackParams(pState, pContext, pSurface, &SavedParams);
     795                            vmsvga3dOglSetPackParams(pState, pContext, pSurface, &SavedParams);
    796796
    797797                            glGetTexImage(GL_TEXTURE_2D,
     
    802802                            VMSVGA3D_CHECK_LAST_ERROR_WARN(pState, pContext);
    803803
    804                             vmsvga3dRestorePackParams(pState, pContext, pSurface, &SavedParams);
     804                            vmsvga3dOglRestorePackParams(pState, pContext, pSurface, &SavedParams);
    805805
    806806                            /* Data follows */
  • trunk/src/VBox/Devices/Graphics/DevVGA-SVGA3d-win.cpp

    r57149 r57151  
    160160*******************************************************************************/
    161161static void vmsvgaDumpD3DCaps(D3DCAPS9 *pCaps);
    162 static int  vmsvga3dCreateTexture(PVMSVGA3DCONTEXT pContext, uint32_t idAssociatedContext, PVMSVGA3DSURFACE pSurface);
    163162
    164163
     
    923922 * Convert SVGA format value to its D3D equivalent
    924923 */
    925 static D3DFORMAT vmsvga3dSurfaceFormat2D3D(SVGA3dSurfaceFormat format)
     924D3DFORMAT vmsvga3dSurfaceFormat2D3D(SVGA3dSurfaceFormat format)
    926925{
    927926    switch (format)
     
    10751074}
    10761075
    1077 int vmsvga3dSurfaceDefine(PVGASTATE pThis, uint32_t sid, uint32_t surfaceFlags, SVGA3dSurfaceFormat format, SVGA3dSurfaceFace face[SVGA3D_MAX_SURFACE_FACES],
    1078                           uint32_t multisampleCount, SVGA3dTextureFilter autogenFilter, uint32_t cMipLevels, SVGA3dSize *pMipLevelSize)
     1076
     1077/**
     1078 * Destroy backend specific surface bits (part of SVGA_3D_CMD_SURFACE_DESTROY).
     1079 *
     1080 * @param   pState              The VMSVGA3d state.
     1081 * @param   pSurface            The surface being destroyed.
     1082 */
     1083void vmsvga3dBackSurfaceDestroy(PVMSVGA3DSTATE pState, PVMSVGA3DSURFACE pSurface)
    10791084{
    1080     PVMSVGA3DSURFACE pSurface;
    1081     PVMSVGA3DSTATE   pState = pThis->svga.p3dState;
    1082     AssertReturn(pState, VERR_NO_MEMORY);
    1083 
    1084     Log(("vmsvga3dSurfaceDefine: sid=%x surfaceFlags=%x format=%s (%x) multiSampleCount=%d autogenFilter=%d, cMipLevels=%d size=(%d,%d,%d)\n",
    1085          sid, surfaceFlags, vmsvgaLookupEnum((int)format, &g_SVGA3dSurfaceFormat2String), format, multisampleCount, autogenFilter, cMipLevels, pMipLevelSize->width, pMipLevelSize->height, pMipLevelSize->depth));
    1086 
    1087     AssertReturn(sid < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
    1088     AssertReturn(cMipLevels >= 1, VERR_INVALID_PARAMETER);
    1089     /* Assuming all faces have the same nr of mipmaps. */
    1090     AssertReturn(!(surfaceFlags & SVGA3D_SURFACE_CUBEMAP) || cMipLevels == face[0].numMipLevels * 6, VERR_INVALID_PARAMETER);
    1091     AssertReturn((surfaceFlags & SVGA3D_SURFACE_CUBEMAP) || cMipLevels == face[0].numMipLevels, VERR_INVALID_PARAMETER);
    1092 
    1093     if (sid >= pState->cSurfaces)
    1094     {
    1095         /* Grow the array. */
    1096         uint32_t cNew = RT_ALIGN(sid + 15, 16);
    1097         void *pvNew = RTMemRealloc(pState->papSurfaces, sizeof(pState->papSurfaces[0]) * cNew);
    1098         AssertReturn(pvNew, VERR_NO_MEMORY);
    1099         pState->papSurfaces = (PVMSVGA3DSURFACE *)pvNew;
    1100         while (pState->cSurfaces < cNew)
    1101         {
    1102             pSurface = (PVMSVGA3DSURFACE)RTMemAllocZ(sizeof(*pSurface));
    1103             AssertReturn(pSurface, VERR_NO_MEMORY);
    1104             pSurface->id = SVGA3D_INVALID_ID;
    1105             pState->papSurfaces[pState->cSurfaces++] = pSurface;
    1106         }
    1107     }
    1108     pSurface = pState->papSurfaces[sid];
    1109 
    1110     /* If one already exists with this id, then destroy it now. */
    1111     if (pSurface->id != SVGA3D_INVALID_ID)
    1112         vmsvga3dSurfaceDestroy(pThis, sid);
    1113 
    1114     memset(pSurface, 0, sizeof(*pSurface));
    1115     pSurface->id                    = sid;
    1116     pSurface->idAssociatedContext   = SVGA3D_INVALID_ID;
    1117     pSurface->hSharedObject         = NULL;
    1118     pSurface->pSharedObjectTree     = NULL;
    1119 
    1120     /* The surface type is sort of undefined now, even though the hints and format can help to clear that up.
    1121      * In some case we'll have to wait until the surface is used to create the D3D object.
    1122      */
    1123     switch (format)
    1124     {
    1125     case SVGA3D_Z_D32:
    1126     case SVGA3D_Z_D16:
    1127     case SVGA3D_Z_D24S8:
    1128     case SVGA3D_Z_D15S1:
    1129     case SVGA3D_Z_D24X8:
    1130     case SVGA3D_Z_DF16:
    1131     case SVGA3D_Z_DF24:
    1132     case SVGA3D_Z_D24S8_INT:
    1133         surfaceFlags |= SVGA3D_SURFACE_HINT_DEPTHSTENCIL;
    1134         break;
    1135 
    1136     /* Texture compression formats */
    1137     case SVGA3D_DXT1:
    1138     case SVGA3D_DXT2:
    1139     case SVGA3D_DXT3:
    1140     case SVGA3D_DXT4:
    1141     case SVGA3D_DXT5:
    1142     /* Bump-map formats */
    1143     case SVGA3D_BUMPU8V8:
    1144     case SVGA3D_BUMPL6V5U5:
    1145     case SVGA3D_BUMPX8L8V8U8:
    1146     case SVGA3D_BUMPL8V8U8:
    1147     case SVGA3D_V8U8:
    1148     case SVGA3D_Q8W8V8U8:
    1149     case SVGA3D_CxV8U8:
    1150     case SVGA3D_X8L8V8U8:
    1151     case SVGA3D_A2W10V10U10:
    1152     case SVGA3D_V16U16:
    1153     /* Typical render target formats; we should allow render target buffers to be used as textures. */
    1154     case SVGA3D_X8R8G8B8:
    1155     case SVGA3D_A8R8G8B8:
    1156     case SVGA3D_R5G6B5:
    1157     case SVGA3D_X1R5G5B5:
    1158     case SVGA3D_A1R5G5B5:
    1159     case SVGA3D_A4R4G4B4:
    1160         surfaceFlags |= SVGA3D_SURFACE_HINT_TEXTURE;
    1161         break;
    1162 
    1163     case SVGA3D_LUMINANCE8:
    1164     case SVGA3D_LUMINANCE4_ALPHA4:
    1165     case SVGA3D_LUMINANCE16:
    1166     case SVGA3D_LUMINANCE8_ALPHA8:
    1167     case SVGA3D_ARGB_S10E5:   /* 16-bit floating-point ARGB */
    1168     case SVGA3D_ARGB_S23E8:   /* 32-bit floating-point ARGB */
    1169     case SVGA3D_A2R10G10B10:
    1170     case SVGA3D_ALPHA8:
    1171     case SVGA3D_R_S10E5:
    1172     case SVGA3D_R_S23E8:
    1173     case SVGA3D_RG_S10E5:
    1174     case SVGA3D_RG_S23E8:
    1175     case SVGA3D_G16R16:
    1176     case SVGA3D_A16B16G16R16:
    1177     case SVGA3D_UYVY:
    1178     case SVGA3D_YUY2:
    1179     case SVGA3D_NV12:
    1180     case SVGA3D_AYUV:
    1181     case SVGA3D_BC4_UNORM:
    1182     case SVGA3D_BC5_UNORM:
    1183         break;
    1184 
    1185     /*
    1186      * Any surface can be used as a buffer object, but SVGA3D_BUFFER is
    1187      * the most efficient format to use when creating new surfaces
    1188      * expressly for index or vertex data.
    1189      */
    1190     case SVGA3D_BUFFER:
    1191         break;
    1192     }
    1193 
    1194     pSurface->flags             = surfaceFlags;
    1195     pSurface->format            = format;
    1196     memcpy(pSurface->faces, face, sizeof(face));
    1197     pSurface->cFaces            = 1;    /* check for cube maps later */
    1198     pSurface->multiSampleCount  = multisampleCount;
    1199     pSurface->autogenFilter     = autogenFilter;
    1200     Assert(autogenFilter != SVGA3D_TEX_FILTER_FLATCUBIC);
    1201     Assert(autogenFilter != SVGA3D_TEX_FILTER_GAUSSIANCUBIC);
    1202     pSurface->pMipmapLevels     = (PVMSVGA3DMIPMAPLEVEL)RTMemAllocZ(cMipLevels * sizeof(VMSVGA3DMIPMAPLEVEL));
    1203     AssertReturn(pSurface->pMipmapLevels, VERR_NO_MEMORY);
    1204 
    1205     for (uint32_t i=0; i < cMipLevels; i++)
    1206         pSurface->pMipmapLevels[i].size = pMipLevelSize[i];
    1207 
    1208     /* Translate the format and usage flags to D3D. */
    1209     pSurface->formatD3D         = vmsvga3dSurfaceFormat2D3D(format);
    1210     pSurface->cbBlock           = vmsvga3dSurfaceFormatSize(format);
    1211     pSurface->multiSampleTypeD3D= vmsvga3dMultipeSampleCount2D3D(multisampleCount);
    1212     pSurface->fUsageD3D         = 0;
    1213     if (surfaceFlags & SVGA3D_SURFACE_HINT_DYNAMIC)
    1214         pSurface->fUsageD3D |= D3DUSAGE_DYNAMIC;
    1215     if (surfaceFlags & SVGA3D_SURFACE_HINT_RENDERTARGET)
    1216         pSurface->fUsageD3D |= D3DUSAGE_RENDERTARGET;
    1217     if (surfaceFlags & SVGA3D_SURFACE_HINT_DEPTHSTENCIL)
    1218         pSurface->fUsageD3D |= D3DUSAGE_DEPTHSTENCIL;
    1219     if (surfaceFlags & SVGA3D_SURFACE_HINT_WRITEONLY)
    1220         pSurface->fUsageD3D |= D3DUSAGE_WRITEONLY;
    1221     if (surfaceFlags & SVGA3D_SURFACE_AUTOGENMIPMAPS)
    1222         pSurface->fUsageD3D |= D3DUSAGE_AUTOGENMIPMAP;
    1223 
    1224     switch (surfaceFlags & (SVGA3D_SURFACE_HINT_INDEXBUFFER | SVGA3D_SURFACE_HINT_VERTEXBUFFER | SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET | SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_CUBEMAP))
     1085    RTAvlU32Destroy(&pSurface->pSharedObjectTree, vmsvga3dSharedSurfaceDestroyTree, pSurface);
     1086    Assert(pSurface->pSharedObjectTree == NULL);
     1087
     1088    switch (pSurface->flags & VMSVGA3D_SURFACE_HINT_SWITCH_MASK)
    12251089    {
    12261090    case SVGA3D_SURFACE_CUBEMAP:
    1227         Log(("SVGA3D_SURFACE_CUBEMAP\n"));
    1228         pSurface->cFaces = 6;
     1091        AssertFailed(); /** @todo */
    12291092        break;
    12301093
    12311094    case SVGA3D_SURFACE_HINT_INDEXBUFFER:
    1232         Log(("SVGA3D_SURFACE_HINT_INDEXBUFFER\n"));
    1233         /* else type unknown at this time; postpone buffer creation */
     1095        if (pSurface->u.pIndexBuffer)
     1096            pSurface->u.pIndexBuffer->Release();
    12341097        break;
    12351098
    12361099    case SVGA3D_SURFACE_HINT_VERTEXBUFFER:
    1237         Log(("SVGA3D_SURFACE_HINT_VERTEXBUFFER\n"));
    1238         /* Type unknown at this time; postpone buffer creation */
     1100        if (pSurface->u.pVertexBuffer)
     1101            pSurface->u.pVertexBuffer->Release();
    12391102        break;
    12401103
    12411104    case SVGA3D_SURFACE_HINT_TEXTURE:
    1242         Log(("SVGA3D_SURFACE_HINT_TEXTURE\n"));
     1105    case SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET:
     1106        if (pSurface->u.pTexture)
     1107            pSurface->u.pTexture->Release();
     1108        if (pSurface->bounce.pTexture)
     1109            pSurface->bounce.pTexture->Release();
    12431110        break;
    12441111
    12451112    case SVGA3D_SURFACE_HINT_RENDERTARGET:
    1246         Log(("SVGA3D_SURFACE_HINT_RENDERTARGET\n"));
    1247         break;
    1248 
    12491113    case SVGA3D_SURFACE_HINT_DEPTHSTENCIL:
    1250         Log(("SVGA3D_SURFACE_HINT_DEPTHSTENCIL\n"));
     1114    case SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_HINT_TEXTURE:    /** @todo actual texture surface not supported */
     1115        if (pSurface->fStencilAsTexture)
     1116            pSurface->u.pTexture->Release();
     1117        else
     1118        if (pSurface->u.pSurface)
     1119            pSurface->u.pSurface->Release();
    12511120        break;
    12521121
    12531122    default:
    1254         /* Unknown; decide later. */
    1255         break;
    1256     }
    1257 
    1258     Assert(!pSurface->u.pSurface);
    1259 
    1260     /* Allocate buffer to hold the surface data until we can move it into a D3D object */
    1261     for (uint32_t iFace=0; iFace < pSurface->cFaces; iFace++)
    1262     {
    1263         for (uint32_t i=0; i < pSurface->faces[iFace].numMipLevels; i++)
    1264         {
    1265             uint32_t idx = i + iFace * pSurface->faces[0].numMipLevels;
    1266 
    1267             Log(("vmsvga3dSurfaceDefine: face %d mip level %d (%d,%d,%d)\n", iFace, i, pSurface->pMipmapLevels[idx].size.width, pSurface->pMipmapLevels[idx].size.height, pSurface->pMipmapLevels[idx].size.depth));
    1268             Log(("vmsvga3dSurfaceDefine: cbPitch=%x cbBlock=%x \n", pSurface->cbBlock * pSurface->pMipmapLevels[idx].size.width, pSurface->cbBlock));
    1269 
    1270             pSurface->pMipmapLevels[idx].cbSurfacePitch = pSurface->cbBlock * pSurface->pMipmapLevels[idx].size.width;
    1271             pSurface->pMipmapLevels[idx].cbSurface      = pSurface->pMipmapLevels[idx].cbSurfacePitch * pSurface->pMipmapLevels[idx].size.height * pSurface->pMipmapLevels[idx].size.depth;
    1272             pSurface->pMipmapLevels[idx].pSurfaceData   = RTMemAllocZ(pSurface->pMipmapLevels[idx].cbSurface);
    1273             AssertReturn(pSurface->pMipmapLevels[idx].pSurfaceData, VERR_NO_MEMORY);
    1274         }
    1275     }
    1276     return VINF_SUCCESS;
     1123        AssertMsg(!VMSVGA3DSURFACE_HAS_HW_SURFACE(pSurface), ("type=%x\n", (pSurface->flags & VMSVGA3D_SURFACE_HINT_SWITCH_MASK)));
     1124        break;
     1125    }
     1126
     1127    if (pSurface->pQuery)
     1128        pSurface->pQuery->Release();
    12771129}
     1130
    12781131
    12791132/*
    12801133 * Release all shared surface objects.
    12811134 */
    1282 static DECLCALLBACK(int) vmsvga3dSharedSurfaceDestroyTree(PAVLU32NODECORE pNode, void *pParam)
     1135DECLCALLBACK(int) vmsvga3dSharedSurfaceDestroyTree(PAVLU32NODECORE pNode, void *pvParam)
    12831136{
    12841137    PVMSVGA3DSHAREDSURFACE pSharedSurface = (PVMSVGA3DSHAREDSURFACE)pNode;
    1285     PVMSVGA3DSURFACE       pSurface = (PVMSVGA3DSURFACE)pParam;
     1138    PVMSVGA3DSURFACE       pSurface = (PVMSVGA3DSURFACE)pvParam;
    12861139
    12871140    switch (pSurface->flags & (SVGA3D_SURFACE_HINT_INDEXBUFFER | SVGA3D_SURFACE_HINT_VERTEXBUFFER | SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET | SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_CUBEMAP))
     
    13011154    RTMemFree(pNode);
    13021155    return 0;
    1303 }
    1304 
    1305 int vmsvga3dSurfaceDestroy(PVGASTATE pThis, uint32_t sid)
    1306 {
    1307     PVMSVGA3DSTATE pState = pThis->svga.p3dState;
    1308     AssertReturn(pState, VERR_NO_MEMORY);
    1309 
    1310     if (    sid < pState->cSurfaces
    1311         &&  pState->papSurfaces[sid]->id == sid)
    1312     {
    1313         PVMSVGA3DSURFACE pSurface = pState->papSurfaces[sid];
    1314 
    1315         Log(("vmsvga3dSurfaceDestroy id %x\n", sid));
    1316 
    1317         /* Check all contexts if this surface is used as a render target or active texture. */
    1318         for (uint32_t cid = 0; cid < pState->cContexts; cid++)
    1319         {
    1320             PVMSVGA3DCONTEXT pContext = pState->papContexts[cid];
    1321             if (pContext->id == cid)
    1322             {
    1323                 for (uint32_t i = 0; i < RT_ELEMENTS(pContext->aSidActiveTexture); i++)
    1324                 {
    1325                     if (pContext->aSidActiveTexture[i] == sid)
    1326                         pContext->aSidActiveTexture[i] = SVGA3D_INVALID_ID;
    1327                 }
    1328                 if (pContext->sidRenderTarget == sid)
    1329                     pContext->sidRenderTarget = SVGA3D_INVALID_ID;
    1330             }
    1331         }
    1332 
    1333         RTAvlU32Destroy(&pSurface->pSharedObjectTree, vmsvga3dSharedSurfaceDestroyTree, pSurface);
    1334         Assert(pSurface->pSharedObjectTree == NULL);
    1335 
    1336         switch (pSurface->flags & (  SVGA3D_SURFACE_HINT_INDEXBUFFER  | SVGA3D_SURFACE_HINT_VERTEXBUFFER
    1337                                    | SVGA3D_SURFACE_HINT_TEXTURE      | SVGA3D_SURFACE_HINT_RENDERTARGET
    1338                                    | SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_CUBEMAP))
    1339         {
    1340         case SVGA3D_SURFACE_CUBEMAP:
    1341             AssertFailed(); /* @todo */
    1342             break;
    1343 
    1344         case SVGA3D_SURFACE_HINT_INDEXBUFFER:
    1345             if (pSurface->u.pIndexBuffer)
    1346                 pSurface->u.pIndexBuffer->Release();
    1347             break;
    1348 
    1349         case SVGA3D_SURFACE_HINT_VERTEXBUFFER:
    1350             if (pSurface->u.pVertexBuffer)
    1351                 pSurface->u.pVertexBuffer->Release();
    1352             break;
    1353 
    1354         case SVGA3D_SURFACE_HINT_TEXTURE:
    1355         case SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET:
    1356             if (pSurface->u.pTexture)
    1357                 pSurface->u.pTexture->Release();
    1358             if (pSurface->bounce.pTexture)
    1359                 pSurface->bounce.pTexture->Release();
    1360             break;
    1361 
    1362         case SVGA3D_SURFACE_HINT_RENDERTARGET:
    1363         case SVGA3D_SURFACE_HINT_DEPTHSTENCIL:
    1364         case SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_HINT_TEXTURE:    /* @todo actual texture surface not supported */
    1365             if (pSurface->fStencilAsTexture)
    1366                 pSurface->u.pTexture->Release();
    1367             else
    1368             if (pSurface->u.pSurface)
    1369                 pSurface->u.pSurface->Release();
    1370             break;
    1371 
    1372         default:
    1373             AssertMsg(!pSurface->u.pSurface, ("type=%x\n", (pSurface->flags & (SVGA3D_SURFACE_HINT_INDEXBUFFER | SVGA3D_SURFACE_HINT_VERTEXBUFFER | SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET | SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_CUBEMAP))));
    1374             break;
    1375         }
    1376 
    1377         if (pSurface->pMipmapLevels)
    1378         {
    1379             for (uint32_t face=0; face < pSurface->cFaces; face++)
    1380             {
    1381                 for (uint32_t i=0; i < pSurface->faces[face].numMipLevels; i++)
    1382                 {
    1383                     uint32_t idx = i + face * pSurface->faces[0].numMipLevels;
    1384                     if (pSurface->pMipmapLevels[idx].pSurfaceData)
    1385                         RTMemFree(pSurface->pMipmapLevels[idx].pSurfaceData);
    1386                 }
    1387             }
    1388             RTMemFree(pSurface->pMipmapLevels);
    1389         }
    1390         if (pSurface->pQuery)
    1391             pSurface->pQuery->Release();
    1392 
    1393         memset(pSurface, 0, sizeof(*pSurface));
    1394         pSurface->id = SVGA3D_INVALID_ID;
    1395     }
    1396     else
    1397         AssertFailedReturn(VERR_INVALID_PARAMETER);
    1398 
    1399     return VINF_SUCCESS;
    14001156}
    14011157
     
    14391195}
    14401196
    1441 #ifdef VBOX_VMSVGA3D_WITH_WINE_OPENGL
    1442 #define vmsvga3dSurfaceTrackUsage(a, b, c)
    1443 #define vmsvga3dSurfaceFlush(a, b)
    1444 #else /* !VBOX_VMSVGA3D_WITH_WINE_OPENGL */
    14451197/* Inject a query event into the D3D pipeline so we can check when usage of this surface has finished.
    14461198 * (D3D does not synchronize shared surface usage)
    14471199 */
    1448 static int vmsvga3dSurfaceTrackUsage(PVGASTATE pThis, PVMSVGA3DCONTEXT pContext, uint32_t sid)
     1200static int vmsvga3dSurfaceTrackUsage(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, PVMSVGA3DSURFACE pSurface)
    14491201{
    1450     PVMSVGA3DSTATE   pState = pThis->svga.p3dState;
    1451     PVMSVGA3DSURFACE pSurface  = pState->papSurfaces[sid];
    1452     HRESULT          hr;
    1453 
    1454     AssertReturn(sid < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
    1455     AssertReturn(sid < pState->cSurfaces && pState->papSurfaces[sid]->id == sid, VERR_INVALID_PARAMETER);
     1202#ifndef VBOX_VMSVGA3D_WITH_WINE_OPENGL
     1203    Assert(pSurface->id != SVGA3D_INVALID_ID);
    14561204
    14571205    /* Nothing to do if this surface hasn't been shared. */
     
    14591207        return VINF_SUCCESS;
    14601208
    1461     Log(("vmsvga3dSurfaceTrackUsage: track usage of surface id=%x (cid=%x)\n", sid, pContext->id));
     1209    Log(("vmsvga3dSurfaceTrackUsage: track usage of surface id=%x (cid=%x)\n", pSurface->id, pContext->id));
    14621210
    14631211    /* Release the previous query object. */
     
    14681216        pSurface->pQuery = NULL;
    14691217    }
    1470     hr = pContext->pDevice->CreateQuery(D3DQUERYTYPE_EVENT, &pSurface->pQuery);
     1218    HRESULT hr = pContext->pDevice->CreateQuery(D3DQUERYTYPE_EVENT, &pSurface->pQuery);
    14711219    AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceTrackUsage: CreateQuery failed with %x\n", hr), VERR_INTERNAL_ERROR);
    14721220
    14731221    hr = pSurface->pQuery->Issue(D3DISSUE_END);
    14741222    AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceTrackUsage: Issue failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1223#endif /* !VBOX_VMSVGA3D_WITH_WINE_OPENGL */
    14751224
    14761225    return VINF_SUCCESS;
     
    14781227
    14791228
     1229/**
     1230 * Surface ID based version of vmsvga3dSurfaceTrackUsage.
     1231 *
     1232 * @returns VBox status code.
     1233 * @param   pState              The VMSVGA3d state.
     1234 * @param   pContext            The context.
     1235 * @param   sid                 The surface ID.
     1236 */
     1237static int vmsvga3dSurfaceTrackUsageById(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, uint32_t sid)
     1238{
     1239    Assert(sid < SVGA3D_MAX_SURFACE_IDS);
     1240    AssertReturn(sid < pState->cSurfaces, VERR_INVALID_PARAMETER);
     1241    PVMSVGA3DSURFACE pSurface = pState->papSurfaces[sid];
     1242    AssertReturn(pSurface && pSurface->id == sid, VERR_INVALID_PARAMETER);
     1243
     1244    return vmsvga3dSurfaceTrackUsage(pState, pContext, pSurface);
     1245}
     1246
     1247
    14801248/* Wait for all drawing, that uses this surface, to finish. */
    1481 static int vmsvga3dSurfaceFlush(PVGASTATE pThis, PVMSVGA3DSURFACE pSurface)
     1249int vmsvga3dSurfaceFlush(PVGASTATE pThis, PVMSVGA3DSURFACE pSurface)
    14821250{
     1251#ifndef VBOX_VMSVGA3D_WITH_WINE_OPENGL
    14831252    HRESULT hr;
    14841253
     
    15021271    pSurface->pQuery->Release();
    15031272    pSurface->pQuery = NULL;
     1273#endif /* !VBOX_VMSVGA3D_WITH_WINE_OPENGL */
    15041274
    15051275    return VINF_SUCCESS;
    15061276}
    1507 #endif /* !VBOX_VMSVGA3D_WITH_WINE_OPENGL */
    1508 
    1509 int vmsvga3dSurfaceCopy(PVGASTATE pThis, SVGA3dSurfaceImageId dest, SVGA3dSurfaceImageId src, uint32_t cCopyBoxes, SVGA3dCopyBox *pBox)
     1277
     1278int vmsvga3dSurfaceCopy(PVGASTATE pThis, SVGA3dSurfaceImageId dest, SVGA3dSurfaceImageId src,
     1279                        uint32_t cCopyBoxes, SVGA3dCopyBox *pBox)
    15101280{
    15111281    PVMSVGA3DSTATE      pState = pThis->svga.p3dState;
     
    15511321
    15521322        Log(("vmsvga3dSurfaceCopy: create texture surface id=%x type=%d format=%d -> create texture\n", sidDest, pSurfaceDest->flags, pSurfaceDest->format));
    1553         rc = vmsvga3dCreateTexture(pContext, cid, pSurfaceDest);
     1323        rc = vmsvga3dBackCreateTexture(pState, pContext, cid, pSurfaceDest);
    15541324        AssertRCReturn(rc, rc);
    15551325    }
     
    16461416
    16471417            /* Track the StretchRect operation. */
    1648             vmsvga3dSurfaceTrackUsage(pThis, pContext, sidSrc);
    1649             vmsvga3dSurfaceTrackUsage(pThis, pContext, sidDest);
     1418            vmsvga3dSurfaceTrackUsage(pState, pContext, pSurfaceSrc);
     1419            vmsvga3dSurfaceTrackUsage(pState, pContext, pSurfaceDest);
    16501420
    16511421            AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceCopy: UpdateSurface failed with %x\n", hr), VERR_INTERNAL_ERROR);
     
    17521522}
    17531523
    1754 /* Create D3D texture object for the specified surface. */
    1755 static int vmsvga3dCreateTexture(PVMSVGA3DCONTEXT pContext, uint32_t idAssociatedContext, PVMSVGA3DSURFACE pSurface)
     1524
     1525/**
     1526 * Create D3D/OpenGL texture object for the specified surface.
     1527 *
     1528 * Surfaces are created when needed.
     1529 *
     1530 * @param   pState              The VMSVGA3d state.
     1531 * @param   pContext            The context.
     1532 * @param   idAssociatedContext Probably the same as pContext->id.
     1533 * @param   pSurface            The surface to create the texture for.
     1534 */
     1535int vmsvga3dBackCreateTexture(PVMSVGA3DSTATE pState, PVMSVGA3DCONTEXT pContext, uint32_t idAssociatedContext,
     1536                              PVMSVGA3DSURFACE pSurface)
     1537
    17561538{
    17571539    HRESULT hr;
     
    17731555                                              &pSurface->u.pTexture,
    17741556                                              &pSurface->hSharedObject /* might result in poor performance */);
    1775         AssertMsgReturn(hr == D3D_OK, ("vmsvga3dCreateTexture: CreateTexture INTZ failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1557        AssertMsgReturn(hr == D3D_OK, ("vmsvga3dBackCreateTexture: CreateTexture INTZ failed with %x\n", hr), VERR_INTERNAL_ERROR);
    17761558        pTexture = pSurface->u.pTexture;
    17771559
     
    17991581                                                  &pSurface->bounce.pTexture,
    18001582                                                  NULL);
    1801             AssertMsgReturn(hr == D3D_OK, ("vmsvga3dCreateTexture: CreateTexture (systemmem) failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1583            AssertMsgReturn(hr == D3D_OK, ("vmsvga3dBackCreateTexture: CreateTexture (systemmem) failed with %x\n", hr), VERR_INTERNAL_ERROR);
    18021584            pTexture = pSurface->bounce.pTexture;
    18031585        }
     
    18141596                                                  &pSurface->u.pTexture,
    18151597                                                  &pSurface->hSharedObject /* might result in poor performance */);
    1816             AssertMsgReturn(hr == D3D_OK, ("vmsvga3dCreateTexture: CreateTexture failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1598            AssertMsgReturn(hr == D3D_OK, ("vmsvga3dBackCreateTexture: CreateTexture failed with %x\n", hr), VERR_INTERNAL_ERROR);
    18171599            pTexture = pSurface->u.pTexture;
    18181600        }
     
    18231605        /* Set the mip map generation filter settings. */
    18241606        hr = pSurface->u.pTexture->SetAutoGenFilterType((D3DTEXTUREFILTERTYPE)pSurface->autogenFilter);
    1825         AssertMsg(hr == D3D_OK, ("vmsvga3dCreateTexture: SetAutoGenFilterType failed with %x\n", hr));
     1607        AssertMsg(hr == D3D_OK, ("vmsvga3dBackCreateTexture: SetAutoGenFilterType failed with %x\n", hr));
    18261608    }
    18271609
    18281610    if (pSurface->fDirty)
    18291611    {
    1830         Log(("vmsvga3dCreateTexture: sync dirty texture\n"));
     1612        Log(("vmsvga3dBackCreateTexture: sync dirty texture\n"));
    18311613        for (uint32_t i = 0; i < pSurface->faces[0].numMipLevels; i++)
    18321614        {
     
    18401622                                        0);
    18411623
    1842                 AssertMsgReturn(hr == D3D_OK, ("vmsvga3dCreateTexture: LockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
    1843 
    1844                 Log(("vmsvga3dCreateTexture: sync dirty texture mipmap level %d (pitch %x vs %x)\n", i, LockedRect.Pitch, pSurface->pMipmapLevels[i].cbSurfacePitch));
     1624                AssertMsgReturn(hr == D3D_OK, ("vmsvga3dBackCreateTexture: LockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1625
     1626                Log(("vmsvga3dBackCreateTexture: sync dirty texture mipmap level %d (pitch %x vs %x)\n", i, LockedRect.Pitch, pSurface->pMipmapLevels[i].cbSurfacePitch));
    18451627
    18461628                uint8_t *pDest = (uint8_t *)LockedRect.pBits;
     
    18551637
    18561638                hr = pTexture->UnlockRect(i /* texture level */);
    1857                 AssertMsgReturn(hr == D3D_OK, ("vmsvga3dCreateTexture: UnlockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1639                AssertMsgReturn(hr == D3D_OK, ("vmsvga3dBackCreateTexture: UnlockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
    18581640
    18591641                pSurface->pMipmapLevels[i].fDirty = false;
     
    18621644        if (pSurface->bounce.pTexture)
    18631645        {
    1864             Log(("vmsvga3dCreateTexture: sync dirty texture from bounce buffer\n"));
     1646            Log(("vmsvga3dBackCreateTexture: sync dirty texture from bounce buffer\n"));
    18651647
    18661648            hr = pContext->pDevice->UpdateTexture(pSurface->bounce.pTexture, pSurface->u.pTexture);
    1867             AssertMsgReturn(hr == D3D_OK, ("vmsvga3dCreateTexture: UpdateTexture failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1649            AssertMsgReturn(hr == D3D_OK, ("vmsvga3dBackCreateTexture: UpdateTexture failed with %x\n", hr), VERR_INTERNAL_ERROR);
    18681650
    18691651            /* We will now use the bounce texture for all memory accesses, so free our surface memory buffer. */
     
    18811663}
    18821664
    1883 int vmsvga3dSurfaceStretchBlt(PVGASTATE pThis, SVGA3dSurfaceImageId dest, SVGA3dBox destBox, SVGA3dSurfaceImageId src, SVGA3dBox srcBox, SVGA3dStretchBltMode mode)
     1665
     1666/**
     1667 * Backend worker for implementing SVGA_3D_CMD_SURFACE_STRETCHBLT.
     1668 *
     1669 * @returns VBox status code.
     1670 * @param   pThis               The VGA device instance.
     1671 * @param   pState              The VMSVGA3d state.
     1672 * @param   pDstSurface         The destination host surface.
     1673 * @param   uDstMipmap          The destination mipmap level (valid).
     1674 * @param   pDstBox             The destination box.
     1675 * @param   pSrcSurface         The source host surface.
     1676 * @param   uSrcMipmap          The source mimap level (valid).
     1677 * @param   pSrcBox             The source box.
     1678 * @param   enmMode             The strecht blt mode .
     1679 * @param   pContext            The VMSVGA3d context (already current for OGL).
     1680 */
     1681int vmsvga3dBackSurfaceStretchBlt(PVGASTATE pThis, PVMSVGA3DSTATE pState,
     1682                                  PVMSVGA3DSURFACE pDstSurface, uint32_t uDstMipmap, SVGA3dBox const *pDstBox,
     1683                                  PVMSVGA3DSURFACE pSrcSurface, uint32_t uSrcMipmap, SVGA3dBox const *pSrcBox,
     1684                                  SVGA3dStretchBltMode enmMode, PVMSVGA3DCONTEXT pContext)
    18841685{
    1885     PVMSVGA3DSTATE      pState = pThis->svga.p3dState;
    1886     PVMSVGA3DSURFACE    pSurfaceSrc;
    1887     uint32_t            sidSrc = src.sid;
    1888     PVMSVGA3DSURFACE    pSurfaceDest;
    1889     uint32_t            sidDest = dest.sid;
    1890     int                 rc = VINF_SUCCESS;
    1891     uint32_t            cid;
    1892     PVMSVGA3DCONTEXT    pContext;
    1893 
    1894     AssertReturn(pState, VERR_NO_MEMORY);
    1895     AssertReturn(sidSrc < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
    1896     AssertReturn(sidSrc < pState->cSurfaces && pState->papSurfaces[sidSrc]->id == sidSrc, VERR_INVALID_PARAMETER);
    1897     AssertReturn(sidDest < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
    1898     AssertReturn(sidDest < pState->cSurfaces && pState->papSurfaces[sidDest]->id == sidDest, VERR_INVALID_PARAMETER);
    1899 
    1900     pSurfaceSrc  = pState->papSurfaces[sidSrc];
    1901     pSurfaceDest = pState->papSurfaces[sidDest];
    1902     AssertReturn(pSurfaceSrc->faces[0].numMipLevels > src.mipmap, VERR_INVALID_PARAMETER);
    1903     AssertReturn(pSurfaceDest->faces[0].numMipLevels > dest.mipmap, VERR_INVALID_PARAMETER);
    1904 
    1905     Log(("vmsvga3dSurfaceStretchBlt: src sid=%x (%d,%d)(%d,%d) dest sid=%x (%d,%d)(%d,%d) mode=%x\n", src.sid, srcBox.x, srcBox.y, srcBox.x + srcBox.w, srcBox.y + srcBox.h, dest.sid, destBox.x, destBox.y, destBox.x + destBox.w, destBox.y + destBox.h, mode));
    1906 
    1907     /* @todo stricter checks for associated context */
    1908     cid = pSurfaceDest->idAssociatedContext;
    1909     if (cid == SVGA3D_INVALID_ID)
    1910         cid = pSurfaceSrc->idAssociatedContext;
    1911 
    1912     if (    cid >= pState->cContexts
    1913         ||  pState->papContexts[cid]->id != cid)
    1914     {
    1915         Log(("vmsvga3dSurfaceStretchBlt invalid context id!\n"));
    1916         AssertFailedReturn(VERR_INVALID_PARAMETER);
    1917     }
    1918     pContext = pState->papContexts[cid];
    1919 
    1920     if (!pSurfaceSrc->u.pSurface)
    1921     {
    1922         /* Unknown surface type; turn it into a texture, which can be used for other purposes too. */
    1923         Log(("vmsvga3dSurfaceStretchBlt: unknown src surface id=%x type=%d format=%d -> create texture\n", sidSrc, pSurfaceSrc->flags, pSurfaceSrc->format));
    1924         rc = vmsvga3dCreateTexture(pContext, cid, pSurfaceSrc);
    1925         AssertRCReturn(rc, rc);
    1926     }
    1927 
    1928     if (!pSurfaceDest->u.pSurface)
    1929     {
    1930         /* Unknown surface type; turn it into a texture, which can be used for other purposes too. */
    1931         Log(("vmsvga3dSurfaceStretchBlt: unknown dest surface id=%x type=%d format=%d -> create texture\n", sidDest, pSurfaceDest->flags, pSurfaceDest->format));
    1932         rc = vmsvga3dCreateTexture(pContext, cid, pSurfaceDest);
    1933         AssertRCReturn(rc, rc);
    1934     }
     1686    HRESULT hr;
    19351687
    19361688    /* Flush the drawing pipeline for this surface as it could be used in a shared context. */
    1937     vmsvga3dSurfaceFlush(pThis, pSurfaceSrc);
    1938     vmsvga3dSurfaceFlush(pThis, pSurfaceDest);
    1939 
    1940     bool fSrcTexture  = !!(pSurfaceSrc->flags & SVGA3D_SURFACE_HINT_TEXTURE);
    1941     bool fDestTexture = !!(pSurfaceDest->flags & SVGA3D_SURFACE_HINT_TEXTURE);
    1942 
    1943     HRESULT                 hr;
    1944     RECT                    RectSrc;
    1945     RECT                    RectDest;
    1946     D3DTEXTUREFILTERTYPE    moded3d;
    1947     IDirect3DSurface9      *pSrc;
    1948     IDirect3DSurface9      *pDest;
    1949 
    1950     RectSrc.left    = srcBox.x;
    1951     RectSrc.top     = srcBox.y;
    1952     RectSrc.right   = srcBox.x + srcBox.w;   /* exclusive */
    1953     RectSrc.bottom  = srcBox.y + srcBox.h;   /* exclusive */
    1954     RectDest.left   = destBox.x;
    1955     RectDest.top    = destBox.y;
    1956     RectDest.right  = destBox.x + destBox.w;   /* exclusive */
    1957     RectDest.bottom = destBox.y + destBox.h;   /* exclusive */
    1958 
    1959     Assert(!destBox.z && !srcBox.z);
    1960 
     1689    vmsvga3dSurfaceFlush(pThis, pSrcSurface);
     1690    vmsvga3dSurfaceFlush(pThis, pDstSurface);
     1691
     1692    RECT RectSrc;
     1693    RectSrc.left    = pSrcBox->x;
     1694    RectSrc.top     = pSrcBox->y;
     1695    RectSrc.right   = pSrcBox->x + pSrcBox->w;  /* exclusive */
     1696    RectSrc.bottom  = pSrcBox->y + pSrcBox->h;  /* exclusive */
     1697    Assert(!pSrcBox->z);
     1698
     1699    RECT RectDst;
     1700    RectDst.left   = pDstBox->x;
     1701    RectDst.top    = pDstBox->y;
     1702    RectDst.right  = pDstBox->x + pDstBox->w;  /* exclusive */
     1703    RectDst.bottom = pDstBox->y + pDstBox->h;  /* exclusive */
     1704    Assert(!pDstBox->z);
     1705
     1706    IDirect3DSurface9 *pSrc;
     1707    bool const fSrcTexture  = !!(pSrcSurface->flags & SVGA3D_SURFACE_HINT_TEXTURE);
    19611708    if (fSrcTexture)
    19621709    {
    1963         hr = pSurfaceSrc->u.pTexture->GetSurfaceLevel(src.mipmap /* Texture level */,
    1964                                                       &pSrc);
     1710        hr = pSrcSurface->u.pTexture->GetSurfaceLevel(uSrcMipmap /* Texture level */, &pSrc);
    19651711        AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceStretchBlt: GetSurfaceLevel failed with %x\n", hr), VERR_INTERNAL_ERROR);
    19661712    }
    19671713    else
    1968         pSrc = pSurfaceSrc->u.pSurface;
    1969 
    1970     if (fDestTexture)
    1971     {
    1972         hr = pSurfaceDest->u.pTexture->GetSurfaceLevel(dest.mipmap /* Texture level */,
    1973                                                       &pDest);
     1714        pSrc = pSrcSurface->u.pSurface;
     1715
     1716    IDirect3DSurface9 *pDst;
     1717    bool const fDstTexture = !!(pDstSurface->flags & SVGA3D_SURFACE_HINT_TEXTURE);
     1718    if (fDstTexture)
     1719    {
     1720        hr = pDstSurface->u.pTexture->GetSurfaceLevel(uDstMipmap /* Texture level */, &pDst);
    19741721        AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceStretchBlt: GetSurfaceLevel failed with %x\n", hr), VERR_INTERNAL_ERROR);
    19751722    }
    19761723    else
    1977         pDest = pSurfaceDest->u.pSurface;
    1978 
    1979     switch (mode)
     1724        pDst = pDstSurface->u.pSurface;
     1725
     1726    D3DTEXTUREFILTERTYPE moded3d;
     1727    switch (enmMode)
    19801728    {
    19811729    case SVGA3D_STRETCH_BLT_POINT:
     
    19931741    }
    19941742
    1995     hr = pContext->pDevice->StretchRect(pSrc, &RectSrc, pDest, &RectDest, moded3d);
     1743    hr = pContext->pDevice->StretchRect(pSrc, &RectSrc, pDst, &RectDst, moded3d);
    19961744
    19971745    /* GetSurfaceLevel increases the reference count; release the objects again. */
    1998     if (fDestTexture)
    1999         pDest->Release();
     1746    if (fDstTexture)
     1747        pDst->Release();
    20001748    if (fSrcTexture)
    20011749        pSrc->Release();
     
    20041752
    20051753    /* Track the StretchRect operation. */
    2006     vmsvga3dSurfaceTrackUsage(pThis, pContext, sidSrc);
    2007     vmsvga3dSurfaceTrackUsage(pThis, pContext, sidDest);
     1754    vmsvga3dSurfaceTrackUsage(pState, pContext, pSrcSurface);
     1755    vmsvga3dSurfaceTrackUsage(pState, pContext, pDstSurface);
    20081756
    20091757    return VINF_SUCCESS;
    20101758}
    20111759
    2012 int vmsvga3dSurfaceDMA(PVGASTATE pThis, SVGA3dGuestImage guest, SVGA3dSurfaceImageId host, SVGA3dTransferType transfer,
    2013                        uint32_t cCopyBoxes, SVGA3dCopyBox *pBoxes)
     1760
     1761/**
     1762 * Backend worker for implementing SVGA_3D_CMD_SURFACE_DMA that copies one box.
     1763 *
     1764 * @returns Failure status code or @a rc.
     1765 * @param   pThis               The VGA device instance data.
     1766 * @param   pState              The VMSVGA3d state.
     1767 * @param   pSurface            The host surface.
     1768 * @param   uHostMipmap         The host mipmap level (valid).
     1769 * @param   GuestPtr            The guest pointer.
     1770 * @param   cbSrcPitch          The guest (?) pitch.
     1771 * @param   transfer            The transfer direction.
     1772 * @param   pBox                The box to copy.
     1773 * @param   pContext            The context (for OpenGL).
     1774 * @param   rc                  The current rc for all boxes.
     1775 * @param   iBox                The current box number (for Direct 3D).
     1776 */
     1777int vmsvga3dBackSurfaceDMACopyBox(PVGASTATE pThis, PVMSVGA3DSTATE pState, PVMSVGA3DSURFACE pSurface, uint32_t uHostMipmap,
     1778                                  SVGAGuestPtr GuestPtr, uint32_t cbSrcPitch, SVGA3dTransferType transfer,
     1779                                  SVGA3dCopyBox const *pBox, PVMSVGA3DCONTEXT pContext, int rc, int iBox)
    20141780{
    2015     PVMSVGA3DSTATE          pState = pThis->svga.p3dState;
    2016     PVMSVGA3DSURFACE        pSurface;
    2017     PVMSVGA3DMIPMAPLEVEL    pMipLevel;
    2018     uint32_t                sid = host.sid;
    2019     int                     rc = VINF_SUCCESS;
    2020 
    2021     AssertReturn(pState, VERR_NO_MEMORY);
    2022     AssertReturn(sid < SVGA3D_MAX_SURFACE_IDS, VERR_INVALID_PARAMETER);
    2023     AssertReturn(sid < pState->cSurfaces && pState->papSurfaces[sid]->id == sid, VERR_INVALID_PARAMETER);
    2024 
    2025     pSurface = pState->papSurfaces[sid];
    2026     AssertReturn(pSurface->faces[0].numMipLevels > host.mipmap, VERR_INVALID_PARAMETER);
    2027     pMipLevel = &pSurface->pMipmapLevels[host.mipmap];
    2028 
    2029     if (pSurface->flags & SVGA3D_SURFACE_HINT_TEXTURE)
    2030         Log(("vmsvga3dSurfaceDMA TEXTURE guestptr gmr=%x offset=%x pitch=%x host sid=%x face=%d mipmap=%d transfer=%s cCopyBoxes=%d\n", guest.ptr.gmrId, guest.ptr.offset, guest.pitch, host.sid, host.face, host.mipmap, (transfer == SVGA3D_WRITE_HOST_VRAM) ? "READ" : "WRITE", cCopyBoxes));
    2031     else
    2032         Log(("vmsvga3dSurfaceDMA guestptr gmr=%x offset=%x pitch=%x host sid=%x face=%d mipmap=%d transfer=%s cCopyBoxes=%d\n", guest.ptr.gmrId, guest.ptr.offset, guest.pitch, host.sid, host.face, host.mipmap, (transfer == SVGA3D_WRITE_HOST_VRAM) ? "READ" : "WRITE", cCopyBoxes));
    2033 
    2034     if (!pSurface->u.pSurface)
    2035     {
    2036         AssertReturn(pSurface->pMipmapLevels[host.mipmap].pSurfaceData, VERR_INTERNAL_ERROR);
    2037 
    2038         for (unsigned i = 0; i < cCopyBoxes; i++)
    2039         {
    2040             unsigned uDestOffset;
    2041             unsigned cbSrcPitch;
    2042 
    2043             Log(("Copy box %d (%d,%d,%d)(%d,%d,%d)\n", i, pBoxes[i].srcx, pBoxes[i].srcy, pBoxes[i].srcz, pBoxes[i].w, pBoxes[i].h, pBoxes[i].d));
    2044             /* Apparently we're supposed to clip it (gmr test sample) */
    2045             if (pBoxes[i].x + pBoxes[i].w > pMipLevel->size.width)
    2046                 pBoxes[i].w = pMipLevel->size.width - pBoxes[i].x;
    2047             if (pBoxes[i].y + pBoxes[i].h > pMipLevel->size.height)
    2048                 pBoxes[i].h = pMipLevel->size.height - pBoxes[i].y;
    2049             if (pBoxes[i].z + pBoxes[i].d > pMipLevel->size.depth)
    2050                 pBoxes[i].d = pMipLevel->size.depth - pBoxes[i].z;
    2051 
    2052             if (    !pBoxes[i].w
    2053                 ||  !pBoxes[i].h
    2054                 ||  !pBoxes[i].d
    2055                 ||   pBoxes[i].x > pMipLevel->size.width
    2056                 ||   pBoxes[i].y > pMipLevel->size.height
    2057                 ||   pBoxes[i].z > pMipLevel->size.depth)
     1781    HRESULT hr = D3D_OK;
     1782    DWORD dwFlags = transfer == SVGA3D_READ_HOST_VRAM ? D3DLOCK_READONLY : 0;
     1783    bool fTexture = false;
     1784    bool fVertex = false;
     1785    bool fRenderTargetTexture = false;
     1786    switch (pSurface->flags & VMSVGA3D_SURFACE_HINT_SWITCH_MASK)
     1787    {
     1788    case SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET:
     1789        fRenderTargetTexture = true;
     1790        /* no break */
     1791    case SVGA3D_SURFACE_HINT_TEXTURE:
     1792        fTexture = true;
     1793        /* no break */
     1794    case SVGA3D_SURFACE_HINT_DEPTHSTENCIL:
     1795        if (pSurface->fStencilAsTexture)
     1796            fTexture = true;
     1797        /* no break */
     1798    case SVGA3D_SURFACE_HINT_RENDERTARGET:
     1799    {
     1800        D3DLOCKED_RECT LockedRect;
     1801        RECT Rect;
     1802
     1803        Rect.left   = pBox->x;
     1804        Rect.top    = pBox->y;
     1805        Rect.right  = pBox->x + pBox->w;   /* exclusive */
     1806        Rect.bottom = pBox->y + pBox->h;   /* exclusive */
     1807
     1808        /* @todo inefficient for VRAM buffers!! */
     1809        if (fTexture)
     1810        {
     1811            if (pSurface->bounce.pTexture)
    20581812            {
    2059                 Log(("Empty box; skip\n"));
    2060                 continue;
     1813                if (    transfer == SVGA3D_READ_HOST_VRAM
     1814                    &&  fRenderTargetTexture
     1815                    &&  iBox == 0 /* only the first time */)
     1816                {
     1817                    IDirect3DSurface9 *pSrc, *pDest;
     1818
     1819                    /* @todo stricter checks for associated context */
     1820                    uint32_t cid = pSurface->idAssociatedContext;
     1821                    if (    cid >= pState->cContexts
     1822                        ||  pState->papContexts[cid]->id != cid)
     1823                    {
     1824                        Log(("vmsvga3dSurfaceDMA invalid context id (%x - %x)!\n", cid, (cid >= pState->cContexts) ? -1 : pState->papContexts[cid]->id));
     1825                        AssertFailedReturn(VERR_INVALID_PARAMETER);
     1826                    }
     1827                    pContext = pState->papContexts[cid];
     1828
     1829                    /* @todo only sync when something was actually rendered (since the last sync) */
     1830                    Log(("vmsvga3dSurfaceDMA: sync bounce buffer\n"));
     1831                    hr = pSurface->bounce.pTexture->GetSurfaceLevel(uHostMipmap, &pDest);
     1832                    AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: GetSurfaceLevel failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1833
     1834                    hr = pSurface->u.pTexture->GetSurfaceLevel(uHostMipmap, &pSrc);
     1835                    AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: GetSurfaceLevel failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1836
     1837                    hr = pContext->pDevice->GetRenderTargetData(pSrc, pDest);
     1838                    AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: GetRenderTargetData failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1839
     1840                    pSrc->Release();
     1841                    pDest->Release();
     1842                }
     1843
     1844                hr = pSurface->bounce.pTexture->LockRect(uHostMipmap, /* texture level */
     1845                                                         &LockedRect,
     1846                                                         &Rect,
     1847                                                         dwFlags);
    20611848            }
    2062 
    2063             uDestOffset = pBoxes[i].x * pSurface->cbBlock + pBoxes[i].y * pMipLevel->cbSurfacePitch + pBoxes[i].z * pMipLevel->size.height * pMipLevel->cbSurfacePitch;
    2064             AssertReturn(uDestOffset + pBoxes[i].w * pSurface->cbBlock * pBoxes[i].h * pBoxes[i].d <= pMipLevel->cbSurface, VERR_INTERNAL_ERROR);
    2065 
    2066             cbSrcPitch = (guest.pitch == 0) ? pBoxes[i].w * pSurface->cbBlock : guest.pitch;
    2067 
    2068             rc = vmsvgaGMRTransfer(pThis,
    2069                                     transfer,
    2070                                     (uint8_t *)pMipLevel->pSurfaceData + uDestOffset,
    2071                                     pMipLevel->cbSurfacePitch,
    2072                                     guest.ptr,
    2073                                     pBoxes[i].srcx * pSurface->cbBlock + (pBoxes[i].srcy + pBoxes[i].srcz * pBoxes[i].h) * cbSrcPitch,
    2074                                     cbSrcPitch,
    2075                                     pBoxes[i].w * pSurface->cbBlock,
    2076                                     pBoxes[i].d * pBoxes[i].h);
    2077 
    2078             Log4(("first line:\n%.*Rhxd\n", pMipLevel->cbSurfacePitch, pMipLevel->pSurfaceData));
    2079 
    2080             AssertRC(rc);
    2081         }
    2082         pSurface->pMipmapLevels[host.mipmap].fDirty = true;
    2083         pSurface->fDirty = true;
    2084     }
    2085     else
    2086     {
    2087         HRESULT hr = D3D_OK;
    2088         DWORD   dwFlags = 0;
    2089 
    2090         /* Flush the drawing pipeline for this surface as it could be used in a shared context. */
    2091         vmsvga3dSurfaceFlush(pThis, pSurface);
    2092 
    2093         if (transfer == SVGA3D_READ_HOST_VRAM)
    2094             dwFlags |= D3DLOCK_READONLY;
    2095 
    2096         for (unsigned i = 0; i < cCopyBoxes; i++)
    2097         {
    2098             bool fTexture = false;
    2099             bool fVertex = false;
    2100             bool fRenderTargetTexture = false;
    2101             unsigned cbSrcPitch;
    2102 
    2103             /* Apparently we're supposed to clip it (gmr test sample) */
    2104             if (pBoxes[i].x + pBoxes[i].w > pMipLevel->size.width)
    2105                 pBoxes[i].w = pMipLevel->size.width - pBoxes[i].x;
    2106             if (pBoxes[i].y + pBoxes[i].h > pMipLevel->size.height)
    2107                 pBoxes[i].h = pMipLevel->size.height - pBoxes[i].y;
    2108             if (pBoxes[i].z + pBoxes[i].d > pMipLevel->size.depth)
    2109                 pBoxes[i].d = pMipLevel->size.depth - pBoxes[i].z;
    2110 
    2111             Assert((pBoxes[i].d == 1 || pBoxes[i].d == 0) && pBoxes[i].z == 0);
    2112 
    2113             if (    !pBoxes[i].w
    2114                 ||  !pBoxes[i].h
    2115                 ||   pBoxes[i].x > pMipLevel->size.width
    2116                 ||   pBoxes[i].y > pMipLevel->size.height)
     1849            else
     1850                hr = pSurface->u.pTexture->LockRect(uHostMipmap, /* texture level */
     1851                                                    &LockedRect,
     1852                                                    &Rect,
     1853                                                    dwFlags);
     1854        }
     1855        else
     1856            hr = pSurface->u.pSurface->LockRect(&LockedRect,
     1857                                                &Rect,
     1858                                                dwFlags);
     1859        AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: LockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1860
     1861        if (fTexture)
     1862            Log(("Lock TEXTURE (bounce=%d) memory for rectangle (%d,%d)(%d,%d)\n", !!(pSurface->bounce.pTexture), Rect.left, Rect.top, Rect.right, Rect.bottom));
     1863        else
     1864            Log(("Lock %s memory for rectangle (%d,%d)(%d,%d)\n", (pSurface->flags & SVGA3D_SURFACE_HINT_DEPTHSTENCIL) ? "DEPTH-STENCIL" : "RENDERTARGET", Rect.left, Rect.top, Rect.right, Rect.bottom));
     1865
     1866        rc = vmsvgaGMRTransfer(pThis,
     1867                               transfer,
     1868                               (uint8_t *)LockedRect.pBits,
     1869                               LockedRect.Pitch,
     1870                               GuestPtr,
     1871                               pBox->srcx * pSurface->cbBlock + pBox->srcy * cbSrcPitch,
     1872                               cbSrcPitch,
     1873                               pBox->w * pSurface->cbBlock,
     1874                               pBox->h);
     1875        AssertRC(rc);
     1876
     1877        Log4(("first line:\n%.*Rhxd\n", pBox->w * pSurface->cbBlock, LockedRect.pBits));
     1878
     1879        if (fTexture)
     1880        {
     1881            if (pSurface->bounce.pTexture)
    21171882            {
    2118                 Log(("Empty box; skip\n"));
    2119                 continue;
     1883                hr = pSurface->bounce.pTexture->UnlockRect(uHostMipmap);
     1884                AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: UnlockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1885
     1886                if (transfer == SVGA3D_WRITE_HOST_VRAM)
     1887                {
     1888                    /* @todo stricter checks for associated context */
     1889                    uint32_t cid = pSurface->idAssociatedContext;
     1890                    if (    cid >= pState->cContexts
     1891                        ||  pState->papContexts[cid]->id != cid)
     1892                    {
     1893                        Log(("vmsvga3dSurfaceDMA invalid context id!\n"));
     1894                        AssertFailedReturn(VERR_INVALID_PARAMETER);
     1895                    }
     1896                    pContext = pState->papContexts[cid];
     1897
     1898                    Log(("vmsvga3dSurfaceDMA: sync texture from bounce buffer\n"));
     1899
     1900                    /* Copy the new contents to the actual texture object. */
     1901                    hr = pContext->pDevice->UpdateTexture(pSurface->bounce.pTexture, pSurface->u.pTexture);
     1902                    AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: UpdateTexture failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1903
     1904                    /* Track the copy operation. */
     1905                    vmsvga3dSurfaceTrackUsage(pState, pContext, pSurface);
     1906                }
    21201907            }
    2121 
    2122             cbSrcPitch = (guest.pitch == 0) ? pBoxes[i].w * pSurface->cbBlock : guest.pitch;
    2123 
    2124             switch (pSurface->flags & (SVGA3D_SURFACE_HINT_INDEXBUFFER | SVGA3D_SURFACE_HINT_VERTEXBUFFER | SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET | SVGA3D_SURFACE_HINT_DEPTHSTENCIL | SVGA3D_SURFACE_CUBEMAP))
    2125             {
    2126             case SVGA3D_SURFACE_HINT_TEXTURE | SVGA3D_SURFACE_HINT_RENDERTARGET:
    2127                 fRenderTargetTexture = true;
    2128                 /* no break */
    2129             case SVGA3D_SURFACE_HINT_TEXTURE:
    2130                 fTexture = true;
    2131                 /* no break */
    2132             case SVGA3D_SURFACE_HINT_DEPTHSTENCIL:
    2133                 if (pSurface->fStencilAsTexture)
    2134                     fTexture = true;
    2135                 /* no break */
    2136             case SVGA3D_SURFACE_HINT_RENDERTARGET:
    2137             {
    2138                 D3DLOCKED_RECT LockedRect;
    2139                 RECT Rect;
    2140 
    2141                 Rect.left   = pBoxes[i].x;
    2142                 Rect.top    = pBoxes[i].y;
    2143                 Rect.right  = pBoxes[i].x + pBoxes[i].w;   /* exclusive */
    2144                 Rect.bottom = pBoxes[i].y + pBoxes[i].h;   /* exclusive */
    2145 
    2146                 /* @todo inefficient for VRAM buffers!! */
    2147                 if (fTexture)
    2148                 {
    2149                     if (pSurface->bounce.pTexture)
    2150                     {
    2151                         if (    transfer == SVGA3D_READ_HOST_VRAM
    2152                             &&  fRenderTargetTexture
    2153                             &&  i == 0 /* only the first time */)
    2154                         {
    2155                             IDirect3DSurface9 *pSrc, *pDest;
    2156 
    2157                             /* @todo stricter checks for associated context */
    2158                             uint32_t cid = pSurface->idAssociatedContext;
    2159                             if (    cid >= pState->cContexts
    2160                                 ||  pState->papContexts[cid]->id != cid)
    2161                             {
    2162                                 Log(("vmsvga3dSurfaceDMA invalid context id (%x - %x)!\n", cid, (cid >= pState->cContexts) ? -1 : pState->papContexts[cid]->id));
    2163                                 AssertFailedReturn(VERR_INVALID_PARAMETER);
    2164                             }
    2165                             PVMSVGA3DCONTEXT pContext = pState->papContexts[cid];
    2166 
    2167                             /* @todo only sync when something was actually rendered (since the last sync) */
    2168                             Log(("vmsvga3dSurfaceDMA: sync bounce buffer\n"));
    2169                             hr = pSurface->bounce.pTexture->GetSurfaceLevel(host.mipmap, &pDest);
    2170                             AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: GetSurfaceLevel failed with %x\n", hr), VERR_INTERNAL_ERROR);
    2171 
    2172                             hr = pSurface->u.pTexture->GetSurfaceLevel(host.mipmap, &pSrc);
    2173                             AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: GetSurfaceLevel failed with %x\n", hr), VERR_INTERNAL_ERROR);
    2174 
    2175                             hr = pContext->pDevice->GetRenderTargetData(pSrc, pDest);
    2176                             AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: GetRenderTargetData failed with %x\n", hr), VERR_INTERNAL_ERROR);
    2177 
    2178                             pSrc->Release();
    2179                             pDest->Release();
    2180                         }
    2181 
    2182                         hr = pSurface->bounce.pTexture->LockRect(host.mipmap, /* texture level */
    2183                                                                  &LockedRect,
    2184                                                                  &Rect,
    2185                                                                  dwFlags);
    2186                     }
    2187                     else
    2188                         hr = pSurface->u.pTexture->LockRect(host.mipmap, /* texture level */
    2189                                                             &LockedRect,
    2190                                                             &Rect,
    2191                                                             dwFlags);
    2192                 }
    2193                 else
    2194                     hr = pSurface->u.pSurface->LockRect(&LockedRect,
    2195                                                         &Rect,
    2196                                                         dwFlags);
    2197                 AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: LockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
    2198 
    2199                 if (fTexture)
    2200                     Log(("Lock TEXTURE (bounce=%d) memory for rectangle (%d,%d)(%d,%d)\n", !!(pSurface->bounce.pTexture), Rect.left, Rect.top, Rect.right, Rect.bottom));
    2201                 else
    2202                     Log(("Lock %s memory for rectangle (%d,%d)(%d,%d)\n", (pSurface->flags & SVGA3D_SURFACE_HINT_DEPTHSTENCIL) ? "DEPTH-STENCIL" : "RENDERTARGET", Rect.left, Rect.top, Rect.right, Rect.bottom));
    2203 
    2204                 rc = vmsvgaGMRTransfer(pThis,
    2205                                        transfer,
    2206                                        (uint8_t *)LockedRect.pBits,
    2207                                        LockedRect.Pitch,
    2208                                        guest.ptr,
    2209                                        pBoxes[i].srcx * pSurface->cbBlock + pBoxes[i].srcy * cbSrcPitch,
    2210                                        cbSrcPitch,
    2211                                        pBoxes[i].w * pSurface->cbBlock,
    2212                                        pBoxes[i].h);
    2213                 AssertRC(rc);
    2214 
    2215                 Log4(("first line:\n%.*Rhxd\n", pBoxes[i].w * pSurface->cbBlock, LockedRect.pBits));
    2216 
    2217                 if (fTexture)
    2218                 {
    2219                     if (pSurface->bounce.pTexture)
    2220                     {
    2221                         hr = pSurface->bounce.pTexture->UnlockRect(host.mipmap);
    2222                         AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: UnlockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
    2223 
    2224                         if (transfer == SVGA3D_WRITE_HOST_VRAM)
    2225                         {
    2226                             /* @todo stricter checks for associated context */
    2227                             uint32_t cid = pSurface->idAssociatedContext;
    2228                             if (    cid >= pState->cContexts
    2229                                 ||  pState->papContexts[cid]->id != cid)
    2230                             {
    2231                                 Log(("vmsvga3dSurfaceDMA invalid context id!\n"));
    2232                                 AssertFailedReturn(VERR_INVALID_PARAMETER);
    2233                             }
    2234                             PVMSVGA3DCONTEXT pContext = pState->papContexts[cid];
    2235 
    2236                             Log(("vmsvga3dSurfaceDMA: sync texture from bounce buffer\n"));
    2237 
    2238                             /* Copy the new contents to the actual texture object. */
    2239                             hr = pContext->pDevice->UpdateTexture(pSurface->bounce.pTexture, pSurface->u.pTexture);
    2240                             AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: UpdateTexture failed with %x\n", hr), VERR_INTERNAL_ERROR);
    2241 
    2242                             /* Track the copy operation. */
    2243                             vmsvga3dSurfaceTrackUsage(pThis, pContext, pSurface->id);
    2244                         }
    2245                     }
    2246                     else
    2247                         hr = pSurface->u.pTexture->UnlockRect(host.mipmap);
    2248                 }
    2249                 else
    2250                     hr = pSurface->u.pSurface->UnlockRect();
    2251                 AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: UnlockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
    2252                 break;
    2253             }
    2254 
    2255             case SVGA3D_SURFACE_HINT_VERTEXBUFFER:
    2256                 fVertex = true;
    2257                 /* no break */
    2258 
    2259             case SVGA3D_SURFACE_HINT_INDEXBUFFER:
    2260             {
    2261                 uint8_t *pData;
    2262                 unsigned uDestOffset;
    2263 
    2264                 uDestOffset = pBoxes[i].x * pSurface->cbBlock + pBoxes[i].y * pSurface->pMipmapLevels[host.mipmap].cbSurfacePitch;
    2265                 AssertReturn(uDestOffset + pBoxes[i].w * pSurface->cbBlock + (pBoxes[i].h - 1) * pSurface->pMipmapLevels[host.mipmap].cbSurfacePitch <= pSurface->pMipmapLevels[host.mipmap].cbSurface, VERR_INTERNAL_ERROR);
    2266 
    2267                 /** @todo lock only as much as we really need */
    2268                 if (fVertex)
    2269                     hr = pSurface->u.pVertexBuffer->Lock(0, 0, (void **)&pData, dwFlags);
    2270                 else
    2271                     hr = pSurface->u.pIndexBuffer->Lock(0, 0, (void **)&pData, dwFlags);
    2272                 AssertMsg(hr == D3D_OK, ("vmsvga3dSurfaceDMA: Lock %s failed with %x\n", (fVertex) ? "vertex" : "index", hr));
    2273 
    2274                 Log(("Lock %s memory for rectangle (%d,%d)(%d,%d)\n", (fVertex) ? "vertex" : "index", pBoxes[i].x, pBoxes[i].y, pBoxes[i].x + pBoxes[i].w, pBoxes[i].y + pBoxes[i].h));
    2275 
    2276                 rc = vmsvgaGMRTransfer(pThis,
    2277                                        transfer,
    2278                                        pData + uDestOffset,
    2279                                        pSurface->pMipmapLevels[host.mipmap].cbSurfacePitch,
    2280                                        guest.ptr,
    2281                                        pBoxes[i].srcx * pSurface->cbBlock + pBoxes[i].srcy * cbSrcPitch,
    2282                                        cbSrcPitch,
    2283                                        pBoxes[i].w * pSurface->cbBlock,
    2284                                        pBoxes[i].h);
    2285                 AssertRC(rc);
    2286 
    2287                 Log4(("first line:\n%.*Rhxd\n", cbSrcPitch, pData));
    2288 
    2289                 if (fVertex)
    2290                     hr = pSurface->u.pVertexBuffer->Unlock();
    2291                 else
    2292                     hr = pSurface->u.pIndexBuffer->Unlock();
    2293                 AssertMsg(hr == D3D_OK, ("vmsvga3dSurfaceDMA: Unlock %s failed with %x\n", (fVertex) ? "vertex" : "index", hr));
    2294                 break;
    2295             }
    2296 
    2297             default:
    2298                 AssertFailed();
    2299                 break;
    2300             }
    2301         }
    2302     }
     1908            else
     1909                hr = pSurface->u.pTexture->UnlockRect(uHostMipmap);
     1910        }
     1911        else
     1912            hr = pSurface->u.pSurface->UnlockRect();
     1913        AssertMsgReturn(hr == D3D_OK, ("vmsvga3dSurfaceDMA: UnlockRect failed with %x\n", hr), VERR_INTERNAL_ERROR);
     1914        break;
     1915    }
     1916
     1917    case SVGA3D_SURFACE_HINT_VERTEXBUFFER:
     1918        fVertex = true;
     1919        /* no break */
     1920
     1921    case SVGA3D_SURFACE_HINT_INDEXBUFFER:
     1922    {
     1923        uint8_t *pData;
     1924        unsigned uDestOffset;
     1925
     1926        uDestOffset = pBox->x * pSurface->cbBlock + pBox->y * pSurface->pMipmapLevels[uHostMipmap].cbSurfacePitch;
     1927        AssertReturn(uDestOffset + pBox->w * pSurface->cbBlock + (pBox->h - 1) * pSurface->pMipmapLevels[uHostMipmap].cbSurfacePitch <= pSurface->pMipmapLevels[uHostMipmap].cbSurface, VERR_INTERNAL_ERROR);
     1928
     1929        /** @todo lock only as much as we really need */
     1930        if (fVertex)
     1931            hr = pSurface->u.pVertexBuffer->Lock(0, 0, (void **)&pData, dwFlags);
     1932        else
     1933            hr = pSurface->u.pIndexBuffer->Lock(0, 0, (void **)&pData, dwFlags);
     1934        AssertMsg(hr == D3D_OK, ("vmsvga3dSurfaceDMA: Lock %s failed with %x\n", (fVertex) ? "vertex" : "index", hr));
     1935
     1936        Log(("Lock %s memory for rectangle (%d,%d)(%d,%d)\n", (fVertex) ? "vertex" : "index", pBox->x, pBox->y, pBox->x + pBox->w, pBox->y + pBox->h));
     1937
     1938        rc = vmsvgaGMRTransfer(pThis,
     1939                               transfer,
     1940                               pData + uDestOffset,
     1941                               pSurface->pMipmapLevels[uHostMipmap].cbSurfacePitch,
     1942                               GuestPtr,
     1943                               pBox->srcx * pSurface->cbBlock + pBox->srcy * cbSrcPitch,
     1944                               cbSrcPitch,
     1945                               pBox->w * pSurface->cbBlock,
     1946                               pBox->h);
     1947        AssertRC(rc);
     1948
     1949        Log4(("first line:\n%.*Rhxd\n", cbSrcPitch, pData));
     1950
     1951        if (fVertex)
     1952            hr = pSurface->u.pVertexBuffer->Unlock();
     1953        else
     1954            hr = pSurface->u.pIndexBuffer->Unlock();
     1955        AssertMsg(hr == D3D_OK, ("vmsvga3dSurfaceDMA: Unlock %s failed with %x\n", (fVertex) ? "vertex" : "index", hr));
     1956        break;
     1957    }
     1958
     1959    default:
     1960        AssertFailed();
     1961        break;
     1962    }
     1963
    23031964    return rc;
    23041965}
     1966
    23051967
    23061968int vmsvga3dSurfaceBlitToScreen(PVGASTATE pThis, uint32_t dest, SVGASignedRect destRect, SVGA3dSurfaceImageId src, SVGASignedRect srcRect, uint32_t cRects, SVGASignedRect *pRect)
     
    24572119        /* Unknown surface type; turn it into a texture. */
    24582120        Log(("vmsvga3dGenerateMipmaps: unknown src surface id=%x type=%d format=%d -> create texture\n", sid, pSurface->flags, pSurface->format));
    2459         rc = vmsvga3dCreateTexture(pContext, cid, pSurface);
     2121        rc = vmsvga3dBackCreateTexture(pState, pContext, cid, pSurface);
    24602122        AssertRCReturn(rc, rc);
    24612123    }
     
    28542516}
    28552517
    2856 #ifdef VBOX_VMSVGA3D_WITH_WINE_OPENGL
    2857 #define vmsvga3dContextTrackUsage(pThis, pContext)
    2858 #else
    28592518static int vmsvga3dContextTrackUsage(PVGASTATE pThis, PVMSVGA3DCONTEXT pContext)
    28602519{
     2520#ifndef VBOX_VMSVGA3D_WITH_WINE_OPENGL
     2521    PVMSVGA3DSTATE pState = pThis->svga.p3dState;
     2522    AssertReturn(pState, VERR_NO_MEMORY);
     2523
    28612524    /* Inject fences to make sure we can track surface usage in case the client wants to reuse it in another context. */
    28622525    for (uint32_t i = 0; i < RT_ELEMENTS(pContext->aSidActiveTexture); i++)
    28632526    {
    28642527        if (pContext->aSidActiveTexture[i] != SVGA3D_INVALID_ID)
    2865             vmsvga3dSurfaceTrackUsage(pThis, pContext, pContext->aSidActiveTexture[i]);
     2528            vmsvga3dSurfaceTrackUsageById(pState, pContext, pContext->aSidActiveTexture[i]);
    28662529    }
    28672530    if (pContext->sidRenderTarget != SVGA3D_INVALID_ID)
    2868         vmsvga3dSurfaceTrackUsage(pThis, pContext, pContext->sidRenderTarget);
     2531        vmsvga3dSurfaceTrackUsageById(pState, pContext, pContext->sidRenderTarget);
     2532#endif
    28692533    return VINF_SUCCESS;
    28702534}
    2871 #endif
    28722535
    28732536/* Handle resize */
     
    40633726            {
    40643727                Log(("vmsvga3dSetRenderTarget: Creating stencil surface as texture!\n"));
    4065                 int rc = vmsvga3dCreateTexture(pContext, cid, pRenderTarget);
     3728                int rc = vmsvga3dBackCreateTexture(pState, pContext, cid, pRenderTarget);
    40663729                AssertRC(rc);   /* non-fatal */
    40673730            }
     
    41743837            {
    41753838                Log(("vmsvga3dSetRenderTarget: create texture to be used as render target; surface id=%x type=%d format=%d -> create texture\n", target.sid, pRenderTarget->flags, pRenderTarget->format));
    4176                 int rc = vmsvga3dCreateTexture(pContext, cid, pRenderTarget);
     3839                int rc = vmsvga3dBackCreateTexture(pState, pContext, cid, pRenderTarget);
    41773840                AssertRCReturn(rc, rc);
    41783841            }
     
    45324195                    Assert(pSurface->idAssociatedContext == SVGA3D_INVALID_ID);
    45334196                    Log(("CreateTexture (%d,%d) level=%d fUsage=%x format=%x\n", pSurface->pMipmapLevels[0].size.width, pSurface->pMipmapLevels[0].size.height, pSurface->faces[0].numMipLevels, pSurface->fUsageD3D, pSurface->formatD3D));
    4534                     int rc = vmsvga3dCreateTexture(pContext, cid, pSurface);
     4197                    int rc = vmsvga3dBackCreateTexture(pState, pContext, cid, pSurface);
    45354198                    AssertRCReturn(rc, rc);
    45364199                }
     
    49274590    /* Make sure we can track drawing usage of active render targets. */
    49284591    if (pContext->sidRenderTarget != SVGA3D_INVALID_ID)
    4929         vmsvga3dSurfaceTrackUsage(pThis, pContext, pContext->sidRenderTarget);
     4592        vmsvga3dSurfaceTrackUsageById(pState, pContext, pContext->sidRenderTarget);
    49304593
    49314594    return VINF_SUCCESS;
  • trunk/src/VBox/Devices/Graphics/DevVGA-SVGA3d.h

    r57149 r57151  
    6161int vmsvga3dSurfaceDestroy(PVGASTATE pThis, uint32_t sid);
    6262int vmsvga3dSurfaceCopy(PVGASTATE pThis, SVGA3dSurfaceImageId dest, SVGA3dSurfaceImageId src, uint32_t cCopyBoxes, SVGA3dCopyBox *pBox);
    63 int vmsvga3dSurfaceStretchBlt(PVGASTATE pThis, SVGA3dSurfaceImageId dest, SVGA3dBox destBox, SVGA3dSurfaceImageId src, SVGA3dBox srcBox, SVGA3dStretchBltMode mode);
     63int vmsvga3dSurfaceStretchBlt(PVGASTATE pThis, SVGA3dSurfaceImageId const *pDstSfcImg, SVGA3dBox const *pDstBox,
     64                              SVGA3dSurfaceImageId const *pSrcSfcImg, SVGA3dBox const *pSrcBox, SVGA3dStretchBltMode enmMode);
    6465int vmsvga3dSurfaceDMA(PVGASTATE pThis, SVGA3dGuestImage guest, SVGA3dSurfaceImageId host, SVGA3dTransferType transfer, uint32_t cCopyBoxes, SVGA3dCopyBox *pBoxes);
    6566int vmsvga3dSurfaceBlitToScreen(PVGASTATE pThis, uint32_t dest, SVGASignedRect destRect, SVGA3dSurfaceImageId src, SVGASignedRect srcRect, uint32_t cRects, SVGASignedRect *pRect);
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette