[PATCH 5/5] ddraw/tests: Test palette alpha behavior.

Stefan Dösinger stefan at codeweavers.com
Wed May 7 08:16:38 CDT 2014


What I care about here is that setting peFlags != 0 doesn't cause errors
either during ddraw palette creation or DIB section creation. peFlags
isn't an alpha channel, but P8 textures abuse it that way, hence the
name of the test. It probably has deeper meaning in DDSCL_NORMAL when
the X server is running in 8 bit paletteindexed mode, but I don't think
we really care about this.

The DDERR_CANTCREATEDC error happens on the Win2k testbot, and only in
ddraw1 and ddraw2. The same VM executes the ddraw4 and 7 tests and
returns a working device context.
---
 dlls/ddraw/tests/ddraw1.c | 158 +++++++++++++++++++++++++++++++++++++++++++
 dlls/ddraw/tests/ddraw2.c | 166 ++++++++++++++++++++++++++++++++++++++++++++++
 dlls/ddraw/tests/ddraw4.c | 154 ++++++++++++++++++++++++++++++++++++++++++
 dlls/ddraw/tests/ddraw7.c | 154 ++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 632 insertions(+)

diff --git a/dlls/ddraw/tests/ddraw1.c b/dlls/ddraw/tests/ddraw1.c
index 7dd3412..ef07b97 100644
--- a/dlls/ddraw/tests/ddraw1.c
+++ b/dlls/ddraw/tests/ddraw1.c
@@ -5315,6 +5315,163 @@ static void test_palette_gdi(void)
     DestroyWindow(window);
 }
 
