[PATCH 6/6] d3d9/tests: d3d9ex video memory accounting tests

Stefan Dösinger stefan at codeweavers.com
Tue May 14 16:46:05 CDT 2013


These tests have the potential to break on Windows when other
applications create or release a large number of video memory resources
while the test is running.

I'm not testing video memory exhaustion, as that might lead to system
memory exhaustion in systems that have roughly the same amount of video
memory and system memory.
---
 dlls/d3d9/tests/d3d9ex.c | 49 ++++++++++++++++++++++++++++++++++++++++
 dlls/d3d9/tests/device.c | 58 ++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 107 insertions(+)

diff --git a/dlls/d3d9/tests/d3d9ex.c b/dlls/d3d9/tests/d3d9ex.c
index 5e5524e..2deef76 100644
--- a/dlls/d3d9/tests/d3d9ex.c
+++ b/dlls/d3d9/tests/d3d9ex.c
@@ -908,6 +908,54 @@ done:
     DestroyWindow(window);
 }
 
+static void test_vidmem_accounting(void)
+{
+    IDirect3DDevice9Ex *device;
+    unsigned int i;
+    HWND window;
+    HRESULT hr = D3D_OK;
+    ULONG ref;
+    UINT vidmem_start, vidmem_end;
+    INT diff;
+    IDirect3DTexture9 *textures[20];
+
+    window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW,
+            0, 0, 640, 480, 0, 0, 0, 0);
+    if (!(device = create_device(window, window, TRUE)))
+    {
+        skip("Failed to create a D3D device, skipping tests.\n");
+        goto done;
+    }
+
+    vidmem_start = IDirect3DDevice9_GetAvailableTextureMem(device);
+    memset(textures, 0, sizeof(textures));
+    for (i = 0; i < 20 && SUCCEEDED(hr); i++)
+    {
+        hr = IDirect3DDevice9_CreateTexture(device, 1024, 1024, 1, D3DUSAGE_RENDERTARGET,
+                D3DFMT_X8R8G8B8, D3DPOOL_DEFAULT, &textures[i], NULL);
+        /* No D3DERR_OUTOFVIDEOMEMORY in d3d9ex */
+        ok(SUCCEEDED(hr) || hr == E_OUTOFMEMORY, "Failed to create texture, hr %#x.\n", hr);
+    }
+    vidmem_end = IDirect3DDevice9_GetAvailableTextureMem(device);
+
+    diff = vidmem_start - vidmem_end;
+    diff = abs(diff);
+    ok(diff < 1024 * 1024, "Expected a video memory difference of less than 1 MB, got %u MB.\n",
+            diff / 1024 / 1024);
+
+    for (i = 0; i < 20; i++)
+    {
+        if (textures[i])
+            IDirect3DTexture9_Release(textures[i]);
+    }
+
+    ref = IDirect3DDevice9_Release(device);
+    ok(ref == 0, "The device was not properly freed: refcount %u.\n", ref);
+
+done:
+    DestroyWindow(window);
+}
+
 START_TEST(d3d9ex)
 {
     d3d9_handle = LoadLibraryA("d3d9.dll");
@@ -935,4 +983,5 @@ START_TEST(d3d9ex)
     test_texture_sysmem_create();
     test_reset();
     test_reset_resources();
+    test_vidmem_accounting();
 }
diff --git a/dlls/d3d9/tests/device.c b/dlls/d3d9/tests/device.c
index 3283a6e..abf565a 100644
--- a/dlls/d3d9/tests/device.c
+++ b/dlls/d3d9/tests/device.c
@@ -6396,6 +6396,63 @@ done:
 
 }
 
+static void test_vidmem_accounting(void)
+{
+    IDirect3DDevice9 *device;
+    IDirect3D9 *d3d9;
+    ULONG refcount;
+    HWND window;
+    HRESULT hr = D3D_OK;
+    IDirect3DTexture9 *textures[20];
+    unsigned int i;
+    UINT vidmem_start, vidmem_end, diff;
+
+    if (!(d3d9 = pDirect3DCreate9(D3D_SDK_VERSION)))
+    {
+        skip("Failed to create IDirect3D9 object, skipping tests.\n");
+        return;
+    }
+
+    window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW,
+            0, 0, 640, 480, 0, 0, 0, 0);
+    if (!(device = create_device(d3d9, window, window, TRUE)))
+    {
+        skip("Failed to create a D3D device, skipping tests.\n");
+        IDirect3D9_Release(d3d9);
+        DestroyWindow(window);
+        return;
+    }
+
+    vidmem_start = IDirect3DDevice9_GetAvailableTextureMem(device);
+    memset(textures, 0, sizeof(textures));
+    for (i = 0; i < sizeof(textures) / sizeof(*textures) && SUCCEEDED(hr); i++)
+    {
+        hr = IDirect3DDevice9_CreateTexture(device, 1024, 1024, 1, D3DUSAGE_RENDERTARGET,
+                D3DFMT_X8R8G8B8, D3DPOOL_DEFAULT, &textures[i], NULL);
+        /* D3DERR_OUTOFVIDEOMEMORY is returned when the card runs out of video memory
+         * E_FAIL is returned on address space or system memory exhaustion */
+        ok(SUCCEEDED(hr) || hr == D3DERR_OUTOFVIDEOMEMORY || hr == E_OUTOFMEMORY,
+                "Failed to create texture, hr %#x.\n", hr);
+    }
+    vidmem_end = IDirect3DDevice9_GetAvailableTextureMem(device);
+
+    ok(vidmem_start > vidmem_end, "Expected available texture memory to decrease during texture creation.\n");
+    diff = vidmem_start - vidmem_end;
+    ok(diff > 1024 * 1024 * 2 * i, "Expected a video memory difference of at least %u MB, got %u MB.\n",
+            2 * i, diff / 1024 / 1024);
+
+    for (i = 0; i < sizeof(textures) / sizeof(*textures); i++)
+    {
+        if (textures[i])
+            IDirect3DTexture9_Release(textures[i]);
+    }
+
+    refcount = IDirect3DDevice9_Release(device);
+    ok(!refcount, "Device has %u references left.\n", refcount);
+    IDirect3D9_Release(d3d9);
+    DestroyWindow(window);
+}
+
 START_TEST(device)
 {
     HMODULE d3d9_handle = LoadLibraryA( "d3d9.dll" );
@@ -6485,6 +6542,7 @@ START_TEST(device)
         test_swvp_buffer();
         test_rtpatch();
         test_npot_textures();
+        test_vidmem_accounting();
     }
 
 out:
-- 
1.8.1.5




More information about the wine-patches mailing list