+static void test_palette_alpha(void)
+{
+    IDirectDrawSurface *surface;
+    DDSURFACEDESC surface_desc;
+    IDirectDraw *ddraw;
+    IDirectDrawPalette *palette;
+    ULONG refcount;
+    HWND window;
+    HRESULT hr;
+    PALETTEENTRY palette_entries[256];
+    unsigned int i;
+    static const struct
+    {
+        DWORD caps, flags;
+        BOOL attach_allowed;
+        const char *name;
+    }
+    test_data[] =
+    {
+        {DDSCAPS_OFFSCREENPLAIN, DDSD_WIDTH | DDSD_HEIGHT, FALSE, "offscreenplain"},
+        {DDSCAPS_TEXTURE, DDSD_WIDTH | DDSD_HEIGHT, TRUE, "texture"},
+        {DDSCAPS_PRIMARYSURFACE, 0, FALSE, "primary"}
+    };
+
+    window = CreateWindowA("static", "ddraw_test", WS_OVERLAPPEDWINDOW,
+            0, 0, 640, 480, 0, 0, 0, 0);
+    ddraw = create_ddraw();
+    ok(!!ddraw, "Failed to create a ddraw object.\n");
+    if (FAILED(hr = IDirectDraw_SetDisplayMode(ddraw, 640, 480, 8)))
+    {
+        win_skip("Failed to set 8 bpp display mode, skipping test.\n");
+        IDirectDraw_Release(ddraw);
+        DestroyWindow(window);
+        return;
+    }
+    ok(SUCCEEDED(hr), "Failed to set display mode, hr %#x.\n", hr);
+    hr = IDirectDraw_SetCooperativeLevel(ddraw, window, DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN);
+    ok(SUCCEEDED(hr), "Failed to set cooperative level, hr %#x.\n", hr);
+
+    memset(palette_entries, 0, sizeof(palette_entries));
+    palette_entries[1].peFlags = 0x42;
+    palette_entries[2].peFlags = 0xff;
+    palette_entries[3].peFlags = 0x80;
+    hr = IDirectDraw_CreatePalette(ddraw, DDPCAPS_ALLOW256 | DDPCAPS_8BIT, palette_entries, &palette, NULL);
+    ok(SUCCEEDED(hr), "Failed to create palette, hr %#x.\n", hr);
+
+    memset(palette_entries, 0x66, sizeof(palette_entries));
+    hr = IDirectDrawPalette_GetEntries(palette, 0, 1, 4, palette_entries);
+    ok(SUCCEEDED(hr), "Failed to get palette entries, hr %#x.\n", hr);
+    ok(palette_entries[0].peFlags == 0x42, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[0].peFlags);
+    ok(palette_entries[1].peFlags == 0xff, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[1].peFlags);
+    ok(palette_entries[2].peFlags == 0x80, "Got unexpected peFlags 0x%02x, expected 0x80.\n",
+            palette_entries[2].peFlags);
+    ok(palette_entries[3].peFlags == 0x00, "Got unexpected peFlags 0x%02x, expected 0x00.\n",
+            palette_entries[3].peFlags);
+
+    IDirectDrawPalette_Release(palette);
+
+    memset(palette_entries, 0, sizeof(palette_entries));
+    palette_entries[1].peFlags = 0x42;
+    palette_entries[1].peRed   = 0xff;
+    palette_entries[2].peFlags = 0xff;
+    palette_entries[3].peFlags = 0x80;
+    hr = IDirectDraw_CreatePalette(ddraw, DDPCAPS_ALLOW256 | DDPCAPS_8BIT | DDPCAPS_ALPHA,
+            palette_entries, &palette, NULL);
+    ok(SUCCEEDED(hr), "Failed to create palette, hr %#x.\n", hr);
+
+    memset(palette_entries, 0x66, sizeof(palette_entries));
+    hr = IDirectDrawPalette_GetEntries(palette, 0, 1, 4, palette_entries);
+    ok(SUCCEEDED(hr), "Failed to get palette entries, hr %#x.\n", hr);
+    ok(palette_entries[0].peFlags == 0x42, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[0].peFlags);
+    ok(palette_entries[1].peFlags == 0xff, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[1].peFlags);
+    ok(palette_entries[2].peFlags == 0x80, "Got unexpected peFlags 0x%02x, expected 0x80.\n",
+            palette_entries[2].peFlags);
+    ok(palette_entries[3].peFlags == 0x00, "Got unexpected peFlags 0x%02x, expected 0x00.\n",
+            palette_entries[3].peFlags);
+
+    for (i = 0; i < sizeof(test_data) / sizeof(*test_data); i++)
+    {
+        memset(&surface_desc, 0, sizeof(surface_desc));
+        surface_desc.dwSize = sizeof(surface_desc);
+        surface_desc.dwFlags = DDSD_CAPS | test_data[i].flags;
+        surface_desc.dwWidth = 128;
+        surface_desc.dwHeight = 128;
+        surface_desc.ddsCaps.dwCaps = test_data[i].caps;
+        hr = IDirectDraw_CreateSurface(ddraw, &surface_desc, &surface, NULL);
+        ok(SUCCEEDED(hr), "Failed to create %s surface, hr %#x.\n", test_data[i].name, hr);
+
+        hr = IDirectDrawSurface_SetPalette(surface, palette);
+        if (test_data[i].attach_allowed)
+            ok(SUCCEEDED(hr), "Failed to attach palette to %s surface, hr %#x.\n", test_data[i].name, hr);
+        else
+            ok(hr == DDERR_INVALIDSURFACETYPE, "Got unexpected hr %#x, %s surface.\n", hr, test_data[i].name);
+
+        if (SUCCEEDED(hr))
+        {
+            HDC dc;
+            RGBQUAD rgbquad;
+            UINT retval;
+
+            hr = IDirectDrawSurface_GetDC(surface, &dc);
+            ok(SUCCEEDED(hr) || broken(hr == DDERR_CANTCREATEDC) /* Win2k testbot */,
+                    "Failed to get DC, hr %#x, %s surface.\n", hr, test_data[i].name);
+            if (SUCCEEDED(hr))
+            {
+                retval = GetDIBColorTable(dc, 1, 1, &rgbquad);
+                ok(retval == 1, "GetDIBColorTable returned unexpected result %u.\n", retval);
+                ok(rgbquad.rgbRed == 0xff, "Expected rgbRed = 0xff, got %#x, %s surface.\n",
+                        rgbquad.rgbRed, test_data[i].name);
+                ok(rgbquad.rgbGreen == 0, "Expected rgbGreen = 0, got %#x, %s surface.\n",
+                        rgbquad.rgbGreen, test_data[i].name);
+                ok(rgbquad.rgbBlue == 0, "Expected rgbBlue = 0, got %#x, %s surface.\n",
+                        rgbquad.rgbBlue, test_data[i].name);
+                todo_wine ok(rgbquad.rgbReserved == 0, "Expected rgbReserved = 0, got %u, %s surface.\n",
+                        rgbquad.rgbReserved, test_data[i].name);
+                hr = IDirectDrawSurface_ReleaseDC(surface, dc);
+                ok(SUCCEEDED(hr), "Failed to release DC, hr %#x.\n", hr);
+            }
+        }
+        IDirectDrawSurface_Release(surface);
+    }
+
+    /* Test INVALIDSURFACETYPE vs INVALIDPIXELFORMAT. */
+    memset(&surface_desc, 0, sizeof(surface_desc));
+    surface_desc.dwSize = sizeof(surface_desc);
+    surface_desc.dwFlags = DDSD_CAPS | DDSD_WIDTH | DDSD_HEIGHT | DDSD_PIXELFORMAT;
+    surface_desc.dwWidth = 128;
+    surface_desc.dwHeight = 128;
+    surface_desc.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN;
+    surface_desc.ddpfPixelFormat.dwSize = sizeof(surface_desc.ddpfPixelFormat);
+    surface_desc.ddpfPixelFormat.dwFlags = DDPF_RGB;
+    U1(surface_desc.ddpfPixelFormat).dwRGBBitCount = 32;
+    U2(surface_desc.ddpfPixelFormat).dwRBitMask = 0x00ff0000;
+    U3(surface_desc.ddpfPixelFormat).dwGBitMask = 0x0000ff00;
+    U4(surface_desc.ddpfPixelFormat).dwBBitMask = 0x000000ff;
+    hr = IDirectDraw_CreateSurface(ddraw, &surface_desc, &surface, NULL);
+    ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
+    hr = IDirectDrawSurface_SetPalette(surface, palette);
+    ok(hr == DDERR_INVALIDSURFACETYPE, "Got unexpected hr %#x.\n", hr);
+    IDirectDrawSurface_Release(surface);
+
+    /* The Windows 8 testbot keeps extra references to the primary
+     * while in 8 bpp mode. */
+    hr = IDirectDraw_RestoreDisplayMode(ddraw);
+    ok(SUCCEEDED(hr), "Failed to restore display mode, hr %#x.\n", hr);
+
+    refcount = IDirectDrawPalette_Release(palette);
+    ok(!refcount, "Got unexpected refcount %u.\n", refcount);
+    refcount = IDirectDraw_Release(ddraw);
+    ok(!refcount, "Got unexpected refcount %u.\n", refcount);
+    DestroyWindow(window);
+}
+
 START_TEST(ddraw1)
 {
     IDirectDraw *ddraw;
@@ -5364,4 +5521,5 @@ START_TEST(ddraw1)
     test_p8_rgb_blit();
     test_material();
     test_palette_gdi();
+    test_palette_alpha();
 }
diff --git a/dlls/ddraw/tests/ddraw2.c b/dlls/ddraw/tests/ddraw2.c
index aaef2bc..64aa519 100644
--- a/dlls/ddraw/tests/ddraw2.c
+++ b/dlls/ddraw/tests/ddraw2.c
@@ -6383,6 +6383,171 @@ static void test_palette_gdi(void)
     DestroyWindow(window);
 }
 
+static void test_palette_alpha(void)
+{
+    IDirectDrawSurface *surface1;
+    IDirectDrawSurface2 *surface;
+    DDSURFACEDESC surface_desc;
+    IDirectDraw2 *ddraw;
+    IDirectDrawPalette *palette;
+    ULONG refcount;
+    HWND window;
+    HRESULT hr;
+    PALETTEENTRY palette_entries[256];
+    unsigned int i;
+    static const struct
+    {
+        DWORD caps, flags;
+        BOOL attach_allowed;
+        const char *name;
+    }
+    test_data[] =
+    {
+        {DDSCAPS_OFFSCREENPLAIN, DDSD_WIDTH | DDSD_HEIGHT, FALSE, "offscreenplain"},
+        {DDSCAPS_TEXTURE, DDSD_WIDTH | DDSD_HEIGHT, TRUE, "texture"},
+        {DDSCAPS_PRIMARYSURFACE, 0, FALSE, "primary"}
+    };
+
+    window = CreateWindowA("static", "ddraw_test", WS_OVERLAPPEDWINDOW,
+            0, 0, 640, 480, 0, 0, 0, 0);
+    ddraw = create_ddraw();
+    ok(!!ddraw, "Failed to create a ddraw object.\n");
+    if (FAILED(hr = IDirectDraw2_SetDisplayMode(ddraw, 640, 480, 8, 0, 0)))
+    {
+        win_skip("Failed to set 8 bpp display mode, skipping test.\n");
+        IDirectDraw2_Release(ddraw);
+        DestroyWindow(window);
+        return;
+    }
+    ok(SUCCEEDED(hr), "Failed to set display mode, hr %#x.\n", hr);
+    hr = IDirectDraw2_SetCooperativeLevel(ddraw, window, DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN);
+    ok(SUCCEEDED(hr), "Failed to set cooperative level, hr %#x.\n", hr);
+
+    memset(palette_entries, 0, sizeof(palette_entries));
+    palette_entries[1].peFlags = 0x42;
+    palette_entries[2].peFlags = 0xff;
+    palette_entries[3].peFlags = 0x80;
+    hr = IDirectDraw2_CreatePalette(ddraw, DDPCAPS_ALLOW256 | DDPCAPS_8BIT, palette_entries, &palette, NULL);
+    ok(SUCCEEDED(hr), "Failed to create palette, hr %#x.\n", hr);
+
+    memset(palette_entries, 0x66, sizeof(palette_entries));
+    hr = IDirectDrawPalette_GetEntries(palette, 0, 1, 4, palette_entries);
+    ok(SUCCEEDED(hr), "Failed to get palette entries, hr %#x.\n", hr);
+    ok(palette_entries[0].peFlags == 0x42, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[0].peFlags);
+    ok(palette_entries[1].peFlags == 0xff, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[1].peFlags);
+    ok(palette_entries[2].peFlags == 0x80, "Got unexpected peFlags 0x%02x, expected 0x80.\n",
+            palette_entries[2].peFlags);
+    ok(palette_entries[3].peFlags == 0x00, "Got unexpected peFlags 0x%02x, expected 0x00.\n",
+            palette_entries[3].peFlags);
+
+    IDirectDrawPalette_Release(palette);
+
+    memset(palette_entries, 0, sizeof(palette_entries));
+    palette_entries[1].peFlags = 0x42;
+    palette_entries[1].peRed   = 0xff;
+    palette_entries[2].peFlags = 0xff;
+    palette_entries[3].peFlags = 0x80;
+    hr = IDirectDraw2_CreatePalette(ddraw, DDPCAPS_ALLOW256 | DDPCAPS_8BIT | DDPCAPS_ALPHA,
+            palette_entries, &palette, NULL);
+    ok(SUCCEEDED(hr), "Failed to create palette, hr %#x.\n", hr);
+
+    memset(palette_entries, 0x66, sizeof(palette_entries));
+    hr = IDirectDrawPalette_GetEntries(palette, 0, 1, 4, palette_entries);
+    ok(SUCCEEDED(hr), "Failed to get palette entries, hr %#x.\n", hr);
+    ok(palette_entries[0].peFlags == 0x42, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[0].peFlags);
+    ok(palette_entries[1].peFlags == 0xff, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[1].peFlags);
+    ok(palette_entries[2].peFlags == 0x80, "Got unexpected peFlags 0x%02x, expected 0x80.\n",
+            palette_entries[2].peFlags);
+    ok(palette_entries[3].peFlags == 0x00, "Got unexpected peFlags 0x%02x, expected 0x00.\n",
+            palette_entries[3].peFlags);
+
+    for (i = 0; i < sizeof(test_data) / sizeof(*test_data); i++)
+    {
+        memset(&surface_desc, 0, sizeof(surface_desc));
+        surface_desc.dwSize = sizeof(surface_desc);
+        surface_desc.dwFlags = DDSD_CAPS | test_data[i].flags;
+        surface_desc.dwWidth = 128;
+        surface_desc.dwHeight = 128;
+        surface_desc.ddsCaps.dwCaps = test_data[i].caps;
+        hr = IDirectDraw2_CreateSurface(ddraw, &surface_desc, &surface1, NULL);
+        ok(SUCCEEDED(hr), "Failed to create %s surface, hr %#x.\n", test_data[i].name, hr);
+        hr = IDirectDrawSurface_QueryInterface(surface1, &IID_IDirectDrawSurface2, (void **)&surface);
+        ok(SUCCEEDED(hr), "Failed to get IDirectDrawSurface2 interface, hr %#x.\n", hr);
+        IDirectDrawSurface_Release(surface1);
+
+        hr = IDirectDrawSurface2_SetPalette(surface, palette);
+        if (test_data[i].attach_allowed)
+            ok(SUCCEEDED(hr), "Failed to attach palette to %s surface, hr %#x.\n", test_data[i].name, hr);
+        else
+            ok(hr == DDERR_INVALIDSURFACETYPE, "Got unexpected hr %#x, %s surface.\n", hr, test_data[i].name);
+
+        if (SUCCEEDED(hr))
+        {
+            HDC dc;
+            RGBQUAD rgbquad;
+            UINT retval;
+
+            hr = IDirectDrawSurface2_GetDC(surface, &dc);
+            ok(SUCCEEDED(hr) || broken(hr == DDERR_CANTCREATEDC) /* Win2k testbot */,
+                    "Failed to get DC, hr %#x, %s surface.\n", hr, test_data[i].name);
+            if (SUCCEEDED(hr))
+            {
+                retval = GetDIBColorTable(dc, 1, 1, &rgbquad);
+                ok(retval == 1, "GetDIBColorTable returned unexpected result %u.\n", retval);
+                ok(rgbquad.rgbRed == 0xff, "Expected rgbRed = 0xff, got %#x, %s surface.\n",
+                        rgbquad.rgbRed, test_data[i].name);
+                ok(rgbquad.rgbGreen == 0, "Expected rgbGreen = 0, got %#x, %s surface.\n",
+                        rgbquad.rgbGreen, test_data[i].name);
+                ok(rgbquad.rgbBlue == 0, "Expected rgbBlue = 0, got %#x, %s surface.\n",
+                        rgbquad.rgbBlue, test_data[i].name);
+                todo_wine ok(rgbquad.rgbReserved == 0, "Expected rgbReserved = 0, got %u, %s surface.\n",
+                        rgbquad.rgbReserved, test_data[i].name);
+                hr = IDirectDrawSurface2_ReleaseDC(surface, dc);
+                ok(SUCCEEDED(hr), "Failed to release DC, hr %#x.\n", hr);
+            }
+        }
+        IDirectDrawSurface2_Release(surface);
+    }
+
+    /* Test INVALIDSURFACETYPE vs INVALIDPIXELFORMAT. */
+    memset(&surface_desc, 0, sizeof(surface_desc));
+    surface_desc.dwSize = sizeof(surface_desc);
+    surface_desc.dwFlags = DDSD_CAPS | DDSD_WIDTH | DDSD_HEIGHT | DDSD_PIXELFORMAT;
+    surface_desc.dwWidth = 128;
+    surface_desc.dwHeight = 128;
+    surface_desc.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN;
+    surface_desc.ddpfPixelFormat.dwSize = sizeof(surface_desc.ddpfPixelFormat);
+    surface_desc.ddpfPixelFormat.dwFlags = DDPF_RGB;
+    U1(surface_desc.ddpfPixelFormat).dwRGBBitCount = 32;
+    U2(surface_desc.ddpfPixelFormat).dwRBitMask = 0x00ff0000;
+    U3(surface_desc.ddpfPixelFormat).dwGBitMask = 0x0000ff00;
+    U4(surface_desc.ddpfPixelFormat).dwBBitMask = 0x000000ff;
+    hr = IDirectDraw2_CreateSurface(ddraw, &surface_desc, &surface1, NULL);
+    ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
+    hr = IDirectDrawSurface_QueryInterface(surface1, &IID_IDirectDrawSurface2, (void **)&surface);
+    ok(SUCCEEDED(hr), "Failed to get IDirectDrawSurface2 interface, hr %#x.\n", hr);
+    IDirectDrawSurface_Release(surface1);
+
+    hr = IDirectDrawSurface2_SetPalette(surface, palette);
+    ok(hr == DDERR_INVALIDSURFACETYPE, "Got unexpected hr %#x.\n", hr);
+    IDirectDrawSurface2_Release(surface);
+
+    /* The Windows 8 testbot keeps extra references to the primary
+     * while in 8 bpp mode. */
+    hr = IDirectDraw2_RestoreDisplayMode(ddraw);
+    ok(SUCCEEDED(hr), "Failed to restore display mode, hr %#x.\n", hr);
+
+    refcount = IDirectDrawPalette_Release(palette);
+    ok(!refcount, "Got unexpected refcount %u.\n", refcount);
+    refcount = IDirectDraw2_Release(ddraw);
+    ok(!refcount, "Got unexpected refcount %u.\n", refcount);
+    DestroyWindow(window);
+}
+
 START_TEST(ddraw2)
 {
     IDirectDraw2 *ddraw;
@@ -6438,4 +6603,5 @@ START_TEST(ddraw2)
     test_p8_rgb_blit();
     test_material();
     test_palette_gdi();
+    test_palette_alpha();
 }
diff --git a/dlls/ddraw/tests/ddraw4.c b/dlls/ddraw/tests/ddraw4.c
index cc96045..b760dfb 100644
--- a/dlls/ddraw/tests/ddraw4.c
+++ b/dlls/ddraw/tests/ddraw4.c
@@ -7285,6 +7285,159 @@ static void test_palette_gdi(void)
     DestroyWindow(window);
 }
 
+static void test_palette_alpha(void)
+{
+    IDirectDrawSurface4 *surface;
+    DDSURFACEDESC2 surface_desc;
+    IDirectDraw4 *ddraw;
+    IDirectDrawPalette *palette;
+    ULONG refcount;
+    HWND window;
+    HRESULT hr;
+    PALETTEENTRY palette_entries[256];
+    unsigned int i;
+    static const struct
+    {
+        DWORD caps, flags;
+        BOOL attach_allowed;
+        const char *name;
+    }
+    test_data[] =
+    {
+        {DDSCAPS_OFFSCREENPLAIN, DDSD_WIDTH | DDSD_HEIGHT, FALSE, "offscreenplain"},
+        {DDSCAPS_TEXTURE, DDSD_WIDTH | DDSD_HEIGHT, TRUE, "texture"},
+        {DDSCAPS_PRIMARYSURFACE, 0, FALSE, "primary"}
+    };
+
+    window = CreateWindowA("static", "ddraw_test", WS_OVERLAPPEDWINDOW,
+            0, 0, 640, 480, 0, 0, 0, 0);
+    ddraw = create_ddraw();
+    ok(!!ddraw, "Failed to create a ddraw object.\n");
+    if (FAILED(hr = IDirectDraw4_SetDisplayMode(ddraw, 640, 480, 8, 0, 0)))
+    {
+        win_skip("Failed to set 8 bpp display mode, skipping test.\n");
+        IDirectDraw4_Release(ddraw);
+        DestroyWindow(window);
+        return;
+    }
+    ok(SUCCEEDED(hr), "Failed to set display mode, hr %#x.\n", hr);
+    hr = IDirectDraw4_SetCooperativeLevel(ddraw, window, DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN);
+    ok(SUCCEEDED(hr), "Failed to set cooperative level, hr %#x.\n", hr);
+
+    memset(palette_entries, 0, sizeof(palette_entries));
+    palette_entries[1].peFlags = 0x42;
+    palette_entries[2].peFlags = 0xff;
+    palette_entries[3].peFlags = 0x80;
+    hr = IDirectDraw4_CreatePalette(ddraw, DDPCAPS_ALLOW256 | DDPCAPS_8BIT, palette_entries, &palette, NULL);
+    ok(SUCCEEDED(hr), "Failed to create palette, hr %#x.\n", hr);
+
+    memset(palette_entries, 0x66, sizeof(palette_entries));
+    hr = IDirectDrawPalette_GetEntries(palette, 0, 1, 4, palette_entries);
+    ok(SUCCEEDED(hr), "Failed to get palette entries, hr %#x.\n", hr);
+    ok(palette_entries[0].peFlags == 0x42, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[0].peFlags);
+    ok(palette_entries[1].peFlags == 0xff, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[1].peFlags);
+    ok(palette_entries[2].peFlags == 0x80, "Got unexpected peFlags 0x%02x, expected 0x80.\n",
+            palette_entries[2].peFlags);
+    ok(palette_entries[3].peFlags == 0x00, "Got unexpected peFlags 0x%02x, expected 0x00.\n",
+            palette_entries[3].peFlags);
+
+    IDirectDrawPalette_Release(palette);
+
+    memset(palette_entries, 0, sizeof(palette_entries));
+    palette_entries[1].peFlags = 0x42;
+    palette_entries[1].peRed   = 0xff;
+    palette_entries[2].peFlags = 0xff;
+    palette_entries[3].peFlags = 0x80;
+    hr = IDirectDraw4_CreatePalette(ddraw, DDPCAPS_ALLOW256 | DDPCAPS_8BIT | DDPCAPS_ALPHA,
+            palette_entries, &palette, NULL);
+    ok(SUCCEEDED(hr), "Failed to create palette, hr %#x.\n", hr);
+
+    memset(palette_entries, 0x66, sizeof(palette_entries));
+    hr = IDirectDrawPalette_GetEntries(palette, 0, 1, 4, palette_entries);
+    ok(SUCCEEDED(hr), "Failed to get palette entries, hr %#x.\n", hr);
+    ok(palette_entries[0].peFlags == 0x42, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[0].peFlags);
+    ok(palette_entries[1].peFlags == 0xff, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[1].peFlags);
+    ok(palette_entries[2].peFlags == 0x80, "Got unexpected peFlags 0x%02x, expected 0x80.\n",
+            palette_entries[2].peFlags);
+    ok(palette_entries[3].peFlags == 0x00, "Got unexpected peFlags 0x%02x, expected 0x00.\n",
+            palette_entries[3].peFlags);
+
+    for (i = 0; i < sizeof(test_data) / sizeof(*test_data); i++)
+    {
+        memset(&surface_desc, 0, sizeof(surface_desc));
+        surface_desc.dwSize = sizeof(surface_desc);
+        surface_desc.dwFlags = DDSD_CAPS | test_data[i].flags;
+        surface_desc.dwWidth = 128;
+        surface_desc.dwHeight = 128;
+        surface_desc.ddsCaps.dwCaps = test_data[i].caps;
+        hr = IDirectDraw4_CreateSurface(ddraw, &surface_desc, &surface, NULL);
+        ok(SUCCEEDED(hr), "Failed to create %s surface, hr %#x.\n", test_data[i].name, hr);
+
+        hr = IDirectDrawSurface4_SetPalette(surface, palette);
+        if (test_data[i].attach_allowed)
+            ok(SUCCEEDED(hr), "Failed to attach palette to %s surface, hr %#x.\n", test_data[i].name, hr);
+        else
+            ok(hr == DDERR_INVALIDSURFACETYPE, "Got unexpected hr %#x, %s surface.\n", hr, test_data[i].name);
+
+        if (SUCCEEDED(hr))
+        {
+            HDC dc;
+            RGBQUAD rgbquad;
+            UINT retval;
+
+            hr = IDirectDrawSurface4_GetDC(surface, &dc);
+            ok(SUCCEEDED(hr), "Failed to get DC, hr %#x, %s surface.\n", hr, test_data[i].name);
+            retval = GetDIBColorTable(dc, 1, 1, &rgbquad);
+            ok(retval == 1, "GetDIBColorTable returned unexpected result %u.\n", retval);
+            ok(rgbquad.rgbRed == 0xff, "Expected rgbRed = 0xff, got %#x, %s surface.\n",
+                    rgbquad.rgbRed, test_data[i].name);
+            ok(rgbquad.rgbGreen == 0, "Expected rgbGreen = 0, got %#x, %s surface.\n",
+                    rgbquad.rgbGreen, test_data[i].name);
+            ok(rgbquad.rgbBlue == 0, "Expected rgbBlue = 0, got %#x, %s surface.\n",
+                    rgbquad.rgbBlue, test_data[i].name);
+            todo_wine ok(rgbquad.rgbReserved == 0, "Expected rgbReserved = 0, got %u, %s surface.\n",
+                    rgbquad.rgbReserved, test_data[i].name);
+            hr = IDirectDrawSurface4_ReleaseDC(surface, dc);
+            ok(SUCCEEDED(hr), "Failed to release DC, hr %#x.\n", hr);
+        }
+        IDirectDrawSurface4_Release(surface);
+    }
+
+    /* Test INVALIDSURFACETYPE vs INVALIDPIXELFORMAT. */
+    memset(&surface_desc, 0, sizeof(surface_desc));
+    surface_desc.dwSize = sizeof(surface_desc);
+    surface_desc.dwFlags = DDSD_CAPS | DDSD_WIDTH | DDSD_HEIGHT | DDSD_PIXELFORMAT;
+    surface_desc.dwWidth = 128;
+    surface_desc.dwHeight = 128;
+    surface_desc.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN;
+    U4(surface_desc).ddpfPixelFormat.dwSize = sizeof(U4(surface_desc).ddpfPixelFormat);
+    U4(surface_desc).ddpfPixelFormat.dwFlags = DDPF_RGB;
+    U1(U4(surface_desc).ddpfPixelFormat).dwRGBBitCount = 32;
+    U2(U4(surface_desc).ddpfPixelFormat).dwRBitMask = 0x00ff0000;
+    U3(U4(surface_desc).ddpfPixelFormat).dwGBitMask = 0x0000ff00;
+    U4(U4(surface_desc).ddpfPixelFormat).dwBBitMask = 0x000000ff;
+    hr = IDirectDraw4_CreateSurface(ddraw, &surface_desc, &surface, NULL);
+    ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
+    hr = IDirectDrawSurface4_SetPalette(surface, palette);
+    ok(hr == DDERR_INVALIDSURFACETYPE, "Got unexpected hr %#x.\n", hr);
+    IDirectDrawSurface4_Release(surface);
+
+    /* The Windows 8 testbot keeps extra references to the primary
+     * while in 8 bpp mode. */
+    hr = IDirectDraw4_RestoreDisplayMode(ddraw);
+    ok(SUCCEEDED(hr), "Failed to restore display mode, hr %#x.\n", hr);
+
+    refcount = IDirectDrawPalette_Release(palette);
+    ok(!refcount, "Got unexpected refcount %u.\n", refcount);
+    refcount = IDirectDraw4_Release(ddraw);
+    ok(!refcount, "Got unexpected refcount %u.\n", refcount);
+    DestroyWindow(window);
+}
+
 START_TEST(ddraw4)
 {
     IDirectDraw4 *ddraw;
@@ -7346,4 +7499,5 @@ START_TEST(ddraw4)
     test_p8_rgb_blit();
     test_material();
     test_palette_gdi();
+    test_palette_alpha();
 }
diff --git a/dlls/ddraw/tests/ddraw7.c b/dlls/ddraw/tests/ddraw7.c
index fca2892..b61172c 100644
--- a/dlls/ddraw/tests/ddraw7.c
+++ b/dlls/ddraw/tests/ddraw7.c
@@ -7007,6 +7007,159 @@ static void test_palette_gdi(void)
     DestroyWindow(window);
 }
 
+static void test_palette_alpha(void)
+{
+    IDirectDrawSurface7 *surface;
+    DDSURFACEDESC2 surface_desc;
+    IDirectDraw7 *ddraw;
+    IDirectDrawPalette *palette;
+    ULONG refcount;
+    HWND window;
+    HRESULT hr;
+    PALETTEENTRY palette_entries[256];
+    unsigned int i;
+    static const struct
+    {
+        DWORD caps, flags;
+        BOOL attach_allowed;
+        const char *name;
+    }
+    test_data[] =
+    {
+        {DDSCAPS_OFFSCREENPLAIN, DDSD_WIDTH | DDSD_HEIGHT, FALSE, "offscreenplain"},
+        {DDSCAPS_TEXTURE, DDSD_WIDTH | DDSD_HEIGHT, TRUE, "texture"},
+        {DDSCAPS_PRIMARYSURFACE, 0, FALSE, "primary"}
+    };
+
+    window = CreateWindowA("static", "ddraw_test", WS_OVERLAPPEDWINDOW,
+            0, 0, 640, 480, 0, 0, 0, 0);
+    ddraw = create_ddraw();
+    ok(!!ddraw, "Failed to create a ddraw object.\n");
+    if (FAILED(hr = IDirectDraw7_SetDisplayMode(ddraw, 640, 480, 8, 0, 0)))
+    {
+        win_skip("Failed to set 8 bpp display mode, skipping test.\n");
+        IDirectDraw7_Release(ddraw);
+        DestroyWindow(window);
+        return;
+    }
+    ok(SUCCEEDED(hr), "Failed to set display mode, hr %#x.\n", hr);
+    hr = IDirectDraw7_SetCooperativeLevel(ddraw, window, DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN);
+    ok(SUCCEEDED(hr), "Failed to set cooperative level, hr %#x.\n", hr);
+
+    memset(palette_entries, 0, sizeof(palette_entries));
+    palette_entries[1].peFlags = 0x42;
+    palette_entries[2].peFlags = 0xff;
+    palette_entries[3].peFlags = 0x80;
+    hr = IDirectDraw7_CreatePalette(ddraw, DDPCAPS_ALLOW256 | DDPCAPS_8BIT, palette_entries, &palette, NULL);
+    ok(SUCCEEDED(hr), "Failed to create palette, hr %#x.\n", hr);
+
+    memset(palette_entries, 0x66, sizeof(palette_entries));
+    hr = IDirectDrawPalette_GetEntries(palette, 0, 1, 4, palette_entries);
+    ok(SUCCEEDED(hr), "Failed to get palette entries, hr %#x.\n", hr);
+    ok(palette_entries[0].peFlags == 0x42, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[0].peFlags);
+    ok(palette_entries[1].peFlags == 0xff, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[1].peFlags);
+    ok(palette_entries[2].peFlags == 0x80, "Got unexpected peFlags 0x%02x, expected 0x80.\n",
+            palette_entries[2].peFlags);
+    ok(palette_entries[3].peFlags == 0x00, "Got unexpected peFlags 0x%02x, expected 0x00.\n",
+            palette_entries[3].peFlags);
+
+    IDirectDrawPalette_Release(palette);
+
+    memset(palette_entries, 0, sizeof(palette_entries));
+    palette_entries[1].peFlags = 0x42;
+    palette_entries[1].peRed   = 0xff;
+    palette_entries[2].peFlags = 0xff;
+    palette_entries[3].peFlags = 0x80;
+    hr = IDirectDraw7_CreatePalette(ddraw, DDPCAPS_ALLOW256 | DDPCAPS_8BIT | DDPCAPS_ALPHA,
+            palette_entries, &palette, NULL);
+    ok(SUCCEEDED(hr), "Failed to create palette, hr %#x.\n", hr);
+
+    memset(palette_entries, 0x66, sizeof(palette_entries));
+    hr = IDirectDrawPalette_GetEntries(palette, 0, 1, 4, palette_entries);
+    ok(SUCCEEDED(hr), "Failed to get palette entries, hr %#x.\n", hr);
+    ok(palette_entries[0].peFlags == 0x42, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[0].peFlags);
+    ok(palette_entries[1].peFlags == 0xff, "Got unexpected peFlags 0x%02x, expected 0xff.\n",
+            palette_entries[1].peFlags);
+    ok(palette_entries[2].peFlags == 0x80, "Got unexpected peFlags 0x%02x, expected 0x80.\n",
+            palette_entries[2].peFlags);
+    ok(palette_entries[3].peFlags == 0x00, "Got unexpected peFlags 0x%02x, expected 0x00.\n",
+            palette_entries[3].peFlags);
+
+    for (i = 0; i < sizeof(test_data) / sizeof(*test_data); i++)
+    {
+        memset(&surface_desc, 0, sizeof(surface_desc));
+        surface_desc.dwSize = sizeof(surface_desc);
+        surface_desc.dwFlags = DDSD_CAPS | test_data[i].flags;
+        surface_desc.dwWidth = 128;
+        surface_desc.dwHeight = 128;
+        surface_desc.ddsCaps.dwCaps = test_data[i].caps;
+        hr = IDirectDraw7_CreateSurface(ddraw, &surface_desc, &surface, NULL);
+        ok(SUCCEEDED(hr), "Failed to create %s surface, hr %#x.\n", test_data[i].name, hr);
+
+        hr = IDirectDrawSurface7_SetPalette(surface, palette);
+        if (test_data[i].attach_allowed)
+            ok(SUCCEEDED(hr), "Failed to attach palette to %s surface, hr %#x.\n", test_data[i].name, hr);
+        else
+            ok(hr == DDERR_INVALIDSURFACETYPE, "Got unexpected hr %#x, %s surface.\n", hr, test_data[i].name);
+
+        if (SUCCEEDED(hr))
+        {
+            HDC dc;
+            RGBQUAD rgbquad;
+            UINT retval;
+
+            hr = IDirectDrawSurface7_GetDC(surface, &dc);
+            ok(SUCCEEDED(hr), "Failed to get DC, hr %#x, %s surface.\n", hr, test_data[i].name);
+            retval = GetDIBColorTable(dc, 1, 1, &rgbquad);
+            ok(retval == 1, "GetDIBColorTable returned unexpected result %u.\n", retval);
+            ok(rgbquad.rgbRed == 0xff, "Expected rgbRed = 0xff, got %#x, %s surface.\n",
+                    rgbquad.rgbRed, test_data[i].name);
+            ok(rgbquad.rgbGreen == 0, "Expected rgbGreen = 0, got %#x, %s surface.\n",
+                    rgbquad.rgbGreen, test_data[i].name);
+            ok(rgbquad.rgbBlue == 0, "Expected rgbBlue = 0, got %#x, %s surface.\n",
+                    rgbquad.rgbBlue, test_data[i].name);
+            todo_wine ok(rgbquad.rgbReserved == 0, "Expected rgbReserved = 0, got %u, %s surface.\n",
+                    rgbquad.rgbReserved, test_data[i].name);
+            hr = IDirectDrawSurface7_ReleaseDC(surface, dc);
+            ok(SUCCEEDED(hr), "Failed to release DC, hr %#x.\n", hr);
+        }
+        IDirectDrawSurface7_Release(surface);
+    }
+
+    /* Test INVALIDSURFACETYPE vs INVALIDPIXELFORMAT. */
+    memset(&surface_desc, 0, sizeof(surface_desc));
+    surface_desc.dwSize = sizeof(surface_desc);
+    surface_desc.dwFlags = DDSD_CAPS | DDSD_WIDTH | DDSD_HEIGHT | DDSD_PIXELFORMAT;
+    surface_desc.dwWidth = 128;
+    surface_desc.dwHeight = 128;
+    surface_desc.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN;
+    U4(surface_desc).ddpfPixelFormat.dwSize = sizeof(U4(surface_desc).ddpfPixelFormat);
+    U4(surface_desc).ddpfPixelFormat.dwFlags = DDPF_RGB;
+    U1(U4(surface_desc).ddpfPixelFormat).dwRGBBitCount = 32;
+    U2(U4(surface_desc).ddpfPixelFormat).dwRBitMask = 0x00ff0000;
+    U3(U4(surface_desc).ddpfPixelFormat).dwGBitMask = 0x0000ff00;
+    U4(U4(surface_desc).ddpfPixelFormat).dwBBitMask = 0x000000ff;
+    hr = IDirectDraw7_CreateSurface(ddraw, &surface_desc, &surface, NULL);
+    ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
+    hr = IDirectDrawSurface7_SetPalette(surface, palette);
+    ok(hr == DDERR_INVALIDSURFACETYPE, "Got unexpected hr %#x.\n", hr);
+    IDirectDrawSurface7_Release(surface);
+
+    /* The Windows 8 testbot keeps extra references to the primary
+     * while in 8 bpp mode. */
+    hr = IDirectDraw7_RestoreDisplayMode(ddraw);
+    ok(SUCCEEDED(hr), "Failed to restore display mode, hr %#x.\n", hr);
+
+    refcount = IDirectDrawPalette_Release(palette);
+    ok(!refcount, "Got unexpected refcount %u.\n", refcount);
+    refcount = IDirectDraw7_Release(ddraw);
+    ok(!refcount, "Got unexpected refcount %u.\n", refcount);
+    DestroyWindow(window);
+}
+
 START_TEST(ddraw7)
 {
     HMODULE module = GetModuleHandleA("ddraw.dll");
@@ -7075,4 +7228,5 @@ START_TEST(ddraw7)
     test_p8_rgb_blit();
     test_material();
     test_palette_gdi();
+    test_palette_alpha();
 }
-- 
1.8.5.5




More information about the wine-patches mailing list