[WINED3D]
authorKamil Hornicek <kamil.hornicek@reactos.org>
Mon, 11 Oct 2010 13:56:39 +0000 (13:56 +0000)
committerKamil Hornicek <kamil.hornicek@reactos.org>
Mon, 11 Oct 2010 13:56:39 +0000 (13:56 +0000)
Update wined3d, ddraw, d3d8 and d3d9 to Wine 1.3.4.

svn path=/trunk/; revision=49116

93 files changed:
reactos/dll/directx/wine/d3d8/buffer.c [new file with mode: 0644]
reactos/dll/directx/wine/d3d8/cubetexture.c
reactos/dll/directx/wine/d3d8/d3d8.rbuild
reactos/dll/directx/wine/d3d8/d3d8_main.c
reactos/dll/directx/wine/d3d8/d3d8_private.h
reactos/dll/directx/wine/d3d8/device.c
reactos/dll/directx/wine/d3d8/indexbuffer.c [deleted file]
reactos/dll/directx/wine/d3d8/pixelshader.c [deleted file]
reactos/dll/directx/wine/d3d8/shader.c [new file with mode: 0644]
reactos/dll/directx/wine/d3d8/surface.c
reactos/dll/directx/wine/d3d8/swapchain.c
reactos/dll/directx/wine/d3d8/texture.c
reactos/dll/directx/wine/d3d8/vertexbuffer.c [deleted file]
reactos/dll/directx/wine/d3d8/vertexdeclaration.c
reactos/dll/directx/wine/d3d8/vertexshader.c [deleted file]
reactos/dll/directx/wine/d3d8/volume.c
reactos/dll/directx/wine/d3d8/volumetexture.c
reactos/dll/directx/wine/d3d9/buffer.c [new file with mode: 0644]
reactos/dll/directx/wine/d3d9/cubetexture.c
reactos/dll/directx/wine/d3d9/d3d9.rbuild
reactos/dll/directx/wine/d3d9/d3d9_private.h
reactos/dll/directx/wine/d3d9/device.c
reactos/dll/directx/wine/d3d9/indexbuffer.c [deleted file]
reactos/dll/directx/wine/d3d9/pixelshader.c [deleted file]
reactos/dll/directx/wine/d3d9/query.c
reactos/dll/directx/wine/d3d9/shader.c [new file with mode: 0644]
reactos/dll/directx/wine/d3d9/stateblock.c
reactos/dll/directx/wine/d3d9/surface.c
reactos/dll/directx/wine/d3d9/swapchain.c
reactos/dll/directx/wine/d3d9/texture.c
reactos/dll/directx/wine/d3d9/vertexbuffer.c [deleted file]
reactos/dll/directx/wine/d3d9/vertexdeclaration.c
reactos/dll/directx/wine/d3d9/vertexshader.c [deleted file]
reactos/dll/directx/wine/d3d9/volume.c
reactos/dll/directx/wine/d3d9/volumetexture.c
reactos/dll/directx/wine/ddraw/clipper.c
reactos/dll/directx/wine/ddraw/ddraw.c
reactos/dll/directx/wine/ddraw/ddraw.rbuild
reactos/dll/directx/wine/ddraw/ddraw_private.h
reactos/dll/directx/wine/ddraw/ddraw_thunks.c [deleted file]
reactos/dll/directx/wine/ddraw/device.c
reactos/dll/directx/wine/ddraw/direct3d.c [deleted file]
reactos/dll/directx/wine/ddraw/executebuffer.c
reactos/dll/directx/wine/ddraw/gamma.c [deleted file]
reactos/dll/directx/wine/ddraw/legacy.h [new file with mode: 0644]
reactos/dll/directx/wine/ddraw/light.c
reactos/dll/directx/wine/ddraw/main.c
reactos/dll/directx/wine/ddraw/material.c
reactos/dll/directx/wine/ddraw/palette.c
reactos/dll/directx/wine/ddraw/parent.c
reactos/dll/directx/wine/ddraw/regsvr.c
reactos/dll/directx/wine/ddraw/surface.c
reactos/dll/directx/wine/ddraw/surface_thunks.c [deleted file]
reactos/dll/directx/wine/ddraw/texture.c [deleted file]
reactos/dll/directx/wine/ddraw/utils.c
reactos/dll/directx/wine/ddraw/vertexbuffer.c
reactos/dll/directx/wine/ddraw/viewport.c
reactos/dll/directx/wine/wined3d/arb_program_shader.c
reactos/dll/directx/wine/wined3d/ati_fragment_shader.c
reactos/dll/directx/wine/wined3d/basetexture.c
reactos/dll/directx/wine/wined3d/buffer.c
reactos/dll/directx/wine/wined3d/clipper.c
reactos/dll/directx/wine/wined3d/context.c
reactos/dll/directx/wine/wined3d/cubetexture.c
reactos/dll/directx/wine/wined3d/device.c
reactos/dll/directx/wine/wined3d/directx.c
reactos/dll/directx/wine/wined3d/drawprim.c
reactos/dll/directx/wine/wined3d/glsl_shader.c
reactos/dll/directx/wine/wined3d/nvidia_texture_shader.c
reactos/dll/directx/wine/wined3d/palette.c
reactos/dll/directx/wine/wined3d/query.c
reactos/dll/directx/wine/wined3d/resource.c
reactos/dll/directx/wine/wined3d/shader.c
reactos/dll/directx/wine/wined3d/shader_sm4.c
reactos/dll/directx/wine/wined3d/state.c
reactos/dll/directx/wine/wined3d/stateblock.c
reactos/dll/directx/wine/wined3d/surface.c
reactos/dll/directx/wine/wined3d/surface_base.c
reactos/dll/directx/wine/wined3d/surface_gdi.c
reactos/dll/directx/wine/wined3d/swapchain.c
reactos/dll/directx/wine/wined3d/swapchain_base.c
reactos/dll/directx/wine/wined3d/swapchain_gdi.c
reactos/dll/directx/wine/wined3d/texture.c
reactos/dll/directx/wine/wined3d/utils.c
reactos/dll/directx/wine/wined3d/vertexdeclaration.c
reactos/dll/directx/wine/wined3d/view.c
reactos/dll/directx/wine/wined3d/volume.c
reactos/dll/directx/wine/wined3d/volumetexture.c
reactos/dll/directx/wine/wined3d/wined3d.spec
reactos/dll/directx/wine/wined3d/wined3d_gl.h
reactos/dll/directx/wine/wined3d/wined3d_main.c
reactos/dll/directx/wine/wined3d/wined3d_private.h
reactos/include/reactos/wine/wined3d.idl

diff --git a/reactos/dll/directx/wine/d3d8/buffer.c b/reactos/dll/directx/wine/d3d8/buffer.c
new file mode 100644 (file)
index 0000000..f7dc12d
--- /dev/null
@@ -0,0 +1,549 @@
+/*
+ * Copyright 2005 Oliver Stieber
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
+ */
+
+#include "config.h"
+#include "d3d8_private.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(d3d8);
+
+static HRESULT WINAPI d3d8_vertexbuffer_QueryInterface(IDirect3DVertexBuffer8 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    if (IsEqualGUID(riid, &IID_IDirect3DVertexBuffer8)
+            || IsEqualGUID(riid, &IID_IDirect3DResource8)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
+        IUnknown_AddRef(iface);
+        *object = iface;
+        return S_OK;
+    }
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI d3d8_vertexbuffer_AddRef(IDirect3DVertexBuffer8 *iface)
+{
+    IDirect3DVertexBuffer8Impl *buffer = (IDirect3DVertexBuffer8Impl *)iface;
+    ULONG refcount = InterlockedIncrement(&buffer->ref);
+
+    TRACE("%p increasing refcount to %u.\n", iface, refcount);
+
+    if (refcount == 1)
+    {
+        IDirect3DDevice8_AddRef(buffer->parentDevice);
+        wined3d_mutex_lock();
+        IWineD3DBuffer_AddRef(buffer->wineD3DVertexBuffer);
+        wined3d_mutex_unlock();
+    }
+
+    return refcount;
+}
+
+static ULONG WINAPI d3d8_vertexbuffer_Release(IDirect3DVertexBuffer8 *iface)
+{
+    IDirect3DVertexBuffer8Impl *buffer = (IDirect3DVertexBuffer8Impl *)iface;
+    ULONG refcount = InterlockedDecrement(&buffer->ref);
+
+    TRACE("%p decreasing refcount to %u.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        IDirect3DDevice8 *device = buffer->parentDevice;
+
+        wined3d_mutex_lock();
+        IWineD3DBuffer_Release(buffer->wineD3DVertexBuffer);
+        wined3d_mutex_unlock();
+
+        /* Release the device last, as it may cause the device to be destroyed. */
+        IDirect3DDevice8_Release(device);
+    }
+
+    return refcount;
+}
+
+static HRESULT WINAPI d3d8_vertexbuffer_GetDevice(IDirect3DVertexBuffer8 *iface, IDirect3DDevice8 **device)
+{
+    TRACE("iface %p, device %p.\n", iface, device);
+
+    *device = (IDirect3DDevice8 *)((IDirect3DVertexBuffer8Impl *)iface)->parentDevice;
+    IDirect3DDevice8_AddRef(*device);
+
+    TRACE("Returning device %p.\n", *device);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d8_vertexbuffer_SetPrivateData(IDirect3DVertexBuffer8 *iface,
+        REFGUID guid, const void *data, DWORD data_size, DWORD flags)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s, data %p, data_size %u, flags %#x.\n",
+            iface, debugstr_guid(guid), data, data_size, flags);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_SetPrivateData(((IDirect3DVertexBuffer8Impl *)iface)->wineD3DVertexBuffer,
+            guid, data, data_size, flags);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d8_vertexbuffer_GetPrivateData(IDirect3DVertexBuffer8 *iface,
+        REFGUID guid, void *data, DWORD *data_size)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s, data %p, data_size %p.\n",
+            iface, debugstr_guid(guid), data, data_size);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_GetPrivateData(((IDirect3DVertexBuffer8Impl *)iface)->wineD3DVertexBuffer,
+            guid, data, data_size);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d8_vertexbuffer_FreePrivateData(IDirect3DVertexBuffer8 *iface, REFGUID guid)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(guid));
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_FreePrivateData(((IDirect3DVertexBuffer8Impl *)iface)->wineD3DVertexBuffer, guid);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static DWORD WINAPI d3d8_vertexbuffer_SetPriority(IDirect3DVertexBuffer8 *iface, DWORD priority)
+{
+    DWORD previous;
+
+    TRACE("iface %p, priority %u.\n", iface, priority);
+
+    wined3d_mutex_lock();
+    previous = IWineD3DBuffer_SetPriority(((IDirect3DVertexBuffer8Impl *)iface)->wineD3DVertexBuffer, priority);
+    wined3d_mutex_unlock();
+
+    return previous;
+}
+
+static DWORD WINAPI d3d8_vertexbuffer_GetPriority(IDirect3DVertexBuffer8 *iface)
+{
+    DWORD priority;
+
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    priority = IWineD3DBuffer_GetPriority(((IDirect3DVertexBuffer8Impl *)iface)->wineD3DVertexBuffer);
+    wined3d_mutex_unlock();
+
+    return priority;
+}
+
+static void WINAPI d3d8_vertexbuffer_PreLoad(IDirect3DVertexBuffer8 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    IWineD3DBuffer_PreLoad(((IDirect3DVertexBuffer8Impl *)iface)->wineD3DVertexBuffer);
+    wined3d_mutex_unlock();
+}
+
+static D3DRESOURCETYPE WINAPI d3d8_vertexbuffer_GetType(IDirect3DVertexBuffer8 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return D3DRTYPE_VERTEXBUFFER;
+}
+
+static HRESULT WINAPI d3d8_vertexbuffer_Lock(IDirect3DVertexBuffer8 *iface,
+        UINT offset, UINT size, BYTE **data, DWORD flags)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, offset %u, size %u, data %p, flags %#x.\n",
+            iface, offset, size, data, flags);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_Map(((IDirect3DVertexBuffer8Impl *)iface)->wineD3DVertexBuffer,
+            offset, size, data, flags);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d8_vertexbuffer_Unlock(IDirect3DVertexBuffer8 *iface)
+{
+    HRESULT hr;
+
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_Unmap(((IDirect3DVertexBuffer8Impl *)iface)->wineD3DVertexBuffer);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d8_vertexbuffer_GetDesc(IDirect3DVertexBuffer8 *iface, D3DVERTEXBUFFER_DESC *desc)
+{
+    IDirect3DVertexBuffer8Impl *buffer = (IDirect3DVertexBuffer8Impl *)iface;
+    WINED3DBUFFER_DESC wined3d_desc;
+
+    TRACE("iface %p, desc %p.\n", iface, desc);
+
+    wined3d_mutex_lock();
+    IWineD3DBuffer_GetDesc(buffer->wineD3DVertexBuffer, &wined3d_desc);
+    wined3d_mutex_unlock();
+
+    desc->Type = D3DRTYPE_VERTEXBUFFER;
+    desc->Usage = wined3d_desc.Usage;
+    desc->Pool = wined3d_desc.Pool;
+    desc->Size = wined3d_desc.Size;
+    desc->FVF = buffer->fvf;
+    desc->Format = D3DFMT_VERTEXDATA;
+
+    return D3D_OK;
+}
+
+static const IDirect3DVertexBuffer8Vtbl Direct3DVertexBuffer8_Vtbl =
+{
+    /* IUnknown */
+    d3d8_vertexbuffer_QueryInterface,
+    d3d8_vertexbuffer_AddRef,
+    d3d8_vertexbuffer_Release,
+    /* IDirect3DResource8 */
+    d3d8_vertexbuffer_GetDevice,
+    d3d8_vertexbuffer_SetPrivateData,
+    d3d8_vertexbuffer_GetPrivateData,
+    d3d8_vertexbuffer_FreePrivateData,
+    d3d8_vertexbuffer_SetPriority,
+    d3d8_vertexbuffer_GetPriority,
+    d3d8_vertexbuffer_PreLoad,
+    d3d8_vertexbuffer_GetType,
+    /* IDirect3DVertexBuffer8 */
+    d3d8_vertexbuffer_Lock,
+    d3d8_vertexbuffer_Unlock,
+    d3d8_vertexbuffer_GetDesc,
+};
+
+static void STDMETHODCALLTYPE d3d8_vertexbuffer_wined3d_object_destroyed(void *parent)
+{
+    HeapFree(GetProcessHeap(), 0, parent);
+}
+
+static const struct wined3d_parent_ops d3d8_vertexbuffer_wined3d_parent_ops =
+{
+    d3d8_vertexbuffer_wined3d_object_destroyed,
+};
+
+HRESULT vertexbuffer_init(IDirect3DVertexBuffer8Impl *buffer, IDirect3DDevice8Impl *device,
+        UINT size, DWORD usage, DWORD fvf, D3DPOOL pool)
+{
+    HRESULT hr;
+
+    buffer->lpVtbl = &Direct3DVertexBuffer8_Vtbl;
+    buffer->ref = 1;
+    buffer->fvf = fvf;
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_CreateVertexBuffer(device->WineD3DDevice, size, usage & WINED3DUSAGE_MASK,
+            (WINED3DPOOL)pool, buffer, &d3d8_vertexbuffer_wined3d_parent_ops, &buffer->wineD3DVertexBuffer);
+    wined3d_mutex_unlock();
+    if (FAILED(hr))
+    {
+        WARN("Failed to create wined3d buffer, hr %#x.\n", hr);
+        return hr;
+    }
+
+    buffer->parentDevice = (IDirect3DDevice8 *)device;
+    IUnknown_AddRef(buffer->parentDevice);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d8_indexbuffer_QueryInterface(IDirect3DIndexBuffer8 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    if (IsEqualGUID(riid, &IID_IDirect3DIndexBuffer8)
+            || IsEqualGUID(riid, &IID_IDirect3DResource8)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
+        IUnknown_AddRef(iface);
+        *object = iface;
+        return S_OK;
+    }
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI d3d8_indexbuffer_AddRef(IDirect3DIndexBuffer8 *iface)
+{
+    IDirect3DIndexBuffer8Impl *buffer = (IDirect3DIndexBuffer8Impl *)iface;
+    ULONG refcount = InterlockedIncrement(&buffer->ref);
+
+    TRACE("%p increasing refcount to %u.\n", iface, refcount);
+
+    if (refcount == 1)
+    {
+        IDirect3DDevice8_AddRef(buffer->parentDevice);
+        wined3d_mutex_lock();
+        IWineD3DBuffer_AddRef(buffer->wineD3DIndexBuffer);
+        wined3d_mutex_unlock();
+    }
+
+    return refcount;
+}
+
+static ULONG WINAPI d3d8_indexbuffer_Release(IDirect3DIndexBuffer8 *iface)
+{
+    IDirect3DIndexBuffer8Impl *buffer = (IDirect3DIndexBuffer8Impl *)iface;
+    ULONG refcount = InterlockedDecrement(&buffer->ref);
+
+    TRACE("%p decreasing refcount to %u.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        IDirect3DDevice8 *device = buffer->parentDevice;
+
+        wined3d_mutex_lock();
+        IWineD3DBuffer_Release(buffer->wineD3DIndexBuffer);
+        wined3d_mutex_unlock();
+
+        /* Release the device last, as it may cause the device to be destroyed. */
+        IDirect3DDevice8_Release(device);
+    }
+
+    return refcount;
+}
+
+static HRESULT WINAPI d3d8_indexbuffer_GetDevice(IDirect3DIndexBuffer8 *iface, IDirect3DDevice8 **device)
+{
+    TRACE("iface %p, device %p.\n", iface, device);
+
+    *device = (IDirect3DDevice8 *)((IDirect3DIndexBuffer8Impl *)iface)->parentDevice;
+    IDirect3DDevice8_AddRef(*device);
+
+    TRACE("Returning device %p.\n", *device);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d8_indexbuffer_SetPrivateData(IDirect3DIndexBuffer8 *iface,
+        REFGUID guid, const void *data, DWORD data_size, DWORD flags)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s, data %p, data_size %u, flags %#x.\n",
+            iface, debugstr_guid(guid), data, data_size, flags);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_SetPrivateData(((IDirect3DIndexBuffer8Impl *)iface)->wineD3DIndexBuffer,
+            guid, data, data_size, flags);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d8_indexbuffer_GetPrivateData(IDirect3DIndexBuffer8 *iface,
+        REFGUID guid, void *data, DWORD *data_size)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s, data %p, data_size %p.\n",
+            iface, debugstr_guid(guid), data, data_size);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_GetPrivateData(((IDirect3DIndexBuffer8Impl *)iface)->wineD3DIndexBuffer,
+            guid, data, data_size);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d8_indexbuffer_FreePrivateData(IDirect3DIndexBuffer8 *iface, REFGUID guid)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(guid));
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_FreePrivateData(((IDirect3DIndexBuffer8Impl *)iface)->wineD3DIndexBuffer, guid);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static DWORD WINAPI d3d8_indexbuffer_SetPriority(IDirect3DIndexBuffer8 *iface, DWORD priority)
+{
+    DWORD previous;
+
+    TRACE("iface %p, priority %u.\n", iface, priority);
+
+    wined3d_mutex_lock();
+    previous = IWineD3DBuffer_SetPriority(((IDirect3DIndexBuffer8Impl *)iface)->wineD3DIndexBuffer, priority);
+    wined3d_mutex_unlock();
+
+    return previous;
+}
+
+static DWORD WINAPI d3d8_indexbuffer_GetPriority(IDirect3DIndexBuffer8 *iface)
+{
+    DWORD priority;
+
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    priority = IWineD3DBuffer_GetPriority(((IDirect3DIndexBuffer8Impl *)iface)->wineD3DIndexBuffer);
+    wined3d_mutex_unlock();
+
+    return priority;
+}
+
+static void WINAPI d3d8_indexbuffer_PreLoad(IDirect3DIndexBuffer8 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    IWineD3DBuffer_PreLoad(((IDirect3DIndexBuffer8Impl *)iface)->wineD3DIndexBuffer);
+    wined3d_mutex_unlock();
+}
+
+static D3DRESOURCETYPE WINAPI d3d8_indexbuffer_GetType(IDirect3DIndexBuffer8 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return D3DRTYPE_INDEXBUFFER;
+}
+
+static HRESULT WINAPI d3d8_indexbuffer_Lock(IDirect3DIndexBuffer8 *iface,
+        UINT offset, UINT size, BYTE **data, DWORD flags)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, offset %u, size %u, data %p, flags %#x.\n",
+            iface, offset, size, data, flags);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_Map(((IDirect3DIndexBuffer8Impl *)iface)->wineD3DIndexBuffer,
+            offset, size, data, flags);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d8_indexbuffer_Unlock(IDirect3DIndexBuffer8 *iface)
+{
+    HRESULT hr;
+
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_Unmap(((IDirect3DIndexBuffer8Impl *)iface)->wineD3DIndexBuffer);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d8_indexbuffer_GetDesc(IDirect3DIndexBuffer8 *iface, D3DINDEXBUFFER_DESC *desc)
+{
+    IDirect3DIndexBuffer8Impl *buffer = (IDirect3DIndexBuffer8Impl *)iface;
+    WINED3DBUFFER_DESC wined3d_desc;
+
+    TRACE("iface %p, desc %p.\n", iface, desc);
+
+    wined3d_mutex_lock();
+    IWineD3DBuffer_GetDesc(buffer->wineD3DIndexBuffer, &wined3d_desc);
+    wined3d_mutex_unlock();
+
+    desc->Format = d3dformat_from_wined3dformat(buffer->format);
+    desc->Type = D3DRTYPE_INDEXBUFFER;
+    desc->Usage = wined3d_desc.Usage;
+    desc->Pool = wined3d_desc.Pool;
+    desc->Size = wined3d_desc.Size;
+
+    return D3D_OK;
+}
+
+static const IDirect3DIndexBuffer8Vtbl d3d8_indexbuffer_vtbl =
+{
+    /* IUnknown */
+    d3d8_indexbuffer_QueryInterface,
+    d3d8_indexbuffer_AddRef,
+    d3d8_indexbuffer_Release,
+    /* IDirect3DResource8 */
+    d3d8_indexbuffer_GetDevice,
+    d3d8_indexbuffer_SetPrivateData,
+    d3d8_indexbuffer_GetPrivateData,
+    d3d8_indexbuffer_FreePrivateData,
+    d3d8_indexbuffer_SetPriority,
+    d3d8_indexbuffer_GetPriority,
+    d3d8_indexbuffer_PreLoad,
+    d3d8_indexbuffer_GetType,
+    /* IDirect3DIndexBuffer8 */
+    d3d8_indexbuffer_Lock,
+    d3d8_indexbuffer_Unlock,
+    d3d8_indexbuffer_GetDesc,
+};
+
+static void STDMETHODCALLTYPE d3d8_indexbuffer_wined3d_object_destroyed(void *parent)
+{
+    HeapFree(GetProcessHeap(), 0, parent);
+}
+
+static const struct wined3d_parent_ops d3d8_indexbuffer_wined3d_parent_ops =
+{
+    d3d8_indexbuffer_wined3d_object_destroyed,
+};
+
+HRESULT indexbuffer_init(IDirect3DIndexBuffer8Impl *buffer, IDirect3DDevice8Impl *device,
+        UINT size, DWORD usage, D3DFORMAT format, D3DPOOL pool)
+{
+    HRESULT hr;
+
+    buffer->lpVtbl = &d3d8_indexbuffer_vtbl;
+    buffer->ref = 1;
+    buffer->format = wined3dformat_from_d3dformat(format);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_CreateIndexBuffer(device->WineD3DDevice, size, usage & WINED3DUSAGE_MASK,
+            (WINED3DPOOL)pool, buffer, &d3d8_indexbuffer_wined3d_parent_ops, &buffer->wineD3DIndexBuffer);
+    wined3d_mutex_unlock();
+    if (FAILED(hr))
+    {
+        WARN("Failed to create wined3d buffer, hr %#x.\n", hr);
+        return hr;
+    }
+
+    buffer->parentDevice = (IDirect3DDevice8 *)device;
+    IUnknown_AddRef(buffer->parentDevice);
+
+    return D3D_OK;
+}
index 7e48dab..b9b411a 100644 (file)
@@ -253,22 +253,27 @@ static HRESULT WINAPI IDirect3DCubeTexture8Impl_GetLevelDesc(LPDIRECT3DCUBETEXTU
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DCubeTexture8Impl_GetCubeMapSurface(LPDIRECT3DCUBETEXTURE8 iface, D3DCUBEMAP_FACES FaceType, UINT Level, IDirect3DSurface8 **ppCubeMapSurface) {
+static HRESULT WINAPI IDirect3DCubeTexture8Impl_GetCubeMapSurface(IDirect3DCubeTexture8 *iface,
+        D3DCUBEMAP_FACES FaceType, UINT Level, IDirect3DSurface8 **ppCubeMapSurface)
+{
     IDirect3DCubeTexture8Impl *This = (IDirect3DCubeTexture8Impl *)iface;
-    HRESULT hrc = D3D_OK;
     IWineD3DSurface *mySurface = NULL;
+    HRESULT hr;
 
     TRACE("iface %p, face %#x, level %u, surface %p.\n", iface, FaceType, Level, ppCubeMapSurface);
 
     wined3d_mutex_lock();
-    hrc = IWineD3DCubeTexture_GetCubeMapSurface(This->wineD3DCubeTexture, (WINED3DCUBEMAP_FACES) FaceType, Level, &mySurface);
-    if (hrc == D3D_OK && NULL != ppCubeMapSurface) {
-       IWineD3DCubeTexture_GetParent(mySurface, (IUnknown **)ppCubeMapSurface);
+    hr = IWineD3DCubeTexture_GetCubeMapSurface(This->wineD3DCubeTexture,
+            (WINED3DCUBEMAP_FACES) FaceType, Level, &mySurface);
+    if (SUCCEEDED(hr) && ppCubeMapSurface)
+    {
+       *ppCubeMapSurface = IWineD3DCubeTexture_GetParent(mySurface);
+       IDirect3DSurface8_AddRef(*ppCubeMapSurface);
        IWineD3DCubeTexture_Release(mySurface);
     }
     wined3d_mutex_unlock();
 
-    return hrc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DCubeTexture8Impl_LockRect(LPDIRECT3DCUBETEXTURE8 iface, D3DCUBEMAP_FACES FaceType, UINT Level, D3DLOCKED_RECT* pLockedRect, CONST RECT *pRect, DWORD Flags) {
@@ -357,9 +362,9 @@ HRESULT cubetexture_init(IDirect3DCubeTexture8Impl *texture, IDirect3DDevice8Imp
     texture->ref = 1;
 
     wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateCubeTexture(device->WineD3DDevice, edge_length, levels, usage & WINED3DUSAGE_MASK,
-            wined3dformat_from_d3dformat(format), pool, &texture->wineD3DCubeTexture,
-            (IUnknown *)texture, &d3d8_cubetexture_wined3d_parent_ops);
+    hr = IWineD3DDevice_CreateCubeTexture(device->WineD3DDevice, edge_length, levels,
+            usage & WINED3DUSAGE_MASK, wined3dformat_from_d3dformat(format), pool, texture,
+            &d3d8_cubetexture_wined3d_parent_ops, &texture->wineD3DCubeTexture);
     wined3d_mutex_unlock();
     if (FAILED(hr))
     {
index 5af8582..7a1a11a 100644 (file)
        <library>advapi32</library>
        <library>wined3d</library>
 
+       <file>buffer.c</file>
        <file>cubetexture.c</file>
        <file>d3d8_main.c</file>
        <file>device.c</file>
        <file>directx.c</file>
-       <file>indexbuffer.c</file>
-       <file>pixelshader.c</file>
+       <file>shader.c</file>
        <file>surface.c</file>
        <file>swapchain.c</file>
        <file>texture.c</file>
-       <file>vertexbuffer.c</file>
        <file>vertexdeclaration.c</file>
-       <file>vertexshader.c</file>
        <file>volume.c</file>
        <file>volumetexture.c</file>
        <file>version.rc</file>
index c471049..6cefe57 100644 (file)
@@ -98,7 +98,7 @@ HRESULT WINAPI ValidateVertexShader(DWORD* vertexshader, DWORD* reserved1, DWORD
             ret=S_OK;
             break;
         default:
-            ERR("vertexshader version mismatch\n");
+            WARN("Invalid shader version token %#x.\n", *vertexshader);
             ret=E_FAIL;
         }
 
@@ -136,7 +136,7 @@ HRESULT WINAPI ValidatePixelShader(DWORD* pixelshader, DWORD* reserved1, BOOL bo
             ret=S_OK;
             break;
         default:
-            ERR("pixelshader version mismatch\n");
+            WARN("Invalid shader version token %#x.\n", *pixelshader);
             ret=E_FAIL;
         }
   return ret;
index 4ba399b..7e89667 100644 (file)
@@ -220,7 +220,7 @@ struct IDirect3DVolume8Impl
 };
 
 HRESULT volume_init(IDirect3DVolume8Impl *volume, IDirect3DDevice8Impl *device, UINT width, UINT height,
-        UINT depth, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool) DECLSPEC_HIDDEN;
+        UINT depth, DWORD usage, enum wined3d_format_id format, WINED3DPOOL pool) DECLSPEC_HIDDEN;
 
 /* ------------------- */
 /* IDirect3DSwapChain8 */
@@ -329,7 +329,7 @@ struct IDirect3DIndexBuffer8Impl
     /* Parent reference */
     LPDIRECT3DDEVICE8                parentDevice;
 
-    WINED3DFORMAT                    format;
+    enum wined3d_format_id format;
 };
 
 HRESULT indexbuffer_init(IDirect3DIndexBuffer8Impl *buffer, IDirect3DDevice8Impl *device,
@@ -535,13 +535,8 @@ typedef struct IDirect3DPixelShader8Impl {
 HRESULT pixelshader_init(IDirect3DPixelShader8Impl *shader, IDirect3DDevice8Impl *device,
         const DWORD *byte_code, DWORD shader_handle) DECLSPEC_HIDDEN;
 
-/**
- * Internals functions
- *
- * to see how not defined it here
- */
-D3DFORMAT d3dformat_from_wined3dformat(WINED3DFORMAT format) DECLSPEC_HIDDEN;
-WINED3DFORMAT wined3dformat_from_d3dformat(D3DFORMAT format) DECLSPEC_HIDDEN;
+D3DFORMAT d3dformat_from_wined3dformat(enum wined3d_format_id format) DECLSPEC_HIDDEN;
+enum wined3d_format_id wined3dformat_from_d3dformat(D3DFORMAT format) DECLSPEC_HIDDEN;
 void load_local_constants(const DWORD *d3d8_elements, IWineD3DVertexShader *wined3d_vertex_shader) DECLSPEC_HIDDEN;
 size_t parse_token(const DWORD *pToken) DECLSPEC_HIDDEN;
 
index 12ed0fb..f54f043 100644 (file)
@@ -36,7 +36,7 @@
 
 WINE_DEFAULT_DEBUG_CHANNEL(d3d8);
 
-D3DFORMAT d3dformat_from_wined3dformat(WINED3DFORMAT format)
+D3DFORMAT d3dformat_from_wined3dformat(enum wined3d_format_id format)
 {
     BYTE *c = (BYTE *)&format;
 
@@ -82,12 +82,12 @@ D3DFORMAT d3dformat_from_wined3dformat(WINED3DFORMAT format)
         case WINED3DFMT_R16_UINT: return D3DFMT_INDEX16;
         case WINED3DFMT_R32_UINT: return D3DFMT_INDEX32;
         default:
-            FIXME("Unhandled WINED3DFORMAT %#x\n", format);
+            FIXME("Unhandled wined3d format %#x.\n", format);
             return D3DFMT_UNKNOWN;
     }
 }
 
-WINED3DFORMAT wined3dformat_from_d3dformat(D3DFORMAT format)
+enum wined3d_format_id wined3dformat_from_d3dformat(D3DFORMAT format)
 {
     BYTE *c = (BYTE *)&format;
 
@@ -260,8 +260,7 @@ static ULONG WINAPI D3D8CB_DestroySwapChain(IWineD3DSwapChain *swapchain)
 
     TRACE("swapchain %p.\n", swapchain);
 
-    IWineD3DSwapChain_GetParent(swapchain, &parent);
-    IUnknown_Release(parent);
+    parent = IWineD3DSwapChain_GetParent(swapchain);
     return IUnknown_Release(parent);
 }
 
@@ -370,10 +369,11 @@ static HRESULT WINAPI IDirect3DDevice8Impl_ResourceManagerDiscardBytes(LPDIRECT3
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DDevice8Impl_GetDirect3D(LPDIRECT3DDEVICE8 iface, IDirect3D8** ppD3D8) {
+static HRESULT WINAPI IDirect3DDevice8Impl_GetDirect3D(IDirect3DDevice8 *iface, IDirect3D8 **ppD3D8)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
-    HRESULT hr = D3D_OK;
-    IWineD3D* pWineD3D;
+    IWineD3D *pWineD3D;
+    HRESULT hr;
 
     TRACE("iface %p, d3d8 %p.\n", iface, ppD3D8);
 
@@ -383,11 +383,14 @@ static HRESULT WINAPI IDirect3DDevice8Impl_GetDirect3D(LPDIRECT3DDEVICE8 iface,
 
     wined3d_mutex_lock();
     hr = IWineD3DDevice_GetDirect3D(This->WineD3DDevice, &pWineD3D);
-    if (hr == D3D_OK && pWineD3D != NULL)
+    if (SUCCEEDED(hr) && pWineD3D)
     {
-        IWineD3D_GetParent(pWineD3D,(IUnknown **)ppD3D8);
+        *ppD3D8 = IWineD3D_GetParent(pWineD3D);
+        IDirect3D8_AddRef(*ppD3D8);
         IWineD3D_Release(pWineD3D);
-    } else {
+    }
+    else
+    {
         FIXME("Call to IWineD3DDevice_GetDirect3D failed\n");
         *ppD3D8 = NULL;
     }
@@ -589,23 +592,27 @@ static HRESULT WINAPI IDirect3DDevice8Impl_Present(LPDIRECT3DDEVICE8 iface, CONS
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DDevice8Impl_GetBackBuffer(LPDIRECT3DDEVICE8 iface, UINT BackBuffer, D3DBACKBUFFER_TYPE Type, IDirect3DSurface8** ppBackBuffer) {
+static HRESULT WINAPI IDirect3DDevice8Impl_GetBackBuffer(IDirect3DDevice8 *iface,
+        UINT BackBuffer, D3DBACKBUFFER_TYPE Type, IDirect3DSurface8 **ppBackBuffer)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
     IWineD3DSurface *retSurface = NULL;
-    HRESULT rc = D3D_OK;
+    HRESULT hr;
 
     TRACE("iface %p, backbuffer_idx %u, backbuffer_type %#x, backbuffer %p.\n",
             iface, BackBuffer, Type, ppBackBuffer);
 
     wined3d_mutex_lock();
-    rc = IWineD3DDevice_GetBackBuffer(This->WineD3DDevice, 0, BackBuffer, (WINED3DBACKBUFFER_TYPE) Type, &retSurface);
-    if (rc == D3D_OK && NULL != retSurface && NULL != ppBackBuffer) {
-        IWineD3DSurface_GetParent(retSurface, (IUnknown **)ppBackBuffer);
+    hr = IWineD3DDevice_GetBackBuffer(This->WineD3DDevice, 0, BackBuffer, (WINED3DBACKBUFFER_TYPE)Type, &retSurface);
+    if (SUCCEEDED(hr) && retSurface && ppBackBuffer)
+    {
+        *ppBackBuffer = IWineD3DSurface_GetParent(retSurface);
+        IDirect3DSurface8_AddRef(*ppBackBuffer);
         IWineD3DSurface_Release(retSurface);
     }
     wined3d_mutex_unlock();
 
-    return rc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DDevice8Impl_GetRasterStatus(LPDIRECT3DDEVICE8 iface, D3DRASTER_STATUS* pRasterStatus) {
@@ -879,7 +886,7 @@ static HRESULT WINAPI IDirect3DDevice8Impl_CopyRects(LPDIRECT3DDEVICE8 iface, ID
     IDirect3DSurface8Impl *Dest = (IDirect3DSurface8Impl *) pDestinationSurface;
 
     HRESULT              hr = WINED3D_OK;
-    WINED3DFORMAT        srcFormat, destFormat;
+    enum wined3d_format_id srcFormat, destFormat;
     WINED3DSURFACE_DESC  winedesc;
 
     TRACE("iface %p, src_surface %p, src_rects %p, rect_count %u, dst_surface %p, dst_points %p.\n",
@@ -984,10 +991,12 @@ static HRESULT WINAPI IDirect3DDevice8Impl_SetRenderTarget(LPDIRECT3DDEVICE8 ifa
     return hr;
 }
 
-static HRESULT  WINAPI  IDirect3DDevice8Impl_GetRenderTarget(LPDIRECT3DDEVICE8 iface, IDirect3DSurface8** ppRenderTarget) {
+static HRESULT WINAPI IDirect3DDevice8Impl_GetRenderTarget(IDirect3DDevice8 *iface,
+        IDirect3DSurface8 **ppRenderTarget)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
-    HRESULT hr = D3D_OK;
     IWineD3DSurface *pRenderTarget;
+    HRESULT hr;
 
     TRACE("iface %p, render_target %p.\n", iface, ppRenderTarget);
 
@@ -997,11 +1006,14 @@ static HRESULT  WINAPI  IDirect3DDevice8Impl_GetRenderTarget(LPDIRECT3DDEVICE8 i
 
     wined3d_mutex_lock();
     hr = IWineD3DDevice_GetRenderTarget(This->WineD3DDevice, 0, &pRenderTarget);
-
-    if (hr == D3D_OK && pRenderTarget != NULL) {
-        IWineD3DSurface_GetParent(pRenderTarget,(IUnknown**)ppRenderTarget);
+    if (SUCCEEDED(hr) && pRenderTarget)
+    {
+        *ppRenderTarget = IWineD3DSurface_GetParent(pRenderTarget);
+        IDirect3DSurface8_AddRef(*ppRenderTarget);
         IWineD3DSurface_Release(pRenderTarget);
-    } else {
+    }
+    else
+    {
         FIXME("Call to IWineD3DDevice_GetRenderTarget failed\n");
         *ppRenderTarget = NULL;
     }
@@ -1010,10 +1022,12 @@ static HRESULT  WINAPI  IDirect3DDevice8Impl_GetRenderTarget(LPDIRECT3DDEVICE8 i
     return hr;
 }
 
-static HRESULT  WINAPI  IDirect3DDevice8Impl_GetDepthStencilSurface(LPDIRECT3DDEVICE8 iface, IDirect3DSurface8** ppZStencilSurface) {
+static HRESULT WINAPI IDirect3DDevice8Impl_GetDepthStencilSurface(IDirect3DDevice8 *iface,
+        IDirect3DSurface8 **ppZStencilSurface)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
-    HRESULT hr = D3D_OK;
     IWineD3DSurface *pZStencilSurface;
+    HRESULT hr;
 
     TRACE("iface %p, depth_stencil %p.\n", iface, ppZStencilSurface);
 
@@ -1022,11 +1036,15 @@ static HRESULT  WINAPI  IDirect3DDevice8Impl_GetDepthStencilSurface(LPDIRECT3DDE
     }
 
     wined3d_mutex_lock();
-    hr=IWineD3DDevice_GetDepthStencilSurface(This->WineD3DDevice,&pZStencilSurface);
-    if (hr == WINED3D_OK) {
-        IWineD3DSurface_GetParent(pZStencilSurface,(IUnknown**)ppZStencilSurface);
+    hr = IWineD3DDevice_GetDepthStencilSurface(This->WineD3DDevice, &pZStencilSurface);
+    if (SUCCEEDED(hr))
+    {
+        *ppZStencilSurface = IWineD3DSurface_GetParent(pZStencilSurface);
+        IDirect3DSurface8_AddRef(*ppZStencilSurface);
         IWineD3DSurface_Release(pZStencilSurface);
-    }else{
+    }
+    else
+    {
         if (hr != WINED3DERR_NOTFOUND)
                 FIXME("Call to IWineD3DDevice_GetDepthStencilSurface failed with 0x%08x\n", hr);
         *ppZStencilSurface = NULL;
@@ -1069,9 +1087,8 @@ static HRESULT WINAPI IDirect3DDevice8Impl_Clear(LPDIRECT3DDEVICE8 iface, DWORD
     TRACE("iface %p, rect_count %u, rects %p, flags %#x, color 0x%08x, z %.8e, stencil %u.\n",
             iface, Count, pRects, Flags, Color, Z, Stencil);
 
-    /* Note: D3DRECT is compatible with WINED3DRECT */
     wined3d_mutex_lock();
-    hr = IWineD3DDevice_Clear(This->WineD3DDevice, Count, (CONST WINED3DRECT*) pRects, Flags, Color, Z, Stencil);
+    hr = IWineD3DDevice_Clear(This->WineD3DDevice, Count, (const RECT *)pRects, Flags, Color, Z, Stencil);
     wined3d_mutex_unlock();
 
     return hr;
@@ -1415,8 +1432,7 @@ static HRESULT WINAPI IDirect3DDevice8Impl_CreateStateBlock(IDirect3DDevice8 *if
     }
 
     wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateStateBlock(This->WineD3DDevice, (WINED3DSTATEBLOCKTYPE)Type,
-            &stateblock, NULL);
+    hr = IWineD3DDevice_CreateStateBlock(This->WineD3DDevice, (WINED3DSTATEBLOCKTYPE)Type, &stateblock);
     if (FAILED(hr))
     {
         wined3d_mutex_unlock();
@@ -1469,7 +1485,9 @@ static HRESULT WINAPI IDirect3DDevice8Impl_GetClipStatus(LPDIRECT3DDEVICE8 iface
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DDevice8Impl_GetTexture(LPDIRECT3DDEVICE8 iface, DWORD Stage,IDirect3DBaseTexture8** ppTexture) {
+static HRESULT WINAPI IDirect3DDevice8Impl_GetTexture(IDirect3DDevice8 *iface,
+        DWORD Stage, IDirect3DBaseTexture8 **ppTexture)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
     IWineD3DBaseTexture *retTexture;
     HRESULT hr;
@@ -1492,7 +1510,8 @@ static HRESULT WINAPI IDirect3DDevice8Impl_GetTexture(LPDIRECT3DDEVICE8 iface, D
 
     if (retTexture)
     {
-        IWineD3DBaseTexture_GetParent(retTexture, (IUnknown **)ppTexture);
+        *ppTexture = IWineD3DBaseTexture_GetParent(retTexture);
+        IDirect3DBaseTexture8_AddRef(*ppTexture);
         IWineD3DBaseTexture_Release(retTexture);
     }
     else
@@ -1556,13 +1575,22 @@ tss_lookup[] =
     {FALSE, WINED3DTSS_RESULTARG},              /* 28, D3DTSS_RESULTARG */
 };
 
-static HRESULT  WINAPI  IDirect3DDevice8Impl_GetTextureStageState(LPDIRECT3DDEVICE8 iface, DWORD Stage,D3DTEXTURESTAGESTATETYPE Type,DWORD* pValue) {
+static HRESULT  WINAPI  IDirect3DDevice8Impl_GetTextureStageState(LPDIRECT3DDEVICE8 iface, DWORD Stage, D3DTEXTURESTAGESTATETYPE Type, DWORD *pValue)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
-    const struct tss_lookup *l = &tss_lookup[Type];
+    const struct tss_lookup *l;
     HRESULT hr;
 
     TRACE("iface %p, stage %u, state %#x, value %p.\n", iface, Stage, Type, pValue);
 
+    if (Type >= sizeof(tss_lookup) / sizeof(*tss_lookup))
+    {
+        WARN("Invalid Type %#x passed.\n", Type);
+        return D3D_OK;
+    }
+
+    l = &tss_lookup[Type];
+
     wined3d_mutex_lock();
     if (l->sampler_state) hr = IWineD3DDevice_GetSamplerState(This->WineD3DDevice, Stage, l->state, pValue);
     else hr = IWineD3DDevice_GetTextureStageState(This->WineD3DDevice, Stage, l->state, pValue);
@@ -1571,13 +1599,22 @@ static HRESULT  WINAPI  IDirect3DDevice8Impl_GetTextureStageState(LPDIRECT3DDEVI
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DDevice8Impl_SetTextureStageState(LPDIRECT3DDEVICE8 iface, DWORD Stage, D3DTEXTURESTAGESTATETYPE Type, DWORD Value) {
+static HRESULT WINAPI IDirect3DDevice8Impl_SetTextureStageState(LPDIRECT3DDEVICE8 iface, DWORD Stage, D3DTEXTURESTAGESTATETYPE Type, DWORD Value)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
-    const struct tss_lookup *l = &tss_lookup[Type];
+    const struct tss_lookup *l;
     HRESULT hr;
 
     TRACE("iface %p, stage %u, state %#x, value %#x.\n", iface, Stage, Type, Value);
 
+    if (Type >= sizeof(tss_lookup) / sizeof(*tss_lookup))
+    {
+        WARN("Invalid Type %#x passed.\n", Type);
+        return D3D_OK;
+    }
+
+    l = &tss_lookup[Type];
+
     wined3d_mutex_lock();
     if (l->sampler_state) hr = IWineD3DDevice_SetSamplerState(This->WineD3DDevice, Stage, l->state, Value);
     else hr = IWineD3DDevice_SetTextureStageState(This->WineD3DDevice, Stage, l->state, Value);
@@ -1902,22 +1939,23 @@ static HRESULT WINAPI IDirect3DDevice8Impl_SetVertexShader(LPDIRECT3DDEVICE8 ifa
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DDevice8Impl_GetVertexShader(LPDIRECT3DDEVICE8 iface, DWORD* ppShader) {
+static HRESULT WINAPI IDirect3DDevice8Impl_GetVertexShader(IDirect3DDevice8 *iface, DWORD *ppShader)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
     IWineD3DVertexDeclaration *wined3d_declaration;
     IDirect3DVertexDeclaration8 *d3d8_declaration;
-    HRESULT hrc;
+    HRESULT hr;
 
     TRACE("iface %p, shader %p.\n", iface, ppShader);
 
     wined3d_mutex_lock();
-    hrc = IWineD3DDevice_GetVertexDeclaration(This->WineD3DDevice, &wined3d_declaration);
-    if (FAILED(hrc))
+    hr = IWineD3DDevice_GetVertexDeclaration(This->WineD3DDevice, &wined3d_declaration);
+    if (FAILED(hr))
     {
         wined3d_mutex_unlock();
         WARN("(%p) : Call to IWineD3DDevice_GetVertexDeclaration failed %#x (device %p)\n",
-                This, hrc, This->WineD3DDevice);
-        return hrc;
+                This, hr, This->WineD3DDevice);
+        return hr;
     }
 
     if (!wined3d_declaration)
@@ -1927,24 +1965,20 @@ static HRESULT WINAPI IDirect3DDevice8Impl_GetVertexShader(LPDIRECT3DDEVICE8 ifa
         return D3D_OK;
     }
 
-    hrc = IWineD3DVertexDeclaration_GetParent(wined3d_declaration, (IUnknown **)&d3d8_declaration);
+    d3d8_declaration = IWineD3DVertexDeclaration_GetParent(wined3d_declaration);
     IWineD3DVertexDeclaration_Release(wined3d_declaration);
     wined3d_mutex_unlock();
-    if (SUCCEEDED(hrc))
-    {
-        *ppShader = ((IDirect3DVertexDeclaration8Impl *)d3d8_declaration)->shader_handle;
-        IDirect3DVertexDeclaration8_Release(d3d8_declaration);
-    }
+    *ppShader = ((IDirect3DVertexDeclaration8Impl *)d3d8_declaration)->shader_handle;
 
     TRACE("(%p) : returning %#x\n", This, *ppShader);
 
-    return hrc;
+    return hr;
 }
 
 static HRESULT  WINAPI  IDirect3DDevice8Impl_DeleteVertexShader(LPDIRECT3DDEVICE8 iface, DWORD pShader) {
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
     IDirect3DVertexShader8Impl *shader;
-    IWineD3DVertexShader *cur = NULL;
+    IWineD3DVertexShader *cur;
 
     TRACE("iface %p, shader %#x.\n", iface, pShader);
 
@@ -1958,8 +1992,7 @@ static HRESULT  WINAPI  IDirect3DDevice8Impl_DeleteVertexShader(LPDIRECT3DDEVICE
         return D3DERR_INVALIDCALL;
     }
 
-    IWineD3DDevice_GetVertexShader(This->WineD3DDevice, &cur);
-
+    cur = IWineD3DDevice_GetVertexShader(This->WineD3DDevice);
     if (cur)
     {
         if (cur == shader->wineD3DVertexShader) IDirect3DDevice8_SetVertexShader(iface, 0);
@@ -2107,10 +2140,12 @@ static HRESULT WINAPI IDirect3DDevice8Impl_SetIndices(LPDIRECT3DDEVICE8 iface, I
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DDevice8Impl_GetIndices(LPDIRECT3DDEVICE8 iface, IDirect3DIndexBuffer8** ppIndexData,UINT* pBaseVertexIndex) {
+static HRESULT WINAPI IDirect3DDevice8Impl_GetIndices(IDirect3DDevice8 *iface,
+        IDirect3DIndexBuffer8 **ppIndexData, UINT *pBaseVertexIndex)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
     IWineD3DBuffer *retIndexData = NULL;
-    HRESULT rc = D3D_OK;
+    HRESULT hr;
 
     TRACE("iface %p, buffer %p, base_vertex_index %p.\n", iface, ppIndexData, pBaseVertexIndex);
 
@@ -2121,17 +2156,19 @@ static HRESULT WINAPI IDirect3DDevice8Impl_GetIndices(LPDIRECT3DDEVICE8 iface, I
     /* The case from UINT to INT is safe because d3d8 will never set negative values */
     wined3d_mutex_lock();
     IWineD3DDevice_GetBaseVertexIndex(This->WineD3DDevice, (INT *) pBaseVertexIndex);
-    rc = IWineD3DDevice_GetIndexBuffer(This->WineD3DDevice, &retIndexData);
-    if (SUCCEEDED(rc) && retIndexData) {
-        IWineD3DBuffer_GetParent(retIndexData, (IUnknown **)ppIndexData);
+    hr = IWineD3DDevice_GetIndexBuffer(This->WineD3DDevice, &retIndexData);
+    if (SUCCEEDED(hr) && retIndexData)
+    {
+        *ppIndexData = IWineD3DBuffer_GetParent(retIndexData);
+        IDirect3DIndexBuffer8_AddRef(*ppIndexData);
         IWineD3DBuffer_Release(retIndexData);
     } else {
-        if (FAILED(rc)) FIXME("Call to GetIndices failed\n");
+        if (FAILED(hr)) FIXME("Call to GetIndices failed\n");
         *ppIndexData = NULL;
     }
     wined3d_mutex_unlock();
 
-    return rc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DDevice8Impl_CreatePixelShader(IDirect3DDevice8 *iface,
@@ -2219,10 +2256,10 @@ static HRESULT WINAPI IDirect3DDevice8Impl_SetPixelShader(LPDIRECT3DDEVICE8 ifac
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DDevice8Impl_GetPixelShader(LPDIRECT3DDEVICE8 iface, DWORD* ppShader) {
+static HRESULT WINAPI IDirect3DDevice8Impl_GetPixelShader(IDirect3DDevice8 *iface, DWORD *ppShader)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
     IWineD3DPixelShader *object;
-    HRESULT hrc = D3D_OK;
 
     TRACE("iface %p, shader %p.\n", iface, ppShader);
 
@@ -2232,27 +2269,29 @@ static HRESULT WINAPI IDirect3DDevice8Impl_GetPixelShader(LPDIRECT3DDEVICE8 ifac
     }
 
     wined3d_mutex_lock();
-    hrc = IWineD3DDevice_GetPixelShader(This->WineD3DDevice, &object);
-    if (D3D_OK == hrc && NULL != object) {
+    object = IWineD3DDevice_GetPixelShader(This->WineD3DDevice);
+    if (object)
+    {
         IDirect3DPixelShader8Impl *d3d8_shader;
-        hrc = IWineD3DPixelShader_GetParent(object, (IUnknown **)&d3d8_shader);
+        d3d8_shader = IWineD3DPixelShader_GetParent(object);
         IWineD3DPixelShader_Release(object);
         *ppShader = d3d8_shader->handle;
-        IDirect3DPixelShader8_Release((IDirect3DPixelShader8 *)d3d8_shader);
-    } else {
+    }
+    else
+    {
         *ppShader = 0;
     }
     wined3d_mutex_unlock();
 
     TRACE("(%p) : returning %#x\n", This, *ppShader);
 
-    return hrc;
+    return D3D_OK;
 }
 
 static HRESULT WINAPI IDirect3DDevice8Impl_DeletePixelShader(LPDIRECT3DDEVICE8 iface, DWORD pShader) {
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
     IDirect3DPixelShader8Impl *shader;
-    IWineD3DPixelShader *cur = NULL;
+    IWineD3DPixelShader *cur;
 
     TRACE("iface %p, shader %#x.\n", iface, pShader);
 
@@ -2266,8 +2305,7 @@ static HRESULT WINAPI IDirect3DDevice8Impl_DeletePixelShader(LPDIRECT3DDEVICE8 i
         return D3DERR_INVALIDCALL;
     }
 
-    IWineD3DDevice_GetPixelShader(This->WineD3DDevice, &cur);
-
+    cur = IWineD3DDevice_GetPixelShader(This->WineD3DDevice);
     if (cur)
     {
         if (cur == shader->wineD3DPixelShader) IDirect3DDevice8_SetPixelShader(iface, 0);
@@ -2393,10 +2431,12 @@ static HRESULT WINAPI IDirect3DDevice8Impl_SetStreamSource(LPDIRECT3DDEVICE8 ifa
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DDevice8Impl_GetStreamSource(LPDIRECT3DDEVICE8 iface, UINT StreamNumber,IDirect3DVertexBuffer8** pStream,UINT* pStride) {
+static HRESULT WINAPI IDirect3DDevice8Impl_GetStreamSource(IDirect3DDevice8 *iface,
+        UINT StreamNumber, IDirect3DVertexBuffer8 **pStream, UINT *pStride)
+{
     IDirect3DDevice8Impl *This = (IDirect3DDevice8Impl *)iface;
     IWineD3DBuffer *retStream = NULL;
-    HRESULT rc = D3D_OK;
+    HRESULT hr;
 
     TRACE("iface %p, stream_idx %u, buffer %p, stride %p.\n",
             iface, StreamNumber, pStream, pStride);
@@ -2406,19 +2446,22 @@ static HRESULT WINAPI IDirect3DDevice8Impl_GetStreamSource(LPDIRECT3DDEVICE8 ifa
     }
 
     wined3d_mutex_lock();
-    rc = IWineD3DDevice_GetStreamSource(This->WineD3DDevice, StreamNumber, &retStream, 0 /* Offset in bytes */, pStride);
-    if (rc == D3D_OK  && NULL != retStream) {
-        IWineD3DBuffer_GetParent(retStream, (IUnknown **)pStream);
+    hr = IWineD3DDevice_GetStreamSource(This->WineD3DDevice, StreamNumber,
+            &retStream, 0 /* Offset in bytes */, pStride);
+    if (SUCCEEDED(hr) && retStream)
+    {
+        *pStream = IWineD3DBuffer_GetParent(retStream);
+        IDirect3DVertexBuffer8_AddRef(*pStream);
         IWineD3DBuffer_Release(retStream);
-    }else{
-        if (rc != D3D_OK){
-            FIXME("Call to GetStreamSource failed %p\n",  pStride);
-        }
+    }
+    else
+    {
+        if (FAILED(hr)) FIXME("Call to GetStreamSource failed, hr %#x.\n", hr);
         *pStream = NULL;
     }
     wined3d_mutex_unlock();
 
-    return rc;
+    return hr;
 }
 
 static const IDirect3DDevice8Vtbl Direct3DDevice8_Vtbl =
@@ -2556,7 +2599,7 @@ static void STDMETHODCALLTYPE device_parent_WineD3DDeviceCreated(IWineD3DDeviceP
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateSurface(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, WINED3DFORMAT format, DWORD usage,
+        IUnknown *superior, UINT width, UINT height, enum wined3d_format_id format, DWORD usage,
         WINED3DPOOL pool, UINT level, WINED3DCUBEMAP_FACES face, IWineD3DSurface **surface)
 {
     struct IDirect3DDevice8Impl *This = device_from_device_parent(iface);
@@ -2594,8 +2637,9 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateSurface(IWineD3DDeviceParen
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateRenderTarget(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, WINED3DFORMAT format, WINED3DMULTISAMPLE_TYPE multisample_type,
-        DWORD multisample_quality, BOOL lockable, IWineD3DSurface **surface)
+        IUnknown *superior, UINT width, UINT height, enum wined3d_format_id format,
+        WINED3DMULTISAMPLE_TYPE multisample_type, DWORD multisample_quality, BOOL lockable,
+        IWineD3DSurface **surface)
 {
     struct IDirect3DDevice8Impl *This = device_from_device_parent(iface);
     IDirect3DSurface8Impl *d3d_surface;
@@ -2624,16 +2668,16 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateRenderTarget(IWineD3DDevice
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateDepthStencilSurface(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, WINED3DFORMAT format, WINED3DMULTISAMPLE_TYPE multisample_type,
+        UINT width, UINT height, enum wined3d_format_id format, WINED3DMULTISAMPLE_TYPE multisample_type,
         DWORD multisample_quality, BOOL discard, IWineD3DSurface **surface)
 {
     struct IDirect3DDevice8Impl *This = device_from_device_parent(iface);
     IDirect3DSurface8Impl *d3d_surface;
     HRESULT hr;
 
-    TRACE("iface %p, superior %p, width %u, height %u, format %#x, multisample_type %#x,\n"
+    TRACE("iface %p, width %u, height %u, format %#x, multisample_type %#x,\n"
             "\tmultisample_quality %u, discard %u, surface %p\n",
-            iface, superior, width, height, format, multisample_type, multisample_quality, discard, surface);
+            iface, width, height, format, multisample_type, multisample_quality, discard, surface);
 
     hr = IDirect3DDevice8_CreateDepthStencilSurface((IDirect3DDevice8 *)This, width, height,
             d3dformat_from_wined3dformat(format), multisample_type, (IDirect3DSurface8 **)&d3d_surface);
@@ -2654,7 +2698,7 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateDepthStencilSurface(IWineD3
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateVolume(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, UINT depth, WINED3DFORMAT format,
+        IUnknown *superior, UINT width, UINT height, UINT depth, enum wined3d_format_id format,
         WINED3DPOOL pool, DWORD usage, IWineD3DVolume **volume)
 {
     struct IDirect3DDevice8Impl *This = device_from_device_parent(iface);
@@ -2766,9 +2810,8 @@ static const IWineD3DDeviceParentVtbl d3d8_wined3d_device_parent_vtbl =
 
 static void setup_fpu(void)
 {
-    WORD cw;
-
 #if defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__))
+    WORD cw;
     __asm__ volatile ("fnstcw %0" : "=m" (cw));
     cw = (cw & ~0xf3f) | 0x3f;
     __asm__ volatile ("fldcw %0" : : "m" (cw));
@@ -2798,7 +2841,7 @@ HRESULT device_init(IDirect3DDevice8Impl *device, IWineD3D *wined3d, UINT adapte
     if (!(flags & D3DCREATE_FPU_PRESERVE)) setup_fpu();
 
     wined3d_mutex_lock();
-    hr = IWineD3D_CreateDevice(wined3d, adapter, device_type, focus_window, flags, (IUnknown *)device,
+    hr = IWineD3D_CreateDevice(wined3d, adapter, device_type, focus_window, flags,
             (IWineD3DDeviceParent *)&device->device_parent_vtbl, &device->WineD3DDevice);
     if (FAILED(hr))
     {
diff --git a/reactos/dll/directx/wine/d3d8/indexbuffer.c b/reactos/dll/directx/wine/d3d8/indexbuffer.c
deleted file mode 100644 (file)
index b98c2d3..0000000
+++ /dev/null
@@ -1,285 +0,0 @@
-/*
- * IDirect3DIndexBuffer8 implementation
- *
- * Copyright 2005 Oliver Stieber
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "d3d8_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d8);
-
-/* IDirect3DIndexBuffer8 IUnknown parts follow: */
-static HRESULT WINAPI IDirect3DIndexBuffer8Impl_QueryInterface(LPDIRECT3DINDEXBUFFER8 iface, REFIID riid, LPVOID *ppobj) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-
-    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppobj);
-
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IDirect3DResource8)
-        || IsEqualGUID(riid, &IID_IDirect3DIndexBuffer8)) {
-        IUnknown_AddRef(iface);
-        *ppobj = This;
-        return S_OK;
-    }
-
-    WARN("(%p)->(%s,%p),not found\n", This, debugstr_guid(riid), ppobj);
-    *ppobj = NULL;
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI IDirect3DIndexBuffer8Impl_AddRef(LPDIRECT3DINDEXBUFFER8 iface) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    ULONG ref = InterlockedIncrement(&This->ref);
-
-    TRACE("%p increasing refcount to %u.\n", iface, ref);
-
-    if (ref == 1)
-    {
-        IDirect3DDevice8_AddRef(This->parentDevice);
-        wined3d_mutex_lock();
-        IWineD3DBuffer_AddRef(This->wineD3DIndexBuffer);
-        wined3d_mutex_unlock();
-    }
-
-    return ref;
-}
-
-static ULONG WINAPI IDirect3DIndexBuffer8Impl_Release(LPDIRECT3DINDEXBUFFER8 iface) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    ULONG ref = InterlockedDecrement(&This->ref);
-
-    TRACE("%p decreasing refcount to %u.\n", iface, ref);
-
-    if (ref == 0) {
-        IDirect3DDevice8 *parentDevice = This->parentDevice;
-
-        wined3d_mutex_lock();
-        IWineD3DBuffer_Release(This->wineD3DIndexBuffer);
-        wined3d_mutex_unlock();
-
-        /* Release the device last, as it may cause the device to be destroyed. */
-        IDirect3DDevice8_Release(parentDevice);
-    }
-    return ref;
-}
-
-/* IDirect3DIndexBuffer8 IDirect3DResource8 Interface follow: */
-static HRESULT WINAPI IDirect3DIndexBuffer8Impl_GetDevice(IDirect3DIndexBuffer8 *iface, IDirect3DDevice8 **device)
-{
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-
-    TRACE("iface %p, device %p.\n", iface, device);
-
-    *device = (IDirect3DDevice8 *)This->parentDevice;
-    IDirect3DDevice8_AddRef(*device);
-
-    TRACE("Returning device %p.\n", *device);
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI IDirect3DIndexBuffer8Impl_SetPrivateData(LPDIRECT3DINDEXBUFFER8 iface, REFGUID refguid, CONST void* pData, DWORD SizeOfData, DWORD Flags) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s, data %p, data_size %u, flags %#x.\n",
-            iface, debugstr_guid(refguid), pData, SizeOfData, Flags);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_SetPrivateData(This->wineD3DIndexBuffer, refguid, pData, SizeOfData, Flags);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DIndexBuffer8Impl_GetPrivateData(LPDIRECT3DINDEXBUFFER8 iface, REFGUID refguid, void *pData, DWORD *pSizeOfData) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s, data %p, data_size %p.\n",
-            iface, debugstr_guid(refguid), pData, pSizeOfData);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_GetPrivateData(This->wineD3DIndexBuffer, refguid, pData, pSizeOfData);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DIndexBuffer8Impl_FreePrivateData(LPDIRECT3DINDEXBUFFER8 iface, REFGUID refguid) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(refguid));
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_FreePrivateData(This->wineD3DIndexBuffer, refguid);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static DWORD WINAPI IDirect3DIndexBuffer8Impl_SetPriority(LPDIRECT3DINDEXBUFFER8 iface, DWORD PriorityNew) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    DWORD ret;
-
-    TRACE("iface %p, priority %u.\n", iface, PriorityNew);
-
-    wined3d_mutex_lock();
-    ret = IWineD3DBuffer_SetPriority(This->wineD3DIndexBuffer, PriorityNew);
-    wined3d_mutex_unlock();
-
-    return ret;
-}
-
-static DWORD WINAPI IDirect3DIndexBuffer8Impl_GetPriority(LPDIRECT3DINDEXBUFFER8 iface) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    DWORD ret;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    ret = IWineD3DBuffer_GetPriority(This->wineD3DIndexBuffer);
-    wined3d_mutex_unlock();
-
-    return ret;
-}
-
-static void WINAPI IDirect3DIndexBuffer8Impl_PreLoad(LPDIRECT3DINDEXBUFFER8 iface) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    IWineD3DBuffer_PreLoad(This->wineD3DIndexBuffer);
-    wined3d_mutex_unlock();
-}
-
-static D3DRESOURCETYPE WINAPI IDirect3DIndexBuffer8Impl_GetType(IDirect3DIndexBuffer8 *iface)
-{
-    TRACE("iface %p.\n", iface);
-
-    return D3DRTYPE_INDEXBUFFER;
-}
-
-/* IDirect3DIndexBuffer8 Interface follow: */
-static HRESULT WINAPI IDirect3DIndexBuffer8Impl_Lock(LPDIRECT3DINDEXBUFFER8 iface, UINT OffsetToLock, UINT SizeToLock, BYTE **ppbData, DWORD Flags) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, offset %u, size %u, data %p, flags %#x.\n",
-            iface, OffsetToLock, SizeToLock, ppbData, Flags);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_Map(This->wineD3DIndexBuffer, OffsetToLock, SizeToLock, ppbData, Flags);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DIndexBuffer8Impl_Unlock(LPDIRECT3DINDEXBUFFER8 iface) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_Unmap(This->wineD3DIndexBuffer);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DIndexBuffer8Impl_GetDesc(LPDIRECT3DINDEXBUFFER8 iface, D3DINDEXBUFFER_DESC *pDesc) {
-    IDirect3DIndexBuffer8Impl *This = (IDirect3DIndexBuffer8Impl *)iface;
-    HRESULT hr;
-    WINED3DBUFFER_DESC desc;
-
-    TRACE("iface %p, desc %p.\n", iface, pDesc);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_GetDesc(This->wineD3DIndexBuffer, &desc);
-    wined3d_mutex_unlock();
-
-    if (SUCCEEDED(hr)) {
-        pDesc->Format = d3dformat_from_wined3dformat(This->format);
-        pDesc->Type = D3DRTYPE_INDEXBUFFER;
-        pDesc->Usage = desc.Usage;
-        pDesc->Pool = desc.Pool;
-        pDesc->Size = desc.Size;
-    }
-
-    return hr;
-}
-
-static const IDirect3DIndexBuffer8Vtbl Direct3DIndexBuffer8_Vtbl =
-{
-    /* IUnknown */
-    IDirect3DIndexBuffer8Impl_QueryInterface,
-    IDirect3DIndexBuffer8Impl_AddRef,
-    IDirect3DIndexBuffer8Impl_Release,
-    /* IDirect3DResource8 */
-    IDirect3DIndexBuffer8Impl_GetDevice,
-    IDirect3DIndexBuffer8Impl_SetPrivateData,
-    IDirect3DIndexBuffer8Impl_GetPrivateData,
-    IDirect3DIndexBuffer8Impl_FreePrivateData,
-    IDirect3DIndexBuffer8Impl_SetPriority,
-    IDirect3DIndexBuffer8Impl_GetPriority,
-    IDirect3DIndexBuffer8Impl_PreLoad,
-    IDirect3DIndexBuffer8Impl_GetType,
-    /* IDirect3DIndexBuffer8 */
-    IDirect3DIndexBuffer8Impl_Lock,
-    IDirect3DIndexBuffer8Impl_Unlock,
-    IDirect3DIndexBuffer8Impl_GetDesc
-};
-
-static void STDMETHODCALLTYPE d3d8_indexbuffer_wined3d_object_destroyed(void *parent)
-{
-    HeapFree(GetProcessHeap(), 0, parent);
-}
-
-static const struct wined3d_parent_ops d3d8_indexbuffer_wined3d_parent_ops =
-{
-    d3d8_indexbuffer_wined3d_object_destroyed,
-};
-
-HRESULT indexbuffer_init(IDirect3DIndexBuffer8Impl *buffer, IDirect3DDevice8Impl *device,
-        UINT size, DWORD usage, D3DFORMAT format, D3DPOOL pool)
-{
-    HRESULT hr;
-
-    buffer->lpVtbl = &Direct3DIndexBuffer8_Vtbl;
-    buffer->ref = 1;
-    buffer->format = wined3dformat_from_d3dformat(format);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateIndexBuffer(device->WineD3DDevice, size,
-            usage & WINED3DUSAGE_MASK, (WINED3DPOOL)pool, &buffer->wineD3DIndexBuffer,
-            (IUnknown *)buffer, &d3d8_indexbuffer_wined3d_parent_ops);
-    wined3d_mutex_unlock();
-    if (FAILED(hr))
-    {
-        WARN("Failed to create wined3d buffer, hr %#x.\n", hr);
-        return hr;
-    }
-
-    buffer->parentDevice = (IDirect3DDevice8 *)device;
-    IUnknown_AddRef(buffer->parentDevice);
-
-    return D3D_OK;
-}
diff --git a/reactos/dll/directx/wine/d3d8/pixelshader.c b/reactos/dll/directx/wine/d3d8/pixelshader.c
deleted file mode 100644 (file)
index 7b6d4e5..0000000
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * IDirect3DPixelShader8 implementation
- *
- * Copyright 2002-2003 Jason Edmeades
- *                     Raphael Junqueira
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "d3d8_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d8);
-
-/* IDirect3DPixelShader8 IUnknown parts follow: */
-static HRESULT WINAPI IDirect3DPixelShader8Impl_QueryInterface(IDirect3DPixelShader8 *iface, REFIID riid, LPVOID *ppobj) {
-    IDirect3DPixelShader8Impl *This = (IDirect3DPixelShader8Impl *)iface;
-
-    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppobj);
-
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IDirect3DPixelShader8)) {
-        IUnknown_AddRef(iface);
-        *ppobj = This;
-        return S_OK;
-    }
-
-    WARN("(%p)->(%s,%p),not found\n", This, debugstr_guid(riid), ppobj);
-    *ppobj = NULL;
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI IDirect3DPixelShader8Impl_AddRef(IDirect3DPixelShader8 *iface) {
-    IDirect3DPixelShader8Impl *This = (IDirect3DPixelShader8Impl *)iface;
-    ULONG ref = InterlockedIncrement(&This->ref);
-
-    TRACE("%p increasing refcount to %u.\n", iface, ref);
-
-    if (ref == 1)
-    {
-        wined3d_mutex_lock();
-        IWineD3DPixelShader_AddRef(This->wineD3DPixelShader);
-        wined3d_mutex_unlock();
-    }
-
-    return ref;
-}
-
-static ULONG WINAPI IDirect3DPixelShader8Impl_Release(IDirect3DPixelShader8 * iface) {
-    IDirect3DPixelShader8Impl *This = (IDirect3DPixelShader8Impl *)iface;
-    ULONG ref = InterlockedDecrement(&This->ref);
-
-    TRACE("%p decreasing refcount to %u.\n", iface, ref);
-
-    if (ref == 0) {
-        wined3d_mutex_lock();
-        IWineD3DPixelShader_Release(This->wineD3DPixelShader);
-        wined3d_mutex_unlock();
-    }
-    return ref;
-}
-
-static const IDirect3DPixelShader8Vtbl Direct3DPixelShader8_Vtbl =
-{
-    /* IUnknown */
-    IDirect3DPixelShader8Impl_QueryInterface,
-    IDirect3DPixelShader8Impl_AddRef,
-    IDirect3DPixelShader8Impl_Release,
-};
-
-static void STDMETHODCALLTYPE d3d8_pixelshader_wined3d_object_destroyed(void *parent)
-{
-    HeapFree(GetProcessHeap(), 0, parent);
-}
-
-static const struct wined3d_parent_ops d3d8_pixelshader_wined3d_parent_ops =
-{
-    d3d8_pixelshader_wined3d_object_destroyed,
-};
-
-HRESULT pixelshader_init(IDirect3DPixelShader8Impl *shader, IDirect3DDevice8Impl *device,
-        const DWORD *byte_code, DWORD shader_handle)
-{
-    HRESULT hr;
-
-    shader->ref = 1;
-    shader->lpVtbl = &Direct3DPixelShader8_Vtbl;
-    shader->handle = shader_handle;
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreatePixelShader(device->WineD3DDevice, byte_code,
-            NULL, &shader->wineD3DPixelShader, (IUnknown *)shader,
-            &d3d8_pixelshader_wined3d_parent_ops);
-    wined3d_mutex_unlock();
-    if (FAILED(hr))
-    {
-        WARN("Failed to create wined3d pixel shader, hr %#x.\n", hr);
-        return hr;
-    }
-
-    return D3D_OK;
-}
diff --git a/reactos/dll/directx/wine/d3d8/shader.c b/reactos/dll/directx/wine/d3d8/shader.c
new file mode 100644 (file)
index 0000000..a59f10b
--- /dev/null
@@ -0,0 +1,280 @@
+/*
+ * Copyright 2002-2003 Jason Edmeades
+ *                     Raphael Junqueira
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
+ */
+
+#include "config.h"
+#include "d3d8_private.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(d3d8);
+
+static HRESULT WINAPI d3d8_vertexshader_QueryInterface(IDirect3DVertexShader8 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    if (IsEqualGUID(riid, &IID_IDirect3DVertexShader8)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
+        IUnknown_AddRef(iface);
+        *object = iface;
+        return S_OK;
+    }
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI d3d8_vertexshader_AddRef(IDirect3DVertexShader8 *iface)
+{
+    IDirect3DVertexShader8Impl *shader = (IDirect3DVertexShader8Impl *)iface;
+    ULONG refcount = InterlockedIncrement(&shader->ref);
+
+    TRACE("%p increasing refcount to %u.\n", iface, refcount);
+
+    if (refcount == 1 && shader->wineD3DVertexShader)
+    {
+        wined3d_mutex_lock();
+        IWineD3DVertexShader_AddRef(shader->wineD3DVertexShader);
+        wined3d_mutex_unlock();
+    }
+
+    return refcount;
+}
+
+static void STDMETHODCALLTYPE d3d8_vertexshader_wined3d_object_destroyed(void *parent)
+{
+    IDirect3DVertexShader8Impl *shader = parent;
+    IDirect3DVertexDeclaration8_Release(shader->vertex_declaration);
+    HeapFree(GetProcessHeap(), 0, shader);
+}
+
+static ULONG WINAPI d3d8_vertexshader_Release(IDirect3DVertexShader8 *iface)
+{
+    IDirect3DVertexShader8Impl *shader = (IDirect3DVertexShader8Impl *)iface;
+    ULONG refcount = InterlockedDecrement(&shader->ref);
+
+    TRACE("%p decreasing refcount to %u.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        if (shader->wineD3DVertexShader)
+        {
+            wined3d_mutex_lock();
+            IWineD3DVertexShader_Release(shader->wineD3DVertexShader);
+            wined3d_mutex_unlock();
+        }
+        else
+        {
+            d3d8_vertexshader_wined3d_object_destroyed(shader);
+        }
+    }
+
+    return refcount;
+}
+
+static const IDirect3DVertexShader8Vtbl d3d8_vertexshader_vtbl =
+{
+    /* IUnknown */
+    d3d8_vertexshader_QueryInterface,
+    d3d8_vertexshader_AddRef,
+    d3d8_vertexshader_Release,
+};
+
+static const struct wined3d_parent_ops d3d8_vertexshader_wined3d_parent_ops =
+{
+    d3d8_vertexshader_wined3d_object_destroyed,
+};
+
+static HRESULT d3d8_vertexshader_create_vertexdeclaration(IDirect3DDevice8Impl *device,
+        const DWORD *declaration, DWORD shader_handle, IDirect3DVertexDeclaration8 **decl_ptr)
+{
+    IDirect3DVertexDeclaration8Impl *object;
+    HRESULT hr;
+
+    TRACE("device %p, declaration %p, shader_handle %#x, decl_ptr %p.\n",
+            device, declaration, shader_handle, decl_ptr);
+
+    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
+    if (!object)
+    {
+        ERR("Memory allocation failed.\n");
+        return E_OUTOFMEMORY;
+    }
+
+    hr = vertexdeclaration_init(object, device, declaration, shader_handle);
+    if (FAILED(hr))
+    {
+        WARN("Failed to initialize vertex declaration, hr %#x.\n", hr);
+        HeapFree(GetProcessHeap(), 0, object);
+        return hr;
+    }
+
+    TRACE("Created vertex declaration %p.\n", object);
+    *decl_ptr = (IDirect3DVertexDeclaration8 *)object;
+
+    return D3D_OK;
+}
+
+HRESULT vertexshader_init(IDirect3DVertexShader8Impl *shader, IDirect3DDevice8Impl *device,
+        const DWORD *declaration, const DWORD *byte_code, DWORD shader_handle, DWORD usage)
+{
+    const DWORD *token = declaration;
+    HRESULT hr;
+
+    /* Test if the vertex declaration is valid. */
+    while (D3DVSD_END() != *token)
+    {
+        D3DVSD_TOKENTYPE token_type = ((*token & D3DVSD_TOKENTYPEMASK) >> D3DVSD_TOKENTYPESHIFT);
+
+        if (token_type == D3DVSD_TOKEN_STREAMDATA && !(token_type & 0x10000000))
+        {
+            DWORD type = ((*token & D3DVSD_DATATYPEMASK) >> D3DVSD_DATATYPESHIFT);
+            DWORD reg  = ((*token & D3DVSD_VERTEXREGMASK) >> D3DVSD_VERTEXREGSHIFT);
+
+            if (reg == D3DVSDE_NORMAL && type != D3DVSDT_FLOAT3 && !byte_code)
+            {
+                WARN("Attempt to use a non-FLOAT3 normal with the fixed function function\n");
+                return D3DERR_INVALIDCALL;
+            }
+        }
+        token += parse_token(token);
+    }
+
+    shader->ref = 1;
+    shader->lpVtbl = &d3d8_vertexshader_vtbl;
+
+    hr = d3d8_vertexshader_create_vertexdeclaration(device, declaration, shader_handle, &shader->vertex_declaration);
+    if (FAILED(hr))
+    {
+        WARN("Failed to create vertex declaration, hr %#x.\n", hr);
+        return hr;
+    }
+
+    if (byte_code)
+    {
+        if (usage) FIXME("Usage %#x not implemented.\n", usage);
+
+        wined3d_mutex_lock();
+        hr = IWineD3DDevice_CreateVertexShader(device->WineD3DDevice, byte_code, NULL /* output signature */,
+                shader, &d3d8_vertexshader_wined3d_parent_ops, &shader->wineD3DVertexShader);
+        wined3d_mutex_unlock();
+        if (FAILED(hr))
+        {
+            WARN("Failed to create wined3d vertex shader, hr %#x.\n", hr);
+            IDirect3DVertexDeclaration8_Release(shader->vertex_declaration);
+            return hr;
+        }
+
+        load_local_constants(declaration, shader->wineD3DVertexShader);
+    }
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d8_pixelshader_QueryInterface(IDirect3DPixelShader8 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    if (IsEqualGUID(riid, &IID_IDirect3DPixelShader8)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
+        IUnknown_AddRef(iface);
+        *object = iface;
+        return S_OK;
+    }
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI d3d8_pixelshader_AddRef(IDirect3DPixelShader8 *iface)
+{
+    IDirect3DPixelShader8Impl *shader = (IDirect3DPixelShader8Impl *)iface;
+    ULONG refcount = InterlockedIncrement(&shader->ref);
+
+    TRACE("%p increasing refcount to %u.\n", iface, refcount);
+
+    if (refcount == 1)
+    {
+        wined3d_mutex_lock();
+        IWineD3DPixelShader_AddRef(shader->wineD3DPixelShader);
+        wined3d_mutex_unlock();
+    }
+
+    return refcount;
+}
+
+static ULONG WINAPI d3d8_pixelshader_Release(IDirect3DPixelShader8 *iface)
+{
+    IDirect3DPixelShader8Impl *shader = (IDirect3DPixelShader8Impl *)iface;
+    ULONG refcount = InterlockedDecrement(&shader->ref);
+
+    TRACE("%p decreasing refcount to %u.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        wined3d_mutex_lock();
+        IWineD3DPixelShader_Release(shader->wineD3DPixelShader);
+        wined3d_mutex_unlock();
+    }
+
+    return refcount;
+}
+
+static const IDirect3DPixelShader8Vtbl d3d8_pixelshader_vtbl =
+{
+    /* IUnknown */
+    d3d8_pixelshader_QueryInterface,
+    d3d8_pixelshader_AddRef,
+    d3d8_pixelshader_Release,
+};
+
+static void STDMETHODCALLTYPE d3d8_pixelshader_wined3d_object_destroyed(void *parent)
+{
+    HeapFree(GetProcessHeap(), 0, parent);
+}
+
+static const struct wined3d_parent_ops d3d8_pixelshader_wined3d_parent_ops =
+{
+    d3d8_pixelshader_wined3d_object_destroyed,
+};
+
+HRESULT pixelshader_init(IDirect3DPixelShader8Impl *shader, IDirect3DDevice8Impl *device,
+        const DWORD *byte_code, DWORD shader_handle)
+{
+    HRESULT hr;
+
+    shader->ref = 1;
+    shader->lpVtbl = &d3d8_pixelshader_vtbl;
+    shader->handle = shader_handle;
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_CreatePixelShader(device->WineD3DDevice, byte_code, NULL, shader,
+            &d3d8_pixelshader_wined3d_parent_ops, &shader->wineD3DPixelShader);
+    wined3d_mutex_unlock();
+    if (FAILED(hr))
+    {
+        WARN("Failed to create wined3d pixel shader, hr %#x.\n", hr);
+        return hr;
+    }
+
+    return D3D_OK;
+}
index cf72e3e..6e59bd6 100644 (file)
@@ -190,27 +190,23 @@ static HRESULT WINAPI IDirect3DSurface8Impl_GetContainer(LPDIRECT3DSURFACE8 ifac
 static HRESULT WINAPI IDirect3DSurface8Impl_GetDesc(LPDIRECT3DSURFACE8 iface, D3DSURFACE_DESC *pDesc) {
     IDirect3DSurface8Impl *This = (IDirect3DSurface8Impl *)iface;
     WINED3DSURFACE_DESC    wined3ddesc;
-    HRESULT hr;
 
     TRACE("iface %p, desc %p.\n", iface, pDesc);
 
     wined3d_mutex_lock();
-    hr = IWineD3DSurface_GetDesc(This->wineD3DSurface, &wined3ddesc);
+    IWineD3DSurface_GetDesc(This->wineD3DSurface, &wined3ddesc);
     wined3d_mutex_unlock();
 
-    if (SUCCEEDED(hr))
-    {
-        pDesc->Format = d3dformat_from_wined3dformat(wined3ddesc.format);
-        pDesc->Type = wined3ddesc.resource_type;
-        pDesc->Usage = wined3ddesc.usage;
-        pDesc->Pool = wined3ddesc.pool;
-        pDesc->Size = wined3ddesc.size;
-        pDesc->MultiSampleType = wined3ddesc.multisample_type;
-        pDesc->Width = wined3ddesc.width;
-        pDesc->Height = wined3ddesc.height;
-    }
+    pDesc->Format = d3dformat_from_wined3dformat(wined3ddesc.format);
+    pDesc->Type = wined3ddesc.resource_type;
+    pDesc->Usage = wined3ddesc.usage;
+    pDesc->Pool = wined3ddesc.pool;
+    pDesc->Size = wined3ddesc.size;
+    pDesc->MultiSampleType = wined3ddesc.multisample_type;
+    pDesc->Width = wined3ddesc.width;
+    pDesc->Height = wined3ddesc.height;
 
-    return hr;
+    return D3D_OK;
 }
 
 static HRESULT WINAPI IDirect3DSurface8Impl_LockRect(LPDIRECT3DSURFACE8 iface, D3DLOCKED_RECT *pLockedRect, CONST RECT *pRect, DWORD Flags) {
@@ -306,9 +302,8 @@ HRESULT surface_init(IDirect3DSurface8Impl *surface, IDirect3DDevice8Impl *devic
 
     wined3d_mutex_lock();
     hr = IWineD3DDevice_CreateSurface(device->WineD3DDevice, width, height, wined3dformat_from_d3dformat(format),
-            lockable, discard, level, &surface->wineD3DSurface, usage & WINED3DUSAGE_MASK, (WINED3DPOOL)pool,
-            multisample_type, multisample_quality, SURFACE_OPENGL, (IUnknown *)surface,
-            &d3d8_surface_wined3d_parent_ops);
+            lockable, discard, level, usage & WINED3DUSAGE_MASK, (WINED3DPOOL)pool, multisample_type,
+            multisample_quality, SURFACE_OPENGL, surface, &d3d8_surface_wined3d_parent_ops, &surface->wineD3DSurface);
     wined3d_mutex_unlock();
     if (FAILED(hr))
     {
index 1b807fb..1c2a535 100644 (file)
@@ -83,23 +83,28 @@ static HRESULT WINAPI IDirect3DSwapChain8Impl_Present(LPDIRECT3DSWAPCHAIN8 iface
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DSwapChain8Impl_GetBackBuffer(LPDIRECT3DSWAPCHAIN8 iface, UINT iBackBuffer, D3DBACKBUFFER_TYPE Type, IDirect3DSurface8** ppBackBuffer) {
+static HRESULT WINAPI IDirect3DSwapChain8Impl_GetBackBuffer(IDirect3DSwapChain8 *iface,
+        UINT iBackBuffer, D3DBACKBUFFER_TYPE Type, IDirect3DSurface8 **ppBackBuffer)
+{
     IDirect3DSwapChain8Impl *This = (IDirect3DSwapChain8Impl *)iface;
-    HRESULT hrc = D3D_OK;
     IWineD3DSurface *mySurface = NULL;
+    HRESULT hr;
 
     TRACE("iface %p, backbuffer_idx %u, backbuffer_type %#x, backbuffer %p.\n",
             iface, iBackBuffer, Type, ppBackBuffer);
 
     wined3d_mutex_lock();
-    hrc = IWineD3DSwapChain_GetBackBuffer(This->wineD3DSwapChain, iBackBuffer, (WINED3DBACKBUFFER_TYPE )Type, &mySurface);
-    if (hrc == D3D_OK && NULL != mySurface) {
-       IWineD3DSurface_GetParent(mySurface, (IUnknown **)ppBackBuffer);
-       IWineD3DSurface_Release(mySurface);
+    hr = IWineD3DSwapChain_GetBackBuffer(This->wineD3DSwapChain, iBackBuffer,
+            (WINED3DBACKBUFFER_TYPE)Type, &mySurface);
+    if (SUCCEEDED(hr) && mySurface)
+    {
+        *ppBackBuffer = IWineD3DSurface_GetParent(mySurface);
+        IDirect3DSurface8_AddRef(*ppBackBuffer);
+        IWineD3DSurface_Release(mySurface);
     }
     wined3d_mutex_unlock();
 
-    return hrc;
+    return hr;
 }
 
 static const IDirect3DSwapChain8Vtbl Direct3DSwapChain8_Vtbl =
@@ -138,7 +143,7 @@ HRESULT swapchain_init(IDirect3DSwapChain8Impl *swapchain, IDirect3DDevice8Impl
 
     wined3d_mutex_lock();
     hr = IWineD3DDevice_CreateSwapChain(device->WineD3DDevice, &wined3d_parameters,
-            &swapchain->wineD3DSwapChain, (IUnknown *)swapchain, SURFACE_OPENGL);
+            SURFACE_OPENGL, swapchain, &swapchain->wineD3DSwapChain);
     wined3d_mutex_unlock();
 
     present_parameters->BackBufferWidth = wined3d_parameters.BackBufferWidth;
index 67a60b4..a842160 100644 (file)
@@ -251,22 +251,26 @@ static HRESULT WINAPI IDirect3DTexture8Impl_GetLevelDesc(LPDIRECT3DTEXTURE8 ifac
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DTexture8Impl_GetSurfaceLevel(LPDIRECT3DTEXTURE8 iface, UINT Level, IDirect3DSurface8 **ppSurfaceLevel) {
+static HRESULT WINAPI IDirect3DTexture8Impl_GetSurfaceLevel(IDirect3DTexture8 *iface,
+        UINT Level, IDirect3DSurface8 **ppSurfaceLevel)
+{
     IDirect3DTexture8Impl *This = (IDirect3DTexture8Impl *)iface;
-    HRESULT hrc = D3D_OK;
     IWineD3DSurface *mySurface = NULL;
+    HRESULT hr;
 
     TRACE("iface %p, level %u, surface %p.\n", iface, Level, ppSurfaceLevel);
 
     wined3d_mutex_lock();
-    hrc = IWineD3DTexture_GetSurfaceLevel(This->wineD3DTexture, Level, &mySurface);
-    if (hrc == D3D_OK && NULL != ppSurfaceLevel) {
-       IWineD3DSurface_GetParent(mySurface, (IUnknown **)ppSurfaceLevel);
+    hr = IWineD3DTexture_GetSurfaceLevel(This->wineD3DTexture, Level, &mySurface);
+    if (SUCCEEDED(hr) && ppSurfaceLevel)
+    {
+       *ppSurfaceLevel = IWineD3DSurface_GetParent(mySurface);
+       IDirect3DSurface8_AddRef(*ppSurfaceLevel);
        IWineD3DSurface_Release(mySurface);
     }
     wined3d_mutex_unlock();
 
-    return hrc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DTexture8Impl_LockRect(LPDIRECT3DTEXTURE8 iface, UINT Level, D3DLOCKED_RECT *pLockedRect, CONST RECT *pRect, DWORD Flags) {
@@ -357,7 +361,7 @@ HRESULT texture_init(IDirect3DTexture8Impl *texture, IDirect3DDevice8Impl *devic
     wined3d_mutex_lock();
     hr = IWineD3DDevice_CreateTexture(device->WineD3DDevice, width, height, levels,
             usage & WINED3DUSAGE_MASK, wined3dformat_from_d3dformat(format), pool,
-            &texture->wineD3DTexture, (IUnknown *)texture, &d3d8_texture_wined3d_parent_ops);
+            texture, &d3d8_texture_wined3d_parent_ops, &texture->wineD3DTexture);
     wined3d_mutex_unlock();
     if (FAILED(hr))
     {
diff --git a/reactos/dll/directx/wine/d3d8/vertexbuffer.c b/reactos/dll/directx/wine/d3d8/vertexbuffer.c
deleted file mode 100644 (file)
index 476fcc4..0000000
+++ /dev/null
@@ -1,288 +0,0 @@
-/*
- * IDirect3DVertexBuffer8 implementation
- *
- * Copyright 2005 Oliver Stieber
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "d3d8_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d8);
-
-/* IDirect3DVertexBuffer8 IUnknown parts follow: */
-static HRESULT WINAPI IDirect3DVertexBuffer8Impl_QueryInterface(LPDIRECT3DVERTEXBUFFER8 iface, REFIID riid, LPVOID *ppobj) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-
-    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppobj);
-
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IDirect3DResource8)
-        || IsEqualGUID(riid, &IID_IDirect3DVertexBuffer8)) {
-        IUnknown_AddRef(iface);
-        *ppobj = This;
-        return S_OK;
-    }
-
-    WARN("(%p)->(%s,%p),not found\n", This, debugstr_guid(riid), ppobj);
-
-    *ppobj = NULL;
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI IDirect3DVertexBuffer8Impl_AddRef(LPDIRECT3DVERTEXBUFFER8 iface) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    ULONG ref = InterlockedIncrement(&This->ref);
-
-    TRACE("%p increasing refcount to %u.\n", iface, ref);
-
-    if (ref == 1)
-    {
-        IDirect3DDevice8_AddRef(This->parentDevice);
-        wined3d_mutex_lock();
-        IWineD3DBuffer_AddRef(This->wineD3DVertexBuffer);
-        wined3d_mutex_unlock();
-    }
-
-    return ref;
-}
-
-static ULONG WINAPI IDirect3DVertexBuffer8Impl_Release(LPDIRECT3DVERTEXBUFFER8 iface) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    ULONG ref = InterlockedDecrement(&This->ref);
-
-    TRACE("%p decreasing refcount to %u.\n", iface, ref);
-
-    if (ref == 0) {
-        IDirect3DDevice8 *parentDevice = This->parentDevice;
-
-        wined3d_mutex_lock();
-        IWineD3DBuffer_Release(This->wineD3DVertexBuffer);
-        wined3d_mutex_unlock();
-
-        /* Release the device last, as it may cause the device to be destroyed. */
-        IDirect3DDevice8_Release(parentDevice);
-    }
-
-    return ref;
-}
-
-/* IDirect3DVertexBuffer8 IDirect3DResource8 Interface follow: */
-static HRESULT WINAPI IDirect3DVertexBuffer8Impl_GetDevice(IDirect3DVertexBuffer8 *iface, IDirect3DDevice8 **device)
-{
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-
-    TRACE("iface %p, device %p.\n", iface, device);
-
-    *device = (IDirect3DDevice8 *)This->parentDevice;
-    IDirect3DDevice8_AddRef(*device);
-
-    TRACE("Returning device %p.\n", *device);
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer8Impl_SetPrivateData(LPDIRECT3DVERTEXBUFFER8 iface, REFGUID refguid, CONST void *pData, DWORD SizeOfData, DWORD Flags) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s, data %p, data_size %u, flags %#x.\n",
-            iface, debugstr_guid(refguid), pData, SizeOfData, Flags);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_SetPrivateData(This->wineD3DVertexBuffer, refguid, pData, SizeOfData, Flags);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer8Impl_GetPrivateData(LPDIRECT3DVERTEXBUFFER8 iface, REFGUID refguid, void *pData, DWORD *pSizeOfData) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s, data %p, data_size %p.\n",
-            iface, debugstr_guid(refguid), pData, pSizeOfData);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_GetPrivateData(This->wineD3DVertexBuffer, refguid, pData, pSizeOfData);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer8Impl_FreePrivateData(LPDIRECT3DVERTEXBUFFER8 iface, REFGUID refguid) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(refguid));
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_FreePrivateData(This->wineD3DVertexBuffer, refguid);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static DWORD WINAPI IDirect3DVertexBuffer8Impl_SetPriority(LPDIRECT3DVERTEXBUFFER8 iface, DWORD PriorityNew) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    DWORD ret;
-
-    TRACE("iface %p, priority %u.\n", iface, PriorityNew);
-
-    wined3d_mutex_lock();
-    ret = IWineD3DBuffer_SetPriority(This->wineD3DVertexBuffer, PriorityNew);
-    wined3d_mutex_unlock();
-
-    return ret;
-}
-
-static DWORD WINAPI IDirect3DVertexBuffer8Impl_GetPriority(LPDIRECT3DVERTEXBUFFER8 iface) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    DWORD ret;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    ret = IWineD3DBuffer_GetPriority(This->wineD3DVertexBuffer);
-    wined3d_mutex_unlock();
-
-    return ret;
-}
-
-static void WINAPI IDirect3DVertexBuffer8Impl_PreLoad(LPDIRECT3DVERTEXBUFFER8 iface) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    IWineD3DBuffer_PreLoad(This->wineD3DVertexBuffer);
-    wined3d_mutex_unlock();
-}
-
-static D3DRESOURCETYPE WINAPI IDirect3DVertexBuffer8Impl_GetType(IDirect3DVertexBuffer8 *iface)
-{
-    TRACE("iface %p.\n", iface);
-
-    return D3DRTYPE_VERTEXBUFFER;
-}
-
-/* IDirect3DVertexBuffer8 Interface follow: */
-static HRESULT WINAPI IDirect3DVertexBuffer8Impl_Lock(LPDIRECT3DVERTEXBUFFER8 iface, UINT OffsetToLock, UINT SizeToLock, BYTE **ppbData, DWORD Flags) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, offset %u, size %u, data %p, flags %#x.\n",
-            iface, OffsetToLock, SizeToLock, ppbData, Flags);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_Map(This->wineD3DVertexBuffer, OffsetToLock, SizeToLock, ppbData, Flags);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer8Impl_Unlock(LPDIRECT3DVERTEXBUFFER8 iface) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_Unmap(This->wineD3DVertexBuffer);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer8Impl_GetDesc(LPDIRECT3DVERTEXBUFFER8 iface, D3DVERTEXBUFFER_DESC *pDesc) {
-    IDirect3DVertexBuffer8Impl *This = (IDirect3DVertexBuffer8Impl *)iface;
-    HRESULT hr;
-    WINED3DBUFFER_DESC desc;
-
-    TRACE("iface %p, desc %p.\n", iface, pDesc);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_GetDesc(This->wineD3DVertexBuffer, &desc);
-    wined3d_mutex_unlock();
-
-    if (SUCCEEDED(hr)) {
-        pDesc->Type = D3DRTYPE_VERTEXBUFFER;
-        pDesc->Usage = desc.Usage;
-        pDesc->Pool = desc.Pool;
-        pDesc->Size = desc.Size;
-        pDesc->FVF = This->fvf;
-        pDesc->Format = D3DFMT_VERTEXDATA;
-    }
-
-    return hr;
-}
-
-static const IDirect3DVertexBuffer8Vtbl Direct3DVertexBuffer8_Vtbl =
-{
-    /* IUnknown */
-    IDirect3DVertexBuffer8Impl_QueryInterface,
-    IDirect3DVertexBuffer8Impl_AddRef,
-    IDirect3DVertexBuffer8Impl_Release,
-    /* IDirect3DResource8 */
-    IDirect3DVertexBuffer8Impl_GetDevice,
-    IDirect3DVertexBuffer8Impl_SetPrivateData,
-    IDirect3DVertexBuffer8Impl_GetPrivateData,
-    IDirect3DVertexBuffer8Impl_FreePrivateData,
-    IDirect3DVertexBuffer8Impl_SetPriority,
-    IDirect3DVertexBuffer8Impl_GetPriority,
-    IDirect3DVertexBuffer8Impl_PreLoad,
-    IDirect3DVertexBuffer8Impl_GetType,
-    /* IDirect3DVertexBuffer8 */
-    IDirect3DVertexBuffer8Impl_Lock,
-    IDirect3DVertexBuffer8Impl_Unlock,
-    IDirect3DVertexBuffer8Impl_GetDesc
-};
-
-static void STDMETHODCALLTYPE d3d8_vertexbuffer_wined3d_object_destroyed(void *parent)
-{
-    HeapFree(GetProcessHeap(), 0, parent);
-}
-
-static const struct wined3d_parent_ops d3d8_vertexbuffer_wined3d_parent_ops =
-{
-    d3d8_vertexbuffer_wined3d_object_destroyed,
-};
-
-HRESULT vertexbuffer_init(IDirect3DVertexBuffer8Impl *buffer, IDirect3DDevice8Impl *device,
-        UINT size, DWORD usage, DWORD fvf, D3DPOOL pool)
-{
-    HRESULT hr;
-
-    buffer->lpVtbl = &Direct3DVertexBuffer8_Vtbl;
-    buffer->ref = 1;
-    buffer->fvf = fvf;
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateVertexBuffer(device->WineD3DDevice, size,
-            usage & WINED3DUSAGE_MASK, (WINED3DPOOL)pool, &buffer->wineD3DVertexBuffer,
-            (IUnknown *)buffer, &d3d8_vertexbuffer_wined3d_parent_ops);
-    wined3d_mutex_unlock();
-    if (FAILED(hr))
-    {
-        WARN("Failed to create wined3d buffer, hr %#x.\n", hr);
-        return hr;
-    }
-
-    buffer->parentDevice = (IDirect3DDevice8 *)device;
-    IUnknown_AddRef(buffer->parentDevice);
-
-    return D3D_OK;
-}
index b876b66..58573a5 100644 (file)
@@ -254,7 +254,7 @@ static const size_t wined3d_type_sizes[] =
     /*WINED3DDECLTYPE_FLOAT16_4*/ 4 * sizeof(short int)
 };
 
-static const WINED3DFORMAT wined3d_format_lookup[] =
+static const enum wined3d_format_id wined3d_format_lookup[] =
 {
     /*WINED3DDECLTYPE_FLOAT1*/    WINED3DFMT_R32_FLOAT,
     /*WINED3DDECLTYPE_FLOAT2*/    WINED3DFMT_R32G32_FLOAT,
@@ -399,9 +399,8 @@ HRESULT vertexdeclaration_init(IDirect3DVertexDeclaration8Impl *declaration,
     memcpy(declaration->elements, elements, declaration->elements_size);
 
     wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateVertexDeclaration(device->WineD3DDevice, &declaration->wined3d_vertex_declaration,
-            (IUnknown *)declaration, &d3d8_vertexdeclaration_wined3d_parent_ops,
-            wined3d_elements, wined3d_element_count);
+    hr = IWineD3DDevice_CreateVertexDeclaration(device->WineD3DDevice, wined3d_elements, wined3d_element_count,
+            declaration, &d3d8_vertexdeclaration_wined3d_parent_ops, &declaration->wined3d_vertex_declaration);
     wined3d_mutex_unlock();
     HeapFree(GetProcessHeap(), 0, wined3d_elements);
     if (FAILED(hr))
@@ -425,9 +424,8 @@ HRESULT vertexdeclaration_init_fvf(IDirect3DVertexDeclaration8Impl *declaration,
     declaration->elements_size = 0;
     declaration->shader_handle = fvf;
 
-    hr = IWineD3DDevice_CreateVertexDeclarationFromFVF(device->WineD3DDevice,
-            &declaration->wined3d_vertex_declaration, (IUnknown *)declaration,
-            &d3d8_vertexdeclaration_wined3d_parent_ops, fvf);
+    hr = IWineD3DDevice_CreateVertexDeclarationFromFVF(device->WineD3DDevice, fvf, declaration,
+            &d3d8_vertexdeclaration_wined3d_parent_ops, &declaration->wined3d_vertex_declaration);
     if (FAILED(hr))
     {
         WARN("Failed to create wined3d vertex declaration, hr %#x.\n", hr);
diff --git a/reactos/dll/directx/wine/d3d8/vertexshader.c b/reactos/dll/directx/wine/d3d8/vertexshader.c
deleted file mode 100644 (file)
index 1f00aa0..0000000
+++ /dev/null
@@ -1,187 +0,0 @@
-/*
- * IDirect3DVertexShader8 implementation
- *
- * Copyright 2002-2003 Jason Edmeades
- *                     Raphael Junqueira
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "d3d8_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d8);
-
-/* IDirect3DVertexShader8 IUnknown parts follow: */
-static HRESULT WINAPI IDirect3DVertexShader8Impl_QueryInterface(IDirect3DVertexShader8 *iface, REFIID riid, LPVOID* ppobj) {
-    IDirect3DVertexShader8Impl *This = (IDirect3DVertexShader8Impl *)iface;
-
-    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppobj);
-
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IDirect3DVertexShader8)) {
-        IUnknown_AddRef(iface);
-        *ppobj = This;
-        return S_OK;
-    }
-
-    WARN("(%p)->(%s,%p),not found\n", This, debugstr_guid(riid), ppobj);
-    *ppobj = NULL;
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI IDirect3DVertexShader8Impl_AddRef(IDirect3DVertexShader8 *iface) {
-    IDirect3DVertexShader8Impl *This = (IDirect3DVertexShader8Impl *)iface;
-    ULONG ref = InterlockedIncrement(&This->ref);
-
-    TRACE("%p increasing refcount to %u.\n", iface, ref);
-
-    if (ref == 1 && This->wineD3DVertexShader)
-    {
-        wined3d_mutex_lock();
-        IWineD3DVertexShader_AddRef(This->wineD3DVertexShader);
-        wined3d_mutex_unlock();
-    }
-
-    return ref;
-}
-
-static void STDMETHODCALLTYPE d3d8_vertexshader_wined3d_object_destroyed(void *parent)
-{
-    IDirect3DVertexShader8Impl *shader = parent;
-    IDirect3DVertexDeclaration8_Release(shader->vertex_declaration);
-    HeapFree(GetProcessHeap(), 0, shader);
-}
-
-static ULONG WINAPI IDirect3DVertexShader8Impl_Release(IDirect3DVertexShader8 *iface) {
-    IDirect3DVertexShader8Impl *This = (IDirect3DVertexShader8Impl *)iface;
-    ULONG ref = InterlockedDecrement(&This->ref);
-
-    TRACE("%p decreasing refcount to %u.\n", iface, ref);
-
-    if (ref == 0) {
-        if (This->wineD3DVertexShader)
-        {
-            wined3d_mutex_lock();
-            IWineD3DVertexShader_Release(This->wineD3DVertexShader);
-            wined3d_mutex_unlock();
-        }
-        else
-        {
-            d3d8_vertexshader_wined3d_object_destroyed(This);
-        }
-    }
-    return ref;
-}
-
-static const IDirect3DVertexShader8Vtbl Direct3DVertexShader8_Vtbl =
-{
-    /* IUnknown */
-    IDirect3DVertexShader8Impl_QueryInterface,
-    IDirect3DVertexShader8Impl_AddRef,
-    IDirect3DVertexShader8Impl_Release,
-};
-
-static const struct wined3d_parent_ops d3d8_vertexshader_wined3d_parent_ops =
-{
-    d3d8_vertexshader_wined3d_object_destroyed,
-};
-
-static HRESULT vertexshader_create_vertexdeclaration(IDirect3DDevice8Impl *device,
-        const DWORD *declaration, DWORD shader_handle, IDirect3DVertexDeclaration8 **decl_ptr)
-{
-    IDirect3DVertexDeclaration8Impl *object;
-    HRESULT hr;
-
-    TRACE("device %p, declaration %p, shader_handle %#x, decl_ptr %p.\n",
-            device, declaration, shader_handle, decl_ptr);
-
-    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
-    if (!object) {
-        ERR("Memory allocation failed\n");
-        *decl_ptr = NULL;
-        return D3DERR_OUTOFVIDEOMEMORY;
-    }
-
-    hr = vertexdeclaration_init(object, device, declaration, shader_handle);
-    if (FAILED(hr))
-    {
-        WARN("Failed to initialize vertex declaration, hr %#x.\n", hr);
-        HeapFree(GetProcessHeap(), 0, object);
-        return hr;
-    }
-
-    TRACE("Created vertex declaration %p.\n", object);
-    *decl_ptr = (IDirect3DVertexDeclaration8 *)object;
-
-    return D3D_OK;
-}
-
-HRESULT vertexshader_init(IDirect3DVertexShader8Impl *shader, IDirect3DDevice8Impl *device,
-        const DWORD *declaration, const DWORD *byte_code, DWORD shader_handle, DWORD usage)
-{
-    const DWORD *token = declaration;
-    HRESULT hr;
-
-    /* Test if the vertex declaration is valid */
-    while (D3DVSD_END() != *token)
-    {
-        D3DVSD_TOKENTYPE token_type = ((*token & D3DVSD_TOKENTYPEMASK) >> D3DVSD_TOKENTYPESHIFT);
-
-        if (token_type == D3DVSD_TOKEN_STREAMDATA && !(token_type & 0x10000000))
-        {
-            DWORD type = ((*token & D3DVSD_DATATYPEMASK) >> D3DVSD_DATATYPESHIFT);
-            DWORD reg  = ((*token & D3DVSD_VERTEXREGMASK) >> D3DVSD_VERTEXREGSHIFT);
-
-            if (reg == D3DVSDE_NORMAL && type != D3DVSDT_FLOAT3 && !byte_code)
-            {
-                WARN("Attempt to use a non-FLOAT3 normal with the fixed function function\n");
-                return D3DERR_INVALIDCALL;
-            }
-        }
-        token += parse_token(token);
-    }
-
-    shader->ref = 1;
-    shader->lpVtbl = &Direct3DVertexShader8_Vtbl;
-
-    hr = vertexshader_create_vertexdeclaration(device, declaration, shader_handle, &shader->vertex_declaration);
-    if (FAILED(hr))
-    {
-        WARN("Failed to create vertex declaration, hr %#x.\n", hr);
-        return hr;
-    }
-
-    if (byte_code)
-    {
-        if (usage) FIXME("Usage %#x not implemented.\n", usage);
-
-        wined3d_mutex_lock();
-        hr = IWineD3DDevice_CreateVertexShader(device->WineD3DDevice, byte_code,
-                NULL /* output signature */, &shader->wineD3DVertexShader,
-                (IUnknown *)shader, &d3d8_vertexshader_wined3d_parent_ops);
-        wined3d_mutex_unlock();
-        if (FAILED(hr))
-        {
-            WARN("Failed to create wined3d vertex shader, hr %#x.\n", hr);
-            IDirect3DVertexDeclaration8_Release(shader->vertex_declaration);
-            return hr;
-        }
-
-        load_local_constants(declaration, shader->wineD3DVertexShader);
-    }
-
-    return D3D_OK;
-}
index 8e8dc60..1705822 100644 (file)
@@ -177,28 +177,24 @@ static HRESULT WINAPI IDirect3DVolume8Impl_GetContainer(LPDIRECT3DVOLUME8 iface,
 
 static HRESULT WINAPI IDirect3DVolume8Impl_GetDesc(LPDIRECT3DVOLUME8 iface, D3DVOLUME_DESC *pDesc) {
     IDirect3DVolume8Impl *This = (IDirect3DVolume8Impl *)iface;
-    HRESULT hr;
-    WINED3DVOLUME_DESC     wined3ddesc;
+    WINED3DVOLUME_DESC wined3ddesc;
 
     TRACE("iface %p, desc %p.\n", iface, pDesc);
 
     wined3d_mutex_lock();
-    hr = IWineD3DVolume_GetDesc(This->wineD3DVolume, &wined3ddesc);
+    IWineD3DVolume_GetDesc(This->wineD3DVolume, &wined3ddesc);
     wined3d_mutex_unlock();
 
-    if (SUCCEEDED(hr))
-    {
-        pDesc->Format = d3dformat_from_wined3dformat(wined3ddesc.Format);
-        pDesc->Type = wined3ddesc.Type;
-        pDesc->Usage = wined3ddesc.Usage;
-        pDesc->Pool = wined3ddesc.Pool;
-        pDesc->Size = wined3ddesc.Size;
-        pDesc->Width = wined3ddesc.Width;
-        pDesc->Height = wined3ddesc.Height;
-        pDesc->Depth = wined3ddesc.Depth;
-    }
+    pDesc->Format = d3dformat_from_wined3dformat(wined3ddesc.Format);
+    pDesc->Type = wined3ddesc.Type;
+    pDesc->Usage = wined3ddesc.Usage;
+    pDesc->Pool = wined3ddesc.Pool;
+    pDesc->Size = wined3ddesc.Size;
+    pDesc->Width = wined3ddesc.Width;
+    pDesc->Height = wined3ddesc.Height;
+    pDesc->Depth = wined3ddesc.Depth;
 
-    return hr;
+    return D3D_OK;
 }
 
 static HRESULT WINAPI IDirect3DVolume8Impl_LockBox(LPDIRECT3DVOLUME8 iface, D3DLOCKED_BOX *pLockedVolume, CONST D3DBOX *pBox, DWORD Flags) {
@@ -256,7 +252,7 @@ static const struct wined3d_parent_ops d3d8_volume_wined3d_parent_ops =
 };
 
 HRESULT volume_init(IDirect3DVolume8Impl *volume, IDirect3DDevice8Impl *device, UINT width, UINT height,
-        UINT depth, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool)
+        UINT depth, DWORD usage, enum wined3d_format_id format, WINED3DPOOL pool)
 {
     HRESULT hr;
 
@@ -264,7 +260,7 @@ HRESULT volume_init(IDirect3DVolume8Impl *volume, IDirect3DDevice8Impl *device,
     volume->ref = 1;
 
     hr = IWineD3DDevice_CreateVolume(device->WineD3DDevice, width, height, depth, usage,
-            format, pool, &volume->wineD3DVolume, (IUnknown *)volume, &d3d8_volume_wined3d_parent_ops);
+            format, pool, volume, &d3d8_volume_wined3d_parent_ops, &volume->wineD3DVolume);
     if (FAILED(hr))
     {
         WARN("Failed to create wined3d volume, hr %#x.\n", hr);
index bc5c5b8..bd72d68 100644 (file)
@@ -251,22 +251,26 @@ static HRESULT WINAPI IDirect3DVolumeTexture8Impl_GetLevelDesc(LPDIRECT3DVOLUMET
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DVolumeTexture8Impl_GetVolumeLevel(LPDIRECT3DVOLUMETEXTURE8 iface, UINT Level, IDirect3DVolume8 **ppVolumeLevel) {
+static HRESULT WINAPI IDirect3DVolumeTexture8Impl_GetVolumeLevel(IDirect3DVolumeTexture8 *iface,
+        UINT Level, IDirect3DVolume8 **ppVolumeLevel)
+{
     IDirect3DVolumeTexture8Impl *This = (IDirect3DVolumeTexture8Impl *)iface;
-    HRESULT hrc = D3D_OK;
     IWineD3DVolume *myVolume = NULL;
+    HRESULT hr;
 
     TRACE("iface %p, level %u, volume %p.\n", iface, Level, ppVolumeLevel);
 
     wined3d_mutex_lock();
-    hrc = IWineD3DVolumeTexture_GetVolumeLevel(This->wineD3DVolumeTexture, Level, &myVolume);
-    if (hrc == D3D_OK && NULL != ppVolumeLevel) {
-       IWineD3DVolumeTexture_GetParent(myVolume, (IUnknown **)ppVolumeLevel);
-       IWineD3DVolumeTexture_Release(myVolume);
+    hr = IWineD3DVolumeTexture_GetVolumeLevel(This->wineD3DVolumeTexture, Level, &myVolume);
+    if (SUCCEEDED(hr) && ppVolumeLevel)
+    {
+        *ppVolumeLevel = IWineD3DVolumeTexture_GetParent(myVolume);
+        IDirect3DVolume8_AddRef(*ppVolumeLevel);
+        IWineD3DVolumeTexture_Release(myVolume);
     }
     wined3d_mutex_unlock();
 
-    return hrc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DVolumeTexture8Impl_LockBox(LPDIRECT3DVOLUMETEXTURE8 iface, UINT Level, D3DLOCKED_BOX *pLockedVolume, CONST D3DBOX *pBox, DWORD Flags) {
@@ -356,8 +360,8 @@ HRESULT volumetexture_init(IDirect3DVolumeTexture8Impl *texture, IDirect3DDevice
 
     wined3d_mutex_lock();
     hr = IWineD3DDevice_CreateVolumeTexture(device->WineD3DDevice, width, height, depth, levels,
-            usage & WINED3DUSAGE_MASK, wined3dformat_from_d3dformat(format), pool,
-            &texture->wineD3DVolumeTexture, (IUnknown *)texture, &d3d8_volumetexture_wined3d_parent_ops);
+            usage & WINED3DUSAGE_MASK, wined3dformat_from_d3dformat(format), pool, texture,
+            &d3d8_volumetexture_wined3d_parent_ops, &texture->wineD3DVolumeTexture);
     wined3d_mutex_unlock();
     if (FAILED(hr))
     {
diff --git a/reactos/dll/directx/wine/d3d9/buffer.c b/reactos/dll/directx/wine/d3d9/buffer.c
new file mode 100644 (file)
index 0000000..ac8c244
--- /dev/null
@@ -0,0 +1,551 @@
+/*
+ * Copyright 2002-2004 Jason Edmeades
+ * Copyright 2002-2004 Raphael Junqueira
+ * Copyright 2005 Oliver Stieber
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
+ */
+
+#include "config.h"
+#include "d3d9_private.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(d3d9);
+
+static HRESULT WINAPI d3d9_vertexbuffer_QueryInterface(IDirect3DVertexBuffer9 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    if (IsEqualGUID(riid, &IID_IDirect3DVertexBuffer9)
+            || IsEqualGUID(riid, &IID_IDirect3DResource9)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
+        IDirect3DVertexBuffer9_AddRef(iface);
+        *object = iface;
+        return S_OK;
+    }
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI d3d9_vertexbuffer_AddRef(IDirect3DVertexBuffer9 *iface)
+{
+    IDirect3DVertexBuffer9Impl *buffer = (IDirect3DVertexBuffer9Impl *)iface;
+    ULONG refcount = InterlockedIncrement(&buffer->ref);
+
+    TRACE("%p increasing refcount to %u.\n", iface, refcount);
+
+    if (refcount == 1)
+    {
+        IDirect3DDevice9Ex_AddRef(buffer->parentDevice);
+        wined3d_mutex_lock();
+        IWineD3DBuffer_AddRef(buffer->wineD3DVertexBuffer);
+        wined3d_mutex_unlock();
+    }
+
+    return refcount;
+}
+
+static ULONG WINAPI d3d9_vertexbuffer_Release(IDirect3DVertexBuffer9 *iface)
+{
+    IDirect3DVertexBuffer9Impl *buffer = (IDirect3DVertexBuffer9Impl *)iface;
+    ULONG refcount = InterlockedDecrement(&buffer->ref);
+
+    TRACE("%p decreasing refcount to %u.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        IDirect3DDevice9Ex *device = buffer->parentDevice;
+
+        wined3d_mutex_lock();
+        IWineD3DBuffer_Release(buffer->wineD3DVertexBuffer);
+        wined3d_mutex_unlock();
+
+        /* Release the device last, as it may cause the device to be destroyed. */
+        IDirect3DDevice9Ex_Release(device);
+    }
+
+    return refcount;
+}
+
+static HRESULT WINAPI d3d9_vertexbuffer_GetDevice(IDirect3DVertexBuffer9 *iface, IDirect3DDevice9 **device)
+{
+    TRACE("iface %p, device %p.\n", iface, device);
+
+    *device = (IDirect3DDevice9 *)((IDirect3DVertexBuffer9Impl *)iface)->parentDevice;
+    IDirect3DDevice9_AddRef(*device);
+
+    TRACE("Returning device %p.\n", *device);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d9_vertexbuffer_SetPrivateData(IDirect3DVertexBuffer9 *iface,
+        REFGUID guid, const void *data, DWORD data_size, DWORD flags)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s, data %p, data_size %u, flags %#x.\n",
+            iface, debugstr_guid(guid), data, data_size, flags);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_SetPrivateData(((IDirect3DVertexBuffer9Impl *)iface)->wineD3DVertexBuffer,
+            guid, data, data_size, flags);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d9_vertexbuffer_GetPrivateData(IDirect3DVertexBuffer9 *iface,
+        REFGUID guid, void *data, DWORD *data_size)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s, data %p, data_size %p.\n",
+            iface, debugstr_guid(guid), data, data_size);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_GetPrivateData(((IDirect3DVertexBuffer9Impl *)iface)->wineD3DVertexBuffer,
+            guid, data, data_size);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d9_vertexbuffer_FreePrivateData(IDirect3DVertexBuffer9 *iface, REFGUID guid)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(guid));
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_FreePrivateData(((IDirect3DVertexBuffer9Impl *)iface)->wineD3DVertexBuffer, guid);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static DWORD WINAPI d3d9_vertexbuffer_SetPriority(IDirect3DVertexBuffer9 *iface, DWORD priority)
+{
+    DWORD previous;
+
+    TRACE("iface %p, priority %u.\n", iface, priority);
+
+    wined3d_mutex_lock();
+    previous = IWineD3DBuffer_SetPriority(((IDirect3DVertexBuffer9Impl *)iface)->wineD3DVertexBuffer, priority);
+    wined3d_mutex_unlock();
+
+    return previous;
+}
+
+static DWORD WINAPI d3d9_vertexbuffer_GetPriority(IDirect3DVertexBuffer9 *iface)
+{
+    DWORD priority;
+
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    priority = IWineD3DBuffer_GetPriority(((IDirect3DVertexBuffer9Impl *)iface)->wineD3DVertexBuffer);
+    wined3d_mutex_unlock();
+
+    return priority;
+}
+
+static void WINAPI d3d9_vertexbuffer_PreLoad(IDirect3DVertexBuffer9 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    IWineD3DBuffer_PreLoad(((IDirect3DVertexBuffer9Impl *)iface)->wineD3DVertexBuffer);
+    wined3d_mutex_unlock();
+}
+
+static D3DRESOURCETYPE WINAPI d3d9_vertexbuffer_GetType(IDirect3DVertexBuffer9 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return D3DRTYPE_VERTEXBUFFER;
+}
+
+static HRESULT WINAPI d3d9_vertexbuffer_Lock(IDirect3DVertexBuffer9 *iface,
+        UINT offset, UINT size, void **data, DWORD flags)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, offset %u, size %u, data %p, flags %#x.\n",
+            iface, offset, size, data, flags);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_Map(((IDirect3DVertexBuffer9Impl *)iface)->wineD3DVertexBuffer,
+            offset, size, (BYTE **)data, flags);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d9_vertexbuffer_Unlock(IDirect3DVertexBuffer9 *iface)
+{
+    HRESULT hr;
+
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_Unmap(((IDirect3DVertexBuffer9Impl *)iface)->wineD3DVertexBuffer);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d9_vertexbuffer_GetDesc(IDirect3DVertexBuffer9 *iface, D3DVERTEXBUFFER_DESC *desc)
+{
+    IDirect3DVertexBuffer9Impl *buffer = (IDirect3DVertexBuffer9Impl *)iface;
+    WINED3DBUFFER_DESC wined3d_desc;
+
+    TRACE("iface %p, desc %p.\n", iface, desc);
+
+    wined3d_mutex_lock();
+    IWineD3DBuffer_GetDesc(buffer->wineD3DVertexBuffer, &wined3d_desc);
+    wined3d_mutex_unlock();
+
+    desc->Format = D3DFMT_VERTEXDATA;
+    desc->Usage = wined3d_desc.Usage;
+    desc->Pool = wined3d_desc.Pool;
+    desc->Size = wined3d_desc.Size;
+    desc->Type = D3DRTYPE_VERTEXBUFFER;
+    desc->FVF = buffer->fvf;
+
+    return D3D_OK;
+}
+
+static const IDirect3DVertexBuffer9Vtbl d3d9_vertexbuffer_vtbl =
+{
+    /* IUnknown */
+    d3d9_vertexbuffer_QueryInterface,
+    d3d9_vertexbuffer_AddRef,
+    d3d9_vertexbuffer_Release,
+    /* IDirect3DResource9 */
+    d3d9_vertexbuffer_GetDevice,
+    d3d9_vertexbuffer_SetPrivateData,
+    d3d9_vertexbuffer_GetPrivateData,
+    d3d9_vertexbuffer_FreePrivateData,
+    d3d9_vertexbuffer_SetPriority,
+    d3d9_vertexbuffer_GetPriority,
+    d3d9_vertexbuffer_PreLoad,
+    d3d9_vertexbuffer_GetType,
+    /* IDirect3DVertexBuffer9 */
+    d3d9_vertexbuffer_Lock,
+    d3d9_vertexbuffer_Unlock,
+    d3d9_vertexbuffer_GetDesc,
+};
+
+static void STDMETHODCALLTYPE d3d9_vertexbuffer_wined3d_object_destroyed(void *parent)
+{
+    HeapFree(GetProcessHeap(), 0, parent);
+}
+
+static const struct wined3d_parent_ops d3d9_vertexbuffer_wined3d_parent_ops =
+{
+    d3d9_vertexbuffer_wined3d_object_destroyed,
+};
+
+HRESULT vertexbuffer_init(IDirect3DVertexBuffer9Impl *buffer, IDirect3DDevice9Impl *device,
+        UINT size, UINT usage, DWORD fvf, D3DPOOL pool)
+{
+    HRESULT hr;
+
+    buffer->lpVtbl = &d3d9_vertexbuffer_vtbl;
+    buffer->ref = 1;
+    buffer->fvf = fvf;
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_CreateVertexBuffer(device->WineD3DDevice, size, usage & WINED3DUSAGE_MASK,
+            (WINED3DPOOL)pool, buffer, &d3d9_vertexbuffer_wined3d_parent_ops, &buffer->wineD3DVertexBuffer);
+    wined3d_mutex_unlock();
+    if (FAILED(hr))
+    {
+        WARN("Failed to create wined3d buffer, hr %#x.\n", hr);
+        return hr;
+    }
+
+    buffer->parentDevice = (IDirect3DDevice9Ex *)device;
+    IDirect3DDevice9Ex_AddRef(buffer->parentDevice);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d9_indexbuffer_QueryInterface(IDirect3DIndexBuffer9 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    if (IsEqualGUID(riid, &IID_IDirect3DIndexBuffer9)
+            || IsEqualGUID(riid, &IID_IDirect3DResource9)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
+        IDirect3DIndexBuffer9_AddRef(iface);
+        *object = iface;
+        return S_OK;
+    }
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI d3d9_indexbuffer_AddRef(IDirect3DIndexBuffer9 *iface)
+{
+    IDirect3DIndexBuffer9Impl *buffer = (IDirect3DIndexBuffer9Impl *)iface;
+    ULONG refcount = InterlockedIncrement(&buffer->ref);
+
+    TRACE("%p increasing refcount to %u.\n", iface, refcount);
+
+    if (refcount == 1)
+    {
+        IDirect3DDevice9Ex_AddRef(buffer->parentDevice);
+        wined3d_mutex_lock();
+        IWineD3DBuffer_AddRef(buffer->wineD3DIndexBuffer);
+        wined3d_mutex_unlock();
+    }
+
+    return refcount;
+}
+
+static ULONG WINAPI d3d9_indexbuffer_Release(IDirect3DIndexBuffer9 *iface)
+{
+    IDirect3DIndexBuffer9Impl *buffer = (IDirect3DIndexBuffer9Impl *)iface;
+    ULONG refcount = InterlockedDecrement(&buffer->ref);
+
+    TRACE("%p decreasing refcount to %u.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        IDirect3DDevice9Ex *device = buffer->parentDevice;
+
+        wined3d_mutex_lock();
+        IWineD3DBuffer_Release(buffer->wineD3DIndexBuffer);
+        wined3d_mutex_unlock();
+
+        /* Release the device last, as it may cause the device to be destroyed. */
+        IDirect3DDevice9Ex_Release(device);
+    }
+
+    return refcount;
+}
+
+static HRESULT WINAPI d3d9_indexbuffer_GetDevice(IDirect3DIndexBuffer9 *iface, IDirect3DDevice9 **device)
+{
+    TRACE("iface %p, device %p.\n", iface, device);
+
+    *device = (IDirect3DDevice9 *)((IDirect3DIndexBuffer9Impl *)iface)->parentDevice;
+    IDirect3DDevice9_AddRef(*device);
+
+    TRACE("Returning device %p.\n", *device);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d9_indexbuffer_SetPrivateData(IDirect3DIndexBuffer9 *iface,
+        REFGUID guid, const void *data, DWORD data_size, DWORD flags)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s, data %p, data_size %u, flags %#x.\n",
+            iface, debugstr_guid(guid), data, data_size, flags);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_SetPrivateData(((IDirect3DIndexBuffer9Impl *)iface)->wineD3DIndexBuffer,
+            guid, data, data_size, flags);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d9_indexbuffer_GetPrivateData(IDirect3DIndexBuffer9 *iface,
+        REFGUID guid, void *data, DWORD *data_size)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s, data %p, data_size %p.\n",
+            iface, debugstr_guid(guid), data, data_size);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_GetPrivateData(((IDirect3DIndexBuffer9Impl *)iface)->wineD3DIndexBuffer,
+            guid, data, data_size);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d9_indexbuffer_FreePrivateData(IDirect3DIndexBuffer9 *iface, REFGUID guid)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(guid));
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_FreePrivateData(((IDirect3DIndexBuffer9Impl *)iface)->wineD3DIndexBuffer, guid);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static DWORD WINAPI d3d9_indexbuffer_SetPriority(IDirect3DIndexBuffer9 *iface, DWORD priority)
+{
+    DWORD previous;
+
+    TRACE("iface %p, priority %u.\n", iface, priority);
+
+    wined3d_mutex_lock();
+    previous = IWineD3DBuffer_SetPriority(((IDirect3DIndexBuffer9Impl *)iface)->wineD3DIndexBuffer, priority);
+    wined3d_mutex_unlock();
+
+    return previous;
+}
+
+static DWORD WINAPI d3d9_indexbuffer_GetPriority(IDirect3DIndexBuffer9 *iface)
+{
+    DWORD priority;
+
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    priority = IWineD3DBuffer_GetPriority(((IDirect3DIndexBuffer9Impl *)iface)->wineD3DIndexBuffer);
+    wined3d_mutex_unlock();
+
+    return priority;
+}
+
+static void WINAPI d3d9_indexbuffer_PreLoad(IDirect3DIndexBuffer9 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    IWineD3DBuffer_PreLoad(((IDirect3DIndexBuffer9Impl *)iface)->wineD3DIndexBuffer);
+    wined3d_mutex_unlock();
+}
+
+static D3DRESOURCETYPE WINAPI d3d9_indexbuffer_GetType(IDirect3DIndexBuffer9 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return D3DRTYPE_INDEXBUFFER;
+}
+
+static HRESULT WINAPI d3d9_indexbuffer_Lock(IDirect3DIndexBuffer9 *iface,
+        UINT offset, UINT size, void **data, DWORD flags)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, offset %u, size %u, data %p, flags %#x.\n",
+            iface, offset, size, data, flags);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_Map(((IDirect3DIndexBuffer9Impl *)iface)->wineD3DIndexBuffer,
+            offset, size, (BYTE **)data, flags);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d9_indexbuffer_Unlock(IDirect3DIndexBuffer9 *iface)
+{
+    HRESULT hr;
+
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DBuffer_Unmap(((IDirect3DIndexBuffer9Impl *)iface)->wineD3DIndexBuffer);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d9_indexbuffer_GetDesc(IDirect3DIndexBuffer9 *iface, D3DINDEXBUFFER_DESC *desc)
+{
+    IDirect3DIndexBuffer9Impl *buffer = (IDirect3DIndexBuffer9Impl *)iface;
+    WINED3DBUFFER_DESC wined3d_desc;
+
+    TRACE("iface %p, desc %p.\n", iface, desc);
+
+    wined3d_mutex_lock();
+    IWineD3DBuffer_GetDesc(buffer->wineD3DIndexBuffer, &wined3d_desc);
+    wined3d_mutex_unlock();
+
+    desc->Format = d3dformat_from_wined3dformat(buffer->format);
+    desc->Usage = wined3d_desc.Usage;
+    desc->Pool = wined3d_desc.Pool;
+    desc->Size = wined3d_desc.Size;
+    desc->Type = D3DRTYPE_INDEXBUFFER;
+
+    return D3D_OK;
+}
+
+static const IDirect3DIndexBuffer9Vtbl d3d9_indexbuffer_vtbl =
+{
+    /* IUnknown */
+    d3d9_indexbuffer_QueryInterface,
+    d3d9_indexbuffer_AddRef,
+    d3d9_indexbuffer_Release,
+    /* IDirect3DResource9 */
+    d3d9_indexbuffer_GetDevice,
+    d3d9_indexbuffer_SetPrivateData,
+    d3d9_indexbuffer_GetPrivateData,
+    d3d9_indexbuffer_FreePrivateData,
+    d3d9_indexbuffer_SetPriority,
+    d3d9_indexbuffer_GetPriority,
+    d3d9_indexbuffer_PreLoad,
+    d3d9_indexbuffer_GetType,
+    /* IDirect3DIndexBuffer9 */
+    d3d9_indexbuffer_Lock,
+    d3d9_indexbuffer_Unlock,
+    d3d9_indexbuffer_GetDesc,
+};
+
+static void STDMETHODCALLTYPE d3d9_indexbuffer_wined3d_object_destroyed(void *parent)
+{
+    HeapFree(GetProcessHeap(), 0, parent);
+}
+
+static const struct wined3d_parent_ops d3d9_indexbuffer_wined3d_parent_ops =
+{
+    d3d9_indexbuffer_wined3d_object_destroyed,
+};
+
+HRESULT indexbuffer_init(IDirect3DIndexBuffer9Impl *buffer, IDirect3DDevice9Impl *device,
+        UINT size, DWORD usage, D3DFORMAT format, D3DPOOL pool)
+{
+    HRESULT hr;
+
+    buffer->lpVtbl = &d3d9_indexbuffer_vtbl;
+    buffer->ref = 1;
+    buffer->format = wined3dformat_from_d3dformat(format);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_CreateIndexBuffer(device->WineD3DDevice, size, usage & WINED3DUSAGE_MASK,
+            (WINED3DPOOL)pool, buffer, &d3d9_indexbuffer_wined3d_parent_ops, &buffer->wineD3DIndexBuffer);
+    wined3d_mutex_unlock();
+    if (FAILED(hr))
+    {
+        WARN("Failed to create wined3d buffer, hr %#x.\n", hr);
+        return hr;
+    }
+
+    buffer->parentDevice = (IDirect3DDevice9Ex *)device;
+    IDirect3DDevice9Ex_AddRef(buffer->parentDevice);
+
+    return D3D_OK;
+}
index c0d0e3c..508784f 100644 (file)
@@ -292,22 +292,27 @@ static HRESULT WINAPI IDirect3DCubeTexture9Impl_GetLevelDesc(LPDIRECT3DCUBETEXTU
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DCubeTexture9Impl_GetCubeMapSurface(LPDIRECT3DCUBETEXTURE9 iface, D3DCUBEMAP_FACES FaceType, UINT Level, IDirect3DSurface9** ppCubeMapSurface) {
+static HRESULT WINAPI IDirect3DCubeTexture9Impl_GetCubeMapSurface(IDirect3DCubeTexture9 *iface,
+        D3DCUBEMAP_FACES FaceType, UINT Level, IDirect3DSurface9 **ppCubeMapSurface)
+{
     IDirect3DCubeTexture9Impl *This = (IDirect3DCubeTexture9Impl *)iface;
-    HRESULT hrc = D3D_OK;
     IWineD3DSurface *mySurface = NULL;
+    HRESULT hr;
 
     TRACE("iface %p, face %#x, level %u, surface %p.\n", iface, FaceType, Level, ppCubeMapSurface);
 
     wined3d_mutex_lock();
-    hrc = IWineD3DCubeTexture_GetCubeMapSurface(This->wineD3DCubeTexture, (WINED3DCUBEMAP_FACES) FaceType, Level, &mySurface);
-    if (hrc == D3D_OK && NULL != ppCubeMapSurface) {
-       IWineD3DCubeTexture_GetParent(mySurface, (IUnknown **)ppCubeMapSurface);
-       IWineD3DCubeTexture_Release(mySurface);
+    hr = IWineD3DCubeTexture_GetCubeMapSurface(This->wineD3DCubeTexture,
+            (WINED3DCUBEMAP_FACES)FaceType, Level, &mySurface);
+    if (SUCCEEDED(hr) && ppCubeMapSurface)
+    {
+        *ppCubeMapSurface = IWineD3DCubeTexture_GetParent(mySurface);
+        IDirect3DSurface9_AddRef(*ppCubeMapSurface);
+        IWineD3DCubeTexture_Release(mySurface);
     }
     wined3d_mutex_unlock();
 
-    return hrc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DCubeTexture9Impl_LockRect(LPDIRECT3DCUBETEXTURE9 iface, D3DCUBEMAP_FACES FaceType, UINT Level, D3DLOCKED_RECT* pLockedRect, CONST RECT* pRect, DWORD Flags) {
@@ -399,9 +404,9 @@ HRESULT cubetexture_init(IDirect3DCubeTexture9Impl *texture, IDirect3DDevice9Imp
     texture->ref = 1;
 
     wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateCubeTexture(device->WineD3DDevice, edge_length, levels, usage,
-            wined3dformat_from_d3dformat(format), pool, &texture->wineD3DCubeTexture,
-            (IUnknown *)texture, &d3d9_cubetexture_wined3d_parent_ops);
+    hr = IWineD3DDevice_CreateCubeTexture(device->WineD3DDevice, edge_length,
+            levels, usage, wined3dformat_from_d3dformat(format), pool, texture,
+            &d3d9_cubetexture_wined3d_parent_ops, &texture->wineD3DCubeTexture);
     wined3d_mutex_unlock();
     if (FAILED(hr))
     {
index 290ea51..f35663c 100644 (file)
        <library>advapi32</library>
        <library>wined3d</library>
 
+       <file>buffer.c</file>
        <file>cubetexture.c</file>
        <file>d3d9_main.c</file>
        <file>device.c</file>
        <file>directx.c</file>
-       <file>indexbuffer.c</file>
-       <file>pixelshader.c</file>
        <file>query.c</file>
+       <file>shader.c</file>
        <file>stateblock.c</file>
        <file>surface.c</file>
        <file>swapchain.c</file>
        <file>texture.c</file>
-       <file>vertexbuffer.c</file>
        <file>vertexdeclaration.c</file>
-       <file>vertexshader.c</file>
        <file>volume.c</file>
        <file>volumetexture.c</file>
        <file>version.rc</file>
index eb3a032..f1bc1a0 100644 (file)
@@ -42,8 +42,8 @@
    Internal use
    =========================================================================== */
 extern HRESULT vdecl_convert_fvf(DWORD FVF, D3DVERTEXELEMENT9 **ppVertexElements) DECLSPEC_HIDDEN;
-D3DFORMAT d3dformat_from_wined3dformat(WINED3DFORMAT format) DECLSPEC_HIDDEN;
-WINED3DFORMAT wined3dformat_from_d3dformat(D3DFORMAT format) DECLSPEC_HIDDEN;
+D3DFORMAT d3dformat_from_wined3dformat(enum wined3d_format_id format) DECLSPEC_HIDDEN;
+enum wined3d_format_id wined3dformat_from_d3dformat(D3DFORMAT format) DECLSPEC_HIDDEN;
 
 /* ===========================================================================
     Macros
@@ -183,51 +183,6 @@ typedef struct IDirect3DDevice9Impl
 HRESULT device_init(IDirect3DDevice9Impl *device, IWineD3D *wined3d, UINT adapter, D3DDEVTYPE device_type,
         HWND focus_window, DWORD flags, D3DPRESENT_PARAMETERS *parameters) DECLSPEC_HIDDEN;
 
-/* IDirect3DDevice9: */
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetSwapChain(IDirect3DDevice9Ex *iface,
-        UINT iSwapChain, IDirect3DSwapChain9 **pSwapChain) DECLSPEC_HIDDEN;
-extern UINT WINAPI IDirect3DDevice9Impl_GetNumberOfSwapChains(IDirect3DDevice9Ex *iface) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_SetVertexDeclaration(IDirect3DDevice9Ex *iface,
-        IDirect3DVertexDeclaration9 *pDecl) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetVertexDeclaration(IDirect3DDevice9Ex *iface,
-        IDirect3DVertexDeclaration9 **ppDecl) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShader(IDirect3DDevice9Ex *iface,
-        IDirect3DVertexShader9 *pShader) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShader(IDirect3DDevice9Ex *iface,
-        IDirect3DVertexShader9 **ppShader) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShaderConstantF(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, const float *pConstantData, UINT Vector4fCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShaderConstantF(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, float *pConstantData, UINT Vector4fCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShaderConstantI(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, const int *pConstantData, UINT Vector4iCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShaderConstantI(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, int *pConstantData, UINT Vector4iCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShaderConstantB(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, const BOOL *pConstantData, UINT BoolCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShaderConstantB(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, BOOL *pConstantData, UINT BoolCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShader(IDirect3DDevice9Ex *iface,
-        IDirect3DPixelShader9 *pShader) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShader(IDirect3DDevice9Ex *iface,
-        IDirect3DPixelShader9  **ppShader) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShaderConstantF(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, const float *pConstantData, UINT Vector4fCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShaderConstantF(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, float *pConstantData, UINT Vector4fCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShaderConstantI(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, const int *pConstantData, UINT Vector4iCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShaderConstantI(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, int *pConstantData, UINT Vector4iCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShaderConstantB(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, const BOOL *pConstantData, UINT BoolCount) DECLSPEC_HIDDEN;
-extern HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShaderConstantB(IDirect3DDevice9Ex *iface,
-        UINT StartRegister, BOOL *pConstantData, UINT BoolCount) DECLSPEC_HIDDEN;
-
-/* ---------------- */
-/* IDirect3DVolume9 */
-/* ---------------- */
-
 /*****************************************************************************
  * IDirect3DVolume9 implementation structure
  */
@@ -248,7 +203,7 @@ typedef struct IDirect3DVolume9Impl
 } IDirect3DVolume9Impl;
 
 HRESULT volume_init(IDirect3DVolume9Impl *volume, IDirect3DDevice9Impl *device, UINT width, UINT height,
-        UINT depth, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool) DECLSPEC_HIDDEN;
+        UINT depth, DWORD usage, enum wined3d_format_id format, WINED3DPOOL pool) DECLSPEC_HIDDEN;
 
 /* ------------------- */
 /* IDirect3DSwapChain9 */
@@ -351,7 +306,7 @@ typedef struct IDirect3DIndexBuffer9Impl
 
     /* Parent reference */
     LPDIRECT3DDEVICE9EX       parentDevice;
-    WINED3DFORMAT             format;
+    enum wined3d_format_id format;
 } IDirect3DIndexBuffer9Impl;
 
 HRESULT indexbuffer_init(IDirect3DIndexBuffer9Impl *buffer, IDirect3DDevice9Impl *device,
index b9f539e..c788b98 100644 (file)
@@ -25,7 +25,7 @@
 
 WINE_DEFAULT_DEBUG_CHANNEL(d3d9);
 
-D3DFORMAT d3dformat_from_wined3dformat(WINED3DFORMAT format)
+D3DFORMAT d3dformat_from_wined3dformat(enum wined3d_format_id format)
 {
     BYTE *c = (BYTE *)&format;
 
@@ -85,12 +85,12 @@ D3DFORMAT d3dformat_from_wined3dformat(WINED3DFORMAT format)
         case WINED3DFMT_R32G32B32A32_FLOAT: return D3DFMT_A32B32G32R32F;
         case WINED3DFMT_R8G8_SNORM_Cx: return D3DFMT_CxV8U8;
         default:
-            FIXME("Unhandled WINED3DFORMAT %#x\n", format);
+            FIXME("Unhandled wined3d format %#x.\n", format);
             return D3DFMT_UNKNOWN;
     }
 }
 
-WINED3DFORMAT wined3dformat_from_d3dformat(D3DFORMAT format)
+enum wined3d_format_id wined3dformat_from_d3dformat(D3DFORMAT format)
 {
     BYTE *c = (BYTE *)&format;
 
@@ -187,8 +187,9 @@ static ULONG WINAPI D3D9CB_DestroySwapChain(IWineD3DSwapChain *swapchain)
 
     TRACE("swapchain %p.\n", swapchain);
 
-    IWineD3DSwapChain_GetParent(swapchain, (IUnknown **)&parent);
+    parent = IWineD3DSwapChain_GetParent(swapchain);
     parent->isImplicit = FALSE;
+    IDirect3DSwapChain9_AddRef((IDirect3DSwapChain9 *)parent);
     return IDirect3DSwapChain9_Release((IDirect3DSwapChain9 *)parent);
 }
 
@@ -337,7 +338,8 @@ static HRESULT WINAPI IDirect3DDevice9Impl_GetDirect3D(LPDIRECT3DDEVICE9EX iface
     hr = IWineD3DDevice_GetDirect3D(This->WineD3DDevice, &pWineD3D);
     if (hr == D3D_OK && pWineD3D != NULL)
     {
-        IWineD3D_GetParent(pWineD3D,(IUnknown **)ppD3D9);
+        *ppD3D9 = IWineD3D_GetParent(pWineD3D);
+        IDirect3D9_AddRef(*ppD3D9);
         IWineD3D_Release(pWineD3D);
     } else {
         FIXME("Call to IWineD3DDevice_GetDirect3D failed\n");
@@ -484,6 +486,45 @@ static HRESULT WINAPI DECLSPEC_HOTPATCH IDirect3DDevice9Impl_CreateAdditionalSwa
     return D3D_OK;
 }
 
+static HRESULT WINAPI DECLSPEC_HOTPATCH IDirect3DDevice9Impl_GetSwapChain(IDirect3DDevice9Ex *iface,
+        UINT swapchain_idx, IDirect3DSwapChain9 **swapchain)
+{
+    IWineD3DSwapChain *wined3d_swapchain = NULL;
+    HRESULT hr;
+
+    TRACE("iface %p, swapchain_idx %u, swapchain %p.\n", iface, swapchain_idx, swapchain);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_GetSwapChain(((IDirect3DDevice9Impl *)iface)->WineD3DDevice,
+            swapchain_idx, &wined3d_swapchain);
+    if (SUCCEEDED(hr) && swapchain)
+    {
+       *swapchain = IWineD3DSwapChain_GetParent(wined3d_swapchain);
+       IDirect3DSwapChain9_AddRef(*swapchain);
+       IWineD3DSwapChain_Release(wined3d_swapchain);
+    }
+    else
+    {
+        *swapchain = NULL;
+    }
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static UINT WINAPI IDirect3DDevice9Impl_GetNumberOfSwapChains(IDirect3DDevice9Ex *iface)
+{
+    UINT count;
+
+    TRACE("iface %p.\n", iface);
+
+    wined3d_mutex_lock();
+    count = IWineD3DDevice_GetNumberOfSwapChains(((IDirect3DDevice9Impl *)iface)->WineD3DDevice);
+    wined3d_mutex_unlock();
+
+    return count;
+}
+
 static HRESULT WINAPI reset_enum_callback(IWineD3DResource *resource, void *data) {
     BOOL *resources_ok = data;
     D3DRESOURCETYPE type;
@@ -495,7 +536,7 @@ static HRESULT WINAPI reset_enum_callback(IWineD3DResource *resource, void *data
     WINED3DPOOL pool;
     IDirect3DResource9 *parent;
 
-    IWineD3DResource_GetParent(resource, (IUnknown **) &parent);
+    parent = IWineD3DResource_GetParent(resource);
     type = IDirect3DResource9_GetType(parent);
     switch(type) {
         case D3DRTYPE_SURFACE:
@@ -526,16 +567,17 @@ static HRESULT WINAPI reset_enum_callback(IWineD3DResource *resource, void *data
             break;
     }
 
-    if(pool == WINED3DPOOL_DEFAULT) {
-        if(IUnknown_Release(parent) == 0) {
+    if (pool == WINED3DPOOL_DEFAULT)
+    {
+        IDirect3DResource9_AddRef(parent);
+        if (IUnknown_Release(parent) == 0)
+        {
             TRACE("Parent %p is an implicit resource with ref 0\n", parent);
         } else {
             WARN("Resource %p(wineD3D %p) with pool D3DPOOL_DEFAULT blocks the Reset call\n", parent, resource);
             ret = S_FALSE;
             *resources_ok = FALSE;
         }
-    } else {
-        IUnknown_Release(parent);
     }
     IWineD3DResource_Release(resource);
 
@@ -635,23 +677,28 @@ static HRESULT  WINAPI DECLSPEC_HOTPATCH IDirect3DDevice9Impl_Present(LPDIRECT3D
     return hr;
  }
 
-static HRESULT  WINAPI  IDirect3DDevice9Impl_GetBackBuffer(LPDIRECT3DDEVICE9EX iface, UINT iSwapChain, UINT BackBuffer, D3DBACKBUFFER_TYPE Type, IDirect3DSurface9 ** ppBackBuffer) {
+static HRESULT WINAPI IDirect3DDevice9Impl_GetBackBuffer(IDirect3DDevice9Ex *iface,
+        UINT iSwapChain, UINT BackBuffer, D3DBACKBUFFER_TYPE Type, IDirect3DSurface9 **ppBackBuffer)
+{
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     IWineD3DSurface *retSurface = NULL;
-    HRESULT rc = D3D_OK;
+    HRESULT hr;
 
     TRACE("iface %p, swapchain %u, backbuffer_idx %u, backbuffer_type %#x, backbuffer %p.\n",
             iface, iSwapChain, BackBuffer, Type, ppBackBuffer);
 
     wined3d_mutex_lock();
-    rc = IWineD3DDevice_GetBackBuffer(This->WineD3DDevice, iSwapChain, BackBuffer, (WINED3DBACKBUFFER_TYPE) Type, &retSurface);
-    if (rc == D3D_OK && NULL != retSurface && NULL != ppBackBuffer) {
-        IWineD3DSurface_GetParent(retSurface, (IUnknown **)ppBackBuffer);
+    hr = IWineD3DDevice_GetBackBuffer(This->WineD3DDevice, iSwapChain,
+            BackBuffer, (WINED3DBACKBUFFER_TYPE) Type, &retSurface);
+    if (SUCCEEDED(hr) && retSurface && ppBackBuffer)
+    {
+        *ppBackBuffer = IWineD3DSurface_GetParent(retSurface);
+        IDirect3DSurface9_AddRef(*ppBackBuffer);
         IWineD3DSurface_Release(retSurface);
     }
     wined3d_mutex_unlock();
 
-    return rc;
+    return hr;
 }
 static HRESULT  WINAPI  IDirect3DDevice9Impl_GetRasterStatus(LPDIRECT3DDEVICE9EX iface, UINT iSwapChain, D3DRASTER_STATUS* pRasterStatus) {
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
@@ -1007,7 +1054,16 @@ static HRESULT WINAPI IDirect3DDevice9Impl_StretchRect(IDirect3DDevice9Ex *iface
     return hr;
 }
 
-static HRESULT  WINAPI  IDirect3DDevice9Impl_ColorFill(LPDIRECT3DDEVICE9EX iface, IDirect3DSurface9* pSurface, CONST RECT* pRect, D3DCOLOR color) {
+static HRESULT WINAPI IDirect3DDevice9Impl_ColorFill(IDirect3DDevice9Ex *iface,
+        IDirect3DSurface9 *pSurface, const RECT *pRect, D3DCOLOR color)
+{
+    const WINED3DCOLORVALUE c =
+    {
+        ((color >> 16) & 0xff) / 255.0f,
+        ((color >>  8) & 0xff) / 255.0f,
+        (color & 0xff) / 255.0f,
+        ((color >> 24) & 0xff) / 255.0f,
+    };
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     IDirect3DSurface9Impl *surface = (IDirect3DSurface9Impl *)pSurface;
     WINED3DPOOL pool;
@@ -1035,8 +1091,7 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_ColorFill(LPDIRECT3DDEVICE9EX iface
     }
 
     /* Colorfill can only be used on rendertarget surfaces, or offscreen plain surfaces in D3DPOOL_DEFAULT */
-    /* Note: D3DRECT is compatible with WINED3DRECT */
-    hr = IWineD3DDevice_ColorFill(This->WineD3DDevice, surface->wineD3DSurface, (CONST WINED3DRECT*)pRect, color);
+    hr = IWineD3DDevice_ColorFill(This->WineD3DDevice, surface->wineD3DSurface, pRect, &c);
 
     wined3d_mutex_unlock();
 
@@ -1088,7 +1143,9 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_SetRenderTarget(LPDIRECT3DDEVICE9EX
     return hr;
 }
 
-static HRESULT  WINAPI  IDirect3DDevice9Impl_GetRenderTarget(LPDIRECT3DDEVICE9EX iface, DWORD RenderTargetIndex, IDirect3DSurface9 **ppRenderTarget) {
+static HRESULT WINAPI IDirect3DDevice9Impl_GetRenderTarget(IDirect3DDevice9Ex *iface,
+        DWORD RenderTargetIndex, IDirect3DSurface9 **ppRenderTarget)
+{
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     IWineD3DSurface *pRenderTarget;
     HRESULT hr;
@@ -1119,7 +1176,8 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_GetRenderTarget(LPDIRECT3DDEVICE9EX
     }
     else
     {
-        IWineD3DSurface_GetParent(pRenderTarget, (IUnknown **)ppRenderTarget);
+        *ppRenderTarget = IWineD3DSurface_GetParent(pRenderTarget);
+        IDirect3DSurface9_AddRef(*ppRenderTarget);
         IWineD3DSurface_Release(pRenderTarget);
     }
 
@@ -1144,10 +1202,12 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_SetDepthStencilSurface(LPDIRECT3DDE
     return hr;
 }
 
-static HRESULT  WINAPI  IDirect3DDevice9Impl_GetDepthStencilSurface(LPDIRECT3DDEVICE9EX iface, IDirect3DSurface9 **ppZStencilSurface) {
+static HRESULT WINAPI IDirect3DDevice9Impl_GetDepthStencilSurface(IDirect3DDevice9Ex *iface,
+        IDirect3DSurface9 **ppZStencilSurface)
+{
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr = D3D_OK;
     IWineD3DSurface *pZStencilSurface;
+    HRESULT hr;
 
     TRACE("iface %p, depth_stencil %p.\n", iface, ppZStencilSurface);
 
@@ -1157,10 +1217,14 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_GetDepthStencilSurface(LPDIRECT3DDE
 
     wined3d_mutex_lock();
     hr = IWineD3DDevice_GetDepthStencilSurface(This->WineD3DDevice,&pZStencilSurface);
-    if (hr == WINED3D_OK) {
-        IWineD3DSurface_GetParent(pZStencilSurface,(IUnknown**)ppZStencilSurface);
+    if (SUCCEEDED(hr))
+    {
+        *ppZStencilSurface = IWineD3DSurface_GetParent(pZStencilSurface);
+        IDirect3DSurface9_AddRef(*ppZStencilSurface);
         IWineD3DSurface_Release(pZStencilSurface);
-    } else {
+    }
+    else
+    {
         if (hr != WINED3DERR_NOTFOUND)
                 WARN("Call to IWineD3DDevice_GetDepthStencilSurface failed with 0x%08x\n", hr);
         *ppZStencilSurface = NULL;
@@ -1205,7 +1269,7 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_Clear(LPDIRECT3DDEVICE9EX iface, DW
 
     /* Note: D3DRECT is compatible with WINED3DRECT */
     wined3d_mutex_lock();
-    hr = IWineD3DDevice_Clear(This->WineD3DDevice, Count, (CONST WINED3DRECT*) pRects, Flags, Color, Z, Stencil);
+    hr = IWineD3DDevice_Clear(This->WineD3DDevice, Count, (const RECT *)pRects, Flags, Color, Z, Stencil);
     wined3d_mutex_unlock();
 
     return hr;
@@ -1532,10 +1596,12 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_GetClipStatus(LPDIRECT3DDEVICE9EX i
     return hr;
 }
 
-static HRESULT  WINAPI  IDirect3DDevice9Impl_GetTexture(LPDIRECT3DDEVICE9EX iface, DWORD Stage, IDirect3DBaseTexture9 **ppTexture) {
+static HRESULT WINAPI IDirect3DDevice9Impl_GetTexture(IDirect3DDevice9Ex *iface,
+        DWORD Stage, IDirect3DBaseTexture9 **ppTexture)
+{
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     IWineD3DBaseTexture *retTexture = NULL;
-    HRESULT rc = D3D_OK;
+    HRESULT hr;
 
     TRACE("iface %p, stage %u, texture %p.\n", iface, Stage, ppTexture);
 
@@ -1544,19 +1610,24 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_GetTexture(LPDIRECT3DDEVICE9EX ifac
     }
 
     wined3d_mutex_lock();
-    rc = IWineD3DDevice_GetTexture(This->WineD3DDevice, Stage, &retTexture);
-    if (SUCCEEDED(rc) && NULL != retTexture) {
-        IWineD3DBaseTexture_GetParent(retTexture, (IUnknown **)ppTexture);
+    hr = IWineD3DDevice_GetTexture(This->WineD3DDevice, Stage, &retTexture);
+    if (SUCCEEDED(hr) && retTexture)
+    {
+        *ppTexture = IWineD3DBaseTexture_GetParent(retTexture);
+        IWineD3DBaseTexture_AddRef(*ppTexture);
         IWineD3DBaseTexture_Release(retTexture);
-    } else {
-        if(FAILED(rc)) {
+    }
+    else
+    {
+        if (FAILED(hr))
+        {
             WARN("Call to get texture  (%d) failed (%p)\n", Stage, retTexture);
         }
         *ppTexture = NULL;
     }
     wined3d_mutex_unlock();
 
-    return rc;
+    return hr;
 }
 
 static HRESULT  WINAPI  IDirect3DDevice9Impl_SetTexture(LPDIRECT3DDEVICE9EX iface, DWORD Stage, IDirect3DBaseTexture9* pTexture) {
@@ -1610,12 +1681,19 @@ static const WINED3DTEXTURESTAGESTATETYPE tss_lookup[] =
     WINED3DTSS_CONSTANT,                /* 32, D3DTSS_CONSTANT */
 };
 
-static HRESULT  WINAPI  IDirect3DDevice9Impl_GetTextureStageState(LPDIRECT3DDEVICE9EX iface, DWORD Stage, D3DTEXTURESTAGESTATETYPE Type, DWORD* pValue) {
+static HRESULT  WINAPI  IDirect3DDevice9Impl_GetTextureStageState(LPDIRECT3DDEVICE9EX iface, DWORD Stage, D3DTEXTURESTAGESTATETYPE Type, DWORD *pValue)
+{
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     HRESULT hr;
 
     TRACE("iface %p, stage %u, state %#x, value %p.\n", iface, Stage, Type, pValue);
 
+    if (Type >= sizeof(tss_lookup) / sizeof(*tss_lookup))
+    {
+        WARN("Invalid Type %#x passed.\n", Type);
+        return D3D_OK;
+    }
+
     wined3d_mutex_lock();
     hr = IWineD3DDevice_GetTextureStageState(This->WineD3DDevice, Stage, tss_lookup[Type], pValue);
     wined3d_mutex_unlock();
@@ -1623,12 +1701,19 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_GetTextureStageState(LPDIRECT3DDEVI
     return hr;
 }
 
-static HRESULT  WINAPI  IDirect3DDevice9Impl_SetTextureStageState(LPDIRECT3DDEVICE9EX iface, DWORD Stage, D3DTEXTURESTAGESTATETYPE Type, DWORD Value) {
+static HRESULT  WINAPI  IDirect3DDevice9Impl_SetTextureStageState(LPDIRECT3DDEVICE9EX iface, DWORD Stage, D3DTEXTURESTAGESTATETYPE Type, DWORD Value)
+{
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     HRESULT hr;
 
     TRACE("iface %p, stage %u, state %#x, value %#x.\n", iface, Stage, Type, Value);
 
+    if (Type >= sizeof(tss_lookup) / sizeof(*tss_lookup))
+    {
+        WARN("Invalid Type %#x passed.\n", Type);
+        return D3D_OK;
+    }
+
     wined3d_mutex_lock();
     hr = IWineD3DDevice_SetTextureStageState(This->WineD3DDevice, Stage, tss_lookup[Type], Value);
     wined3d_mutex_unlock();
@@ -1939,6 +2024,49 @@ static HRESULT WINAPI IDirect3DDevice9Impl_CreateVertexDeclaration(IDirect3DDevi
     return D3D_OK;
 }
 
+static HRESULT WINAPI IDirect3DDevice9Impl_SetVertexDeclaration(IDirect3DDevice9Ex *iface,
+        IDirect3DVertexDeclaration9 *declaration)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, declaration %p.\n", iface, declaration);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_SetVertexDeclaration(((IDirect3DDevice9Impl *)iface)->WineD3DDevice,
+            declaration ? ((IDirect3DVertexDeclaration9Impl *)declaration)->wineD3DVertexDeclaration : NULL);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_GetVertexDeclaration(IDirect3DDevice9Ex *iface,
+        IDirect3DVertexDeclaration9 **declaration)
+{
+    IWineD3DVertexDeclaration *wined3d_declaration = NULL;
+    HRESULT hr;
+
+    TRACE("iface %p, declaration %p.\n", iface, declaration);
+
+    if (!declaration) return D3DERR_INVALIDCALL;
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_GetVertexDeclaration(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, &wined3d_declaration);
+    if (SUCCEEDED(hr) && wined3d_declaration)
+    {
+        *declaration = IWineD3DVertexDeclaration_GetParent(wined3d_declaration);
+        IDirect3DVertexDeclaration9_AddRef(*declaration);
+        IWineD3DVertexDeclaration_Release(wined3d_declaration);
+    }
+    else
+    {
+        *declaration = NULL;
+    }
+    wined3d_mutex_unlock();
+
+    TRACE("Returning %p.\n", *declaration);
+    return hr;
+}
+
 static IDirect3DVertexDeclaration9 *getConvertedDecl(IDirect3DDevice9Impl *This, DWORD fvf) {
     HRESULT hr;
     D3DVERTEXELEMENT9* elements = NULL;
@@ -2086,6 +2214,145 @@ static HRESULT WINAPI IDirect3DDevice9Impl_CreateVertexShader(IDirect3DDevice9Ex
     return D3D_OK;
 }
 
+static HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShader(IDirect3DDevice9Ex *iface,
+        IDirect3DVertexShader9 *shader)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, shader %p.\n", iface, shader);
+
+    wined3d_mutex_lock();
+    hr =  IWineD3DDevice_SetVertexShader(((IDirect3DDevice9Impl *)iface)->WineD3DDevice,
+            shader ? ((IDirect3DVertexShader9Impl *)shader)->wineD3DVertexShader : NULL);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShader(IDirect3DDevice9Ex *iface,
+        IDirect3DVertexShader9 **shader)
+{
+    IWineD3DVertexShader *wined3d_shader;
+
+    TRACE("iface %p, shader %p.\n", iface, shader);
+
+    wined3d_mutex_lock();
+    wined3d_shader = IWineD3DDevice_GetVertexShader(((IDirect3DDevice9Impl *)iface)->WineD3DDevice);
+    if (wined3d_shader)
+    {
+        *shader = IWineD3DVertexShader_GetParent(wined3d_shader);
+        IDirect3DVertexShader9_AddRef(*shader);
+        IWineD3DVertexShader_Release(wined3d_shader);
+    }
+    else
+    {
+        *shader = NULL;
+    }
+    wined3d_mutex_unlock();
+
+    TRACE("Returning %p.\n", *shader);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShaderConstantF(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, const float *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    if (reg_idx + count > D3D9_MAX_VERTEX_SHADER_CONSTANTF)
+    {
+        WARN("Trying to access %u constants, but d3d9 only supports %u\n",
+             reg_idx + count, D3D9_MAX_VERTEX_SHADER_CONSTANTF);
+        return D3DERR_INVALIDCALL;
+    }
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_SetVertexShaderConstantF(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShaderConstantF(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, float *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    if (reg_idx + count > D3D9_MAX_VERTEX_SHADER_CONSTANTF)
+    {
+        WARN("Trying to access %u constants, but d3d9 only supports %u\n",
+             reg_idx + count, D3D9_MAX_VERTEX_SHADER_CONSTANTF);
+        return D3DERR_INVALIDCALL;
+    }
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_GetVertexShaderConstantF(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShaderConstantI(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, const int *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_SetVertexShaderConstantI(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShaderConstantI(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, int *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_GetVertexShaderConstantI(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShaderConstantB(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, const BOOL *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_SetVertexShaderConstantB(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShaderConstantB(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, BOOL *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_GetVertexShaderConstantB(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
 static HRESULT WINAPI IDirect3DDevice9Impl_SetStreamSource(LPDIRECT3DDEVICE9EX iface, UINT StreamNumber, IDirect3DVertexBuffer9* pStreamData, UINT OffsetInBytes, UINT Stride) {
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     HRESULT hr;
@@ -2102,10 +2369,12 @@ static HRESULT WINAPI IDirect3DDevice9Impl_SetStreamSource(LPDIRECT3DDEVICE9EX i
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DDevice9Impl_GetStreamSource(LPDIRECT3DDEVICE9EX iface, UINT StreamNumber, IDirect3DVertexBuffer9 **pStream, UINT* OffsetInBytes, UINT* pStride) {
+static HRESULT WINAPI IDirect3DDevice9Impl_GetStreamSource(IDirect3DDevice9Ex *iface,
+        UINT StreamNumber, IDirect3DVertexBuffer9 **pStream, UINT* OffsetInBytes, UINT* pStride)
+{
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     IWineD3DBuffer *retStream = NULL;
-    HRESULT rc = D3D_OK;
+    HRESULT hr;
 
     TRACE("iface %p, stream_idx %u, buffer %p, offset %p, stride %p.\n",
             iface, StreamNumber, pStream, OffsetInBytes, pStride);
@@ -2115,19 +2384,24 @@ static HRESULT WINAPI IDirect3DDevice9Impl_GetStreamSource(LPDIRECT3DDEVICE9EX i
     }
 
     wined3d_mutex_lock();
-    rc = IWineD3DDevice_GetStreamSource(This->WineD3DDevice, StreamNumber, &retStream, OffsetInBytes, pStride);
-    if (rc == D3D_OK  && NULL != retStream) {
-        IWineD3DBuffer_GetParent(retStream, (IUnknown **)pStream);
+    hr = IWineD3DDevice_GetStreamSource(This->WineD3DDevice, StreamNumber, &retStream, OffsetInBytes, pStride);
+    if (SUCCEEDED(hr) && retStream)
+    {
+        *pStream = IWineD3DBuffer_GetParent(retStream);
+        IDirect3DVertexBuffer9_AddRef(*pStream);
         IWineD3DBuffer_Release(retStream);
-    }else{
-        if (rc != D3D_OK){
+    }
+    else
+    {
+        if (FAILED(hr))
+        {
             FIXME("Call to GetStreamSource failed %p %p\n", OffsetInBytes, pStride);
         }
         *pStream = NULL;
     }
     wined3d_mutex_unlock();
 
-    return rc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DDevice9Impl_SetStreamSourceFreq(IDirect3DDevice9Ex *iface, UINT StreamNumber,
@@ -2174,10 +2448,11 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_SetIndices(LPDIRECT3DDEVICE9EX ifac
     return hr;
 }
 
-static HRESULT  WINAPI  IDirect3DDevice9Impl_GetIndices(LPDIRECT3DDEVICE9EX iface, IDirect3DIndexBuffer9 **ppIndexData) {
+static HRESULT WINAPI IDirect3DDevice9Impl_GetIndices(IDirect3DDevice9Ex *iface, IDirect3DIndexBuffer9 **ppIndexData)
+{
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     IWineD3DBuffer *retIndexData = NULL;
-    HRESULT rc = D3D_OK;
+    HRESULT hr;
 
     TRACE("iface %p, buffer %p.\n", iface, ppIndexData);
 
@@ -2186,17 +2461,21 @@ static HRESULT  WINAPI  IDirect3DDevice9Impl_GetIndices(LPDIRECT3DDEVICE9EX ifac
     }
 
     wined3d_mutex_lock();
-    rc = IWineD3DDevice_GetIndexBuffer(This->WineD3DDevice, &retIndexData);
-    if (SUCCEEDED(rc) && retIndexData) {
-        IWineD3DBuffer_GetParent(retIndexData, (IUnknown **)ppIndexData);
+    hr = IWineD3DDevice_GetIndexBuffer(This->WineD3DDevice, &retIndexData);
+    if (SUCCEEDED(hr) && retIndexData)
+    {
+        *ppIndexData = IWineD3DBuffer_GetParent(retIndexData);
+        IDirect3DIndexBuffer9_AddRef(*ppIndexData);
         IWineD3DBuffer_Release(retIndexData);
-    } else {
-        if (FAILED(rc)) FIXME("Call to GetIndices failed\n");
+    }
+    else
+    {
+        if (FAILED(hr)) FIXME("Call to GetIndices failed\n");
         *ppIndexData = NULL;
     }
     wined3d_mutex_unlock();
 
-    return rc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DDevice9Impl_CreatePixelShader(IDirect3DDevice9Ex *iface,
@@ -2229,6 +2508,133 @@ static HRESULT WINAPI IDirect3DDevice9Impl_CreatePixelShader(IDirect3DDevice9Ex
     return D3D_OK;
 }
 
+static HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShader(IDirect3DDevice9Ex *iface,
+        IDirect3DPixelShader9 *shader)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, shader %p.\n", iface, shader);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_SetPixelShader(((IDirect3DDevice9Impl *)iface)->WineD3DDevice,
+            shader ? ((IDirect3DPixelShader9Impl *)shader)->wineD3DPixelShader : NULL);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShader(IDirect3DDevice9Ex *iface,
+        IDirect3DPixelShader9 **shader)
+{
+    IWineD3DPixelShader *wined3d_shader;
+
+    TRACE("iface %p, shader %p.\n", iface, shader);
+
+    if (!shader) return D3DERR_INVALIDCALL;
+
+    wined3d_mutex_lock();
+    wined3d_shader = IWineD3DDevice_GetPixelShader(((IDirect3DDevice9Impl *)iface)->WineD3DDevice);
+    if (wined3d_shader)
+    {
+        *shader = IWineD3DPixelShader_GetParent(wined3d_shader);
+        IDirect3DPixelShader9_AddRef(*shader);
+        IWineD3DPixelShader_Release(wined3d_shader);
+    }
+    else
+    {
+        *shader = NULL;
+    }
+    wined3d_mutex_unlock();
+
+    TRACE("Returning %p.\n", *shader);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShaderConstantF(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, const float *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_SetPixelShaderConstantF(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShaderConstantF(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, float *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_GetPixelShaderConstantF(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShaderConstantI(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, const int *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_SetPixelShaderConstantI(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShaderConstantI(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, int *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_GetPixelShaderConstantI(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShaderConstantB(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, const BOOL *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_SetPixelShaderConstantB(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShaderConstantB(IDirect3DDevice9Ex *iface,
+        UINT reg_idx, BOOL *data, UINT count)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, reg_idx %u, data %p, count %u.\n", iface, reg_idx, data, count);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_GetPixelShaderConstantB(((IDirect3DDevice9Impl *)iface)->WineD3DDevice, reg_idx, data, count);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
 static HRESULT  WINAPI  IDirect3DDevice9Impl_DrawRectPatch(LPDIRECT3DDEVICE9EX iface, UINT Handle, CONST float* pNumSegs, CONST D3DRECTPATCH_INFO* pRectPatchInfo) {
     IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
     HRESULT hr;
@@ -2610,7 +3016,7 @@ static void STDMETHODCALLTYPE device_parent_WineD3DDeviceCreated(IWineD3DDeviceP
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateSurface(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, WINED3DFORMAT format, DWORD usage,
+        IUnknown *superior, UINT width, UINT height, enum wined3d_format_id format, DWORD usage,
         WINED3DPOOL pool, UINT level, WINED3DCUBEMAP_FACES face, IWineD3DSurface **surface)
 {
     struct IDirect3DDevice9Impl *This = device_from_device_parent(iface);
@@ -2648,8 +3054,9 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateSurface(IWineD3DDeviceParen
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateRenderTarget(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, WINED3DFORMAT format, WINED3DMULTISAMPLE_TYPE multisample_type,
-        DWORD multisample_quality, BOOL lockable, IWineD3DSurface **surface)
+        IUnknown *superior, UINT width, UINT height, enum wined3d_format_id format,
+        WINED3DMULTISAMPLE_TYPE multisample_type, DWORD multisample_quality, BOOL lockable,
+        IWineD3DSurface **surface)
 {
     struct IDirect3DDevice9Impl *This = device_from_device_parent(iface);
     IDirect3DSurface9Impl *d3d_surface;
@@ -2679,16 +3086,16 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateRenderTarget(IWineD3DDevice
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateDepthStencilSurface(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, WINED3DFORMAT format, WINED3DMULTISAMPLE_TYPE multisample_type,
+        UINT width, UINT height, enum wined3d_format_id format, WINED3DMULTISAMPLE_TYPE multisample_type,
         DWORD multisample_quality, BOOL discard, IWineD3DSurface **surface)
 {
     struct IDirect3DDevice9Impl *This = device_from_device_parent(iface);
     IDirect3DSurface9Impl *d3d_surface;
     HRESULT hr;
 
-    TRACE("iface %p, superior %p, width %u, height %u, format %#x, multisample_type %#x,\n"
+    TRACE("iface %p, width %u, height %u, format %#x, multisample_type %#x,\n"
             "\tmultisample_quality %u, discard %u, surface %p\n",
-            iface, superior, width, height, format, multisample_type, multisample_quality, discard, surface);
+            iface, width, height, format, multisample_type, multisample_quality, discard, surface);
 
     hr = IDirect3DDevice9Impl_CreateDepthStencilSurface((IDirect3DDevice9Ex *)This, width, height,
             d3dformat_from_wined3dformat(format), multisample_type, multisample_quality, discard,
@@ -2709,7 +3116,7 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateDepthStencilSurface(IWineD3
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateVolume(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, UINT depth, WINED3DFORMAT format,
+        IUnknown *superior, UINT width, UINT height, UINT depth, enum wined3d_format_id format,
         WINED3DPOOL pool, DWORD usage, IWineD3DVolume **volume)
 {
     struct IDirect3DDevice9Impl *This = device_from_device_parent(iface);
@@ -2824,9 +3231,8 @@ static const IWineD3DDeviceParentVtbl d3d9_wined3d_device_parent_vtbl =
 
 static void setup_fpu(void)
 {
-    WORD cw;
-
 #if defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__))
+    WORD cw;
     __asm__ volatile ("fnstcw %0" : "=m" (cw));
     cw = (cw & ~0xf3f) | 0x3f;
     __asm__ volatile ("fldcw %0" : : "m" (cw));
@@ -2849,7 +3255,7 @@ HRESULT device_init(IDirect3DDevice9Impl *device, IWineD3D *wined3d, UINT adapte
     if (!(flags & D3DCREATE_FPU_PRESERVE)) setup_fpu();
 
     wined3d_mutex_lock();
-    hr = IWineD3D_CreateDevice(wined3d, adapter, device_type, focus_window, flags, (IUnknown *)device,
+    hr = IWineD3D_CreateDevice(wined3d, adapter, device_type, focus_window, flags,
             (IWineD3DDeviceParent *)&device->device_parent_vtbl, &device->WineD3DDevice);
     if (FAILED(hr))
     {
diff --git a/reactos/dll/directx/wine/d3d9/indexbuffer.c b/reactos/dll/directx/wine/d3d9/indexbuffer.c
deleted file mode 100644 (file)
index 1b7e8e4..0000000
+++ /dev/null
@@ -1,287 +0,0 @@
-/*
- * IDirect3DIndexBuffer9 implementation
- *
- * Copyright 2002-2004 Jason Edmeades
- *                     Raphael Junqueira
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "d3d9_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d9);
-
-/* IDirect3DIndexBuffer9 IUnknown parts follow: */
-static HRESULT WINAPI IDirect3DIndexBuffer9Impl_QueryInterface(LPDIRECT3DINDEXBUFFER9 iface, REFIID riid, LPVOID* ppobj) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-
-    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppobj);
-
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IDirect3DResource9)
-        || IsEqualGUID(riid, &IID_IDirect3DIndexBuffer9)) {
-        IDirect3DIndexBuffer9_AddRef(iface);
-        *ppobj = This;
-        return S_OK;
-    }
-
-    WARN("(%p)->(%s,%p),not found\n", This, debugstr_guid(riid), ppobj);
-    *ppobj = NULL;
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI IDirect3DIndexBuffer9Impl_AddRef(LPDIRECT3DINDEXBUFFER9 iface) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    ULONG ref = InterlockedIncrement(&This->ref);
-
-    TRACE("%p increasing refcount to %u.\n", iface, ref);
-
-    if (ref == 1)
-    {
-        IDirect3DDevice9Ex_AddRef(This->parentDevice);
-        wined3d_mutex_lock();
-        IWineD3DBuffer_AddRef(This->wineD3DIndexBuffer);
-        wined3d_mutex_unlock();
-    }
-
-    return ref;
-}
-
-static ULONG WINAPI IDirect3DIndexBuffer9Impl_Release(LPDIRECT3DINDEXBUFFER9 iface) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    ULONG ref = InterlockedDecrement(&This->ref);
-
-    TRACE("%p decreasing refcount to %u.\n", iface, ref);
-
-    if (ref == 0) {
-        IDirect3DDevice9Ex *parentDevice = This->parentDevice;
-
-        wined3d_mutex_lock();
-        IWineD3DBuffer_Release(This->wineD3DIndexBuffer);
-        wined3d_mutex_unlock();
-
-        /* Release the device last, as it may cause the device to be destroyed. */
-        IDirect3DDevice9Ex_Release(parentDevice);
-    }
-    return ref;
-}
-
-/* IDirect3DIndexBuffer9 IDirect3DResource9 Interface follow: */
-static HRESULT WINAPI IDirect3DIndexBuffer9Impl_GetDevice(IDirect3DIndexBuffer9 *iface, IDirect3DDevice9 **device)
-{
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-
-    TRACE("iface %p, device %p.\n", iface, device);
-
-    *device = (IDirect3DDevice9 *)This->parentDevice;
-    IDirect3DDevice9_AddRef(*device);
-
-    TRACE("Returning device %p.\n", *device);
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI IDirect3DIndexBuffer9Impl_SetPrivateData(LPDIRECT3DINDEXBUFFER9 iface, REFGUID refguid, CONST void* pData, DWORD SizeOfData, DWORD Flags) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s, data %p, data_size %u, flags %#x.\n",
-            iface, debugstr_guid(refguid), pData, SizeOfData, Flags);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_SetPrivateData(This->wineD3DIndexBuffer, refguid, pData, SizeOfData, Flags);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DIndexBuffer9Impl_GetPrivateData(LPDIRECT3DINDEXBUFFER9 iface, REFGUID refguid, void* pData, DWORD* pSizeOfData) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s, data %p, data_size %p.\n",
-            iface, debugstr_guid(refguid), pData, pSizeOfData);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_GetPrivateData(This->wineD3DIndexBuffer, refguid, pData, pSizeOfData);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DIndexBuffer9Impl_FreePrivateData(LPDIRECT3DINDEXBUFFER9 iface, REFGUID refguid) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(refguid));
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_FreePrivateData(This->wineD3DIndexBuffer, refguid);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static DWORD WINAPI IDirect3DIndexBuffer9Impl_SetPriority(LPDIRECT3DINDEXBUFFER9 iface, DWORD PriorityNew) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    DWORD ret;
-
-    TRACE("iface %p, priority %u.\n", iface, PriorityNew);
-
-    wined3d_mutex_lock();
-    ret = IWineD3DBuffer_SetPriority(This->wineD3DIndexBuffer, PriorityNew);
-    wined3d_mutex_unlock();
-
-    return ret;
-}
-
-static DWORD WINAPI IDirect3DIndexBuffer9Impl_GetPriority(LPDIRECT3DINDEXBUFFER9 iface) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    DWORD ret;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    ret = IWineD3DBuffer_GetPriority(This->wineD3DIndexBuffer);
-    wined3d_mutex_unlock();
-
-    return ret;
-}
-
-static void WINAPI IDirect3DIndexBuffer9Impl_PreLoad(LPDIRECT3DINDEXBUFFER9 iface) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    IWineD3DBuffer_PreLoad(This->wineD3DIndexBuffer);
-    wined3d_mutex_unlock();
-}
-
-static D3DRESOURCETYPE WINAPI IDirect3DIndexBuffer9Impl_GetType(IDirect3DIndexBuffer9 *iface)
-{
-    TRACE("iface %p.\n", iface);
-
-    return D3DRTYPE_INDEXBUFFER;
-}
-
-/* IDirect3DIndexBuffer9 Interface follow: */
-static HRESULT WINAPI IDirect3DIndexBuffer9Impl_Lock(LPDIRECT3DINDEXBUFFER9 iface, UINT OffsetToLock, UINT SizeToLock, void** ppbData, DWORD Flags) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, offset %u, size %u, data %p, flags %#x.\n",
-            iface, OffsetToLock, SizeToLock, ppbData, Flags);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_Map(This->wineD3DIndexBuffer, OffsetToLock, SizeToLock, (BYTE **)ppbData, Flags);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DIndexBuffer9Impl_Unlock(LPDIRECT3DINDEXBUFFER9 iface) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_Unmap(This->wineD3DIndexBuffer);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT  WINAPI        IDirect3DIndexBuffer9Impl_GetDesc(LPDIRECT3DINDEXBUFFER9 iface, D3DINDEXBUFFER_DESC *pDesc) {
-    IDirect3DIndexBuffer9Impl *This = (IDirect3DIndexBuffer9Impl *)iface;
-    HRESULT hr;
-    WINED3DBUFFER_DESC desc;
-
-    TRACE("iface %p, desc %p.\n", iface, pDesc);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_GetDesc(This->wineD3DIndexBuffer, &desc);
-    wined3d_mutex_unlock();
-
-    if (SUCCEEDED(hr)) {
-        pDesc->Format = d3dformat_from_wined3dformat(This->format);
-        pDesc->Usage = desc.Usage;
-        pDesc->Pool = desc.Pool;
-        pDesc->Size = desc.Size;
-        pDesc->Type = D3DRTYPE_INDEXBUFFER;
-    }
-
-    return hr;
-}
-
-
-static const IDirect3DIndexBuffer9Vtbl Direct3DIndexBuffer9_Vtbl =
-{
-    /* IUnknown */
-    IDirect3DIndexBuffer9Impl_QueryInterface,
-    IDirect3DIndexBuffer9Impl_AddRef,
-    IDirect3DIndexBuffer9Impl_Release,
-    /* IDirect3DResource9 */
-    IDirect3DIndexBuffer9Impl_GetDevice,
-    IDirect3DIndexBuffer9Impl_SetPrivateData,
-    IDirect3DIndexBuffer9Impl_GetPrivateData,
-    IDirect3DIndexBuffer9Impl_FreePrivateData,
-    IDirect3DIndexBuffer9Impl_SetPriority,
-    IDirect3DIndexBuffer9Impl_GetPriority,
-    IDirect3DIndexBuffer9Impl_PreLoad,
-    IDirect3DIndexBuffer9Impl_GetType,
-    /* IDirect3DIndexBuffer9 */
-    IDirect3DIndexBuffer9Impl_Lock,
-    IDirect3DIndexBuffer9Impl_Unlock,
-    IDirect3DIndexBuffer9Impl_GetDesc
-};
-
-static void STDMETHODCALLTYPE d3d9_indexbuffer_wined3d_object_destroyed(void *parent)
-{
-    HeapFree(GetProcessHeap(), 0, parent);
-}
-
-static const struct wined3d_parent_ops d3d9_indexbuffer_wined3d_parent_ops =
-{
-    d3d9_indexbuffer_wined3d_object_destroyed,
-};
-
-HRESULT indexbuffer_init(IDirect3DIndexBuffer9Impl *buffer, IDirect3DDevice9Impl *device,
-        UINT size, DWORD usage, D3DFORMAT format, D3DPOOL pool)
-{
-    HRESULT hr;
-
-    buffer->lpVtbl = &Direct3DIndexBuffer9_Vtbl;
-    buffer->ref = 1;
-    buffer->format = wined3dformat_from_d3dformat(format);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateIndexBuffer(device->WineD3DDevice, size,
-            usage & WINED3DUSAGE_MASK, (WINED3DPOOL)pool, &buffer->wineD3DIndexBuffer,
-            (IUnknown *)buffer, &d3d9_indexbuffer_wined3d_parent_ops);
-    wined3d_mutex_unlock();
-    if (FAILED(hr))
-    {
-        WARN("Failed to create wined3d buffer, hr %#x.\n", hr);
-        return hr;
-    }
-
-    buffer->parentDevice = (IDirect3DDevice9Ex *)device;
-    IDirect3DDevice9Ex_AddRef(buffer->parentDevice);
-
-    return D3D_OK;
-}
diff --git a/reactos/dll/directx/wine/d3d9/pixelshader.c b/reactos/dll/directx/wine/d3d9/pixelshader.c
deleted file mode 100644 (file)
index 7cb803a..0000000
+++ /dev/null
@@ -1,286 +0,0 @@
-/*
- * IDirect3DPixelShader9 implementation
- *
- * Copyright 2002-2003 Jason Edmeades
- *                     Raphael Junqueira
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "d3d9_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d9);
-
-/* IDirect3DPixelShader9 IUnknown parts follow: */
-static HRESULT WINAPI IDirect3DPixelShader9Impl_QueryInterface(LPDIRECT3DPIXELSHADER9 iface, REFIID riid, LPVOID* ppobj) {
-    IDirect3DPixelShader9Impl *This = (IDirect3DPixelShader9Impl *)iface;
-
-    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppobj);
-
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IDirect3DPixelShader9)) {
-        IDirect3DPixelShader9_AddRef(iface);
-        *ppobj = This;
-        return S_OK;
-    }
-
-    WARN("(%p)->(%s,%p),not found\n", This, debugstr_guid(riid), ppobj);
-    *ppobj = NULL;
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI IDirect3DPixelShader9Impl_AddRef(LPDIRECT3DPIXELSHADER9 iface) {
-    IDirect3DPixelShader9Impl *This = (IDirect3DPixelShader9Impl *)iface;
-    ULONG ref = InterlockedIncrement(&This->ref);
-
-    TRACE("%p increasing refcount to %u.\n", iface, ref);
-
-    if (ref == 1)
-    {
-        IDirect3DDevice9Ex_AddRef(This->parentDevice);
-        wined3d_mutex_lock();
-        IWineD3DPixelShader_AddRef(This->wineD3DPixelShader);
-        wined3d_mutex_unlock();
-    }
-
-    return ref;
-}
-
-static ULONG WINAPI IDirect3DPixelShader9Impl_Release(LPDIRECT3DPIXELSHADER9 iface) {
-    IDirect3DPixelShader9Impl *This = (IDirect3DPixelShader9Impl *)iface;
-    ULONG ref = InterlockedDecrement(&This->ref);
-
-    TRACE("%p decreasing refcount to %u.\n", iface, ref);
-
-    if (ref == 0) {
-        IDirect3DDevice9Ex *parentDevice = This->parentDevice;
-
-        wined3d_mutex_lock();
-        IWineD3DPixelShader_Release(This->wineD3DPixelShader);
-        wined3d_mutex_unlock();
-
-        /* Release the device last, as it may cause the device to be destroyed. */
-        IDirect3DDevice9Ex_Release(parentDevice);
-    }
-    return ref;
-}
-
-/* IDirect3DPixelShader9 Interface follow: */
-static HRESULT WINAPI IDirect3DPixelShader9Impl_GetDevice(IDirect3DPixelShader9 *iface, IDirect3DDevice9 **device)
-{
-    IDirect3DPixelShader9Impl *This = (IDirect3DPixelShader9Impl *)iface;
-
-    TRACE("iface %p, device %p.\n", iface, device);
-
-    *device = (IDirect3DDevice9 *)This->parentDevice;
-    IDirect3DDevice9_AddRef(*device);
-
-    TRACE("Returning device %p.\n", *device);
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI IDirect3DPixelShader9Impl_GetFunction(LPDIRECT3DPIXELSHADER9 iface, VOID* pData, UINT* pSizeOfData) {
-    IDirect3DPixelShader9Impl *This = (IDirect3DPixelShader9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, data %p, data_size %p.\n", iface, pData, pSizeOfData);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DPixelShader_GetFunction(This->wineD3DPixelShader, pData, pSizeOfData);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-
-static const IDirect3DPixelShader9Vtbl Direct3DPixelShader9_Vtbl =
-{
-    /* IUnknown */
-    IDirect3DPixelShader9Impl_QueryInterface,
-    IDirect3DPixelShader9Impl_AddRef,
-    IDirect3DPixelShader9Impl_Release,
-    /* IDirect3DPixelShader9 */
-    IDirect3DPixelShader9Impl_GetDevice,
-    IDirect3DPixelShader9Impl_GetFunction
-};
-
-static void STDMETHODCALLTYPE d3d9_pixelshader_wined3d_object_destroyed(void *parent)
-{
-    HeapFree(GetProcessHeap(), 0, parent);
-}
-
-static const struct wined3d_parent_ops d3d9_pixelshader_wined3d_parent_ops =
-{
-    d3d9_pixelshader_wined3d_object_destroyed,
-};
-
-HRESULT pixelshader_init(IDirect3DPixelShader9Impl *shader, IDirect3DDevice9Impl *device, const DWORD *byte_code)
-{
-    HRESULT hr;
-
-    shader->ref = 1;
-    shader->lpVtbl = &Direct3DPixelShader9_Vtbl;
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreatePixelShader(device->WineD3DDevice, byte_code,
-            NULL, &shader->wineD3DPixelShader, (IUnknown *)shader,
-            &d3d9_pixelshader_wined3d_parent_ops);
-    wined3d_mutex_unlock();
-    if (FAILED(hr))
-    {
-        WARN("Failed to created wined3d pixel shader, hr %#x.\n", hr);
-        return hr;
-    }
-
-    shader->parentDevice = (IDirect3DDevice9Ex *)device;
-    IDirect3DDevice9Ex_AddRef(shader->parentDevice);
-
-    return D3D_OK;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShader(LPDIRECT3DDEVICE9EX iface, IDirect3DPixelShader9* pShader) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    IDirect3DPixelShader9Impl *shader = (IDirect3DPixelShader9Impl *)pShader;
-
-    TRACE("iface %p, shader %p.\n", iface, shader);
-
-    wined3d_mutex_lock();
-    IWineD3DDevice_SetPixelShader(This->WineD3DDevice, shader == NULL ? NULL :shader->wineD3DPixelShader);
-    wined3d_mutex_unlock();
-
-    return D3D_OK;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShader(LPDIRECT3DDEVICE9EX iface, IDirect3DPixelShader9** ppShader) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    IWineD3DPixelShader *object;
-    HRESULT hrc;
-
-    TRACE("iface %p, shader %p.\n", iface, ppShader);
-
-    if (ppShader == NULL) {
-        TRACE("(%p) Invalid call\n", This);
-        return D3DERR_INVALIDCALL;
-    }
-
-    wined3d_mutex_lock();
-    hrc = IWineD3DDevice_GetPixelShader(This->WineD3DDevice, &object);
-    if (SUCCEEDED(hrc))
-    {
-        if (object)
-        {
-            hrc = IWineD3DPixelShader_GetParent(object, (IUnknown **)ppShader);
-            IWineD3DPixelShader_Release(object);
-        }
-        else
-        {
-            *ppShader = NULL;
-        }
-    }
-    else
-    {
-        WARN("(%p) : Call to IWineD3DDevice_GetPixelShader failed %u (device %p)\n", This, hrc, This->WineD3DDevice);
-    }
-    wined3d_mutex_unlock();
-
-    TRACE("(%p) : returning %p\n", This, *ppShader);
-    return hrc;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShaderConstantF(LPDIRECT3DDEVICE9EX iface, UINT Register, CONST float* pConstantData, UINT Vector4fCount) {
-   IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, Vector4fCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_SetPixelShaderConstantF(This->WineD3DDevice, Register, pConstantData, Vector4fCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShaderConstantF(LPDIRECT3DDEVICE9EX iface, UINT Register, float* pConstantData, UINT Vector4fCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, Vector4fCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_GetPixelShaderConstantF(This->WineD3DDevice, Register, pConstantData, Vector4fCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShaderConstantI(LPDIRECT3DDEVICE9EX iface, UINT Register, CONST int* pConstantData, UINT Vector4iCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, Vector4iCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_SetPixelShaderConstantI(This->WineD3DDevice, Register, pConstantData, Vector4iCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShaderConstantI(LPDIRECT3DDEVICE9EX iface, UINT Register, int* pConstantData, UINT Vector4iCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, Vector4iCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_GetPixelShaderConstantI(This->WineD3DDevice, Register, pConstantData, Vector4iCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_SetPixelShaderConstantB(LPDIRECT3DDEVICE9EX iface, UINT Register, CONST BOOL* pConstantData, UINT BoolCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, BoolCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_SetPixelShaderConstantB(This->WineD3DDevice, Register, pConstantData, BoolCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_GetPixelShaderConstantB(LPDIRECT3DDEVICE9EX iface, UINT Register, BOOL* pConstantData, UINT BoolCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, BoolCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_GetPixelShaderConstantB(This->WineD3DDevice, Register, pConstantData, BoolCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
index a38dc9d..4a58696 100644 (file)
@@ -158,7 +158,7 @@ HRESULT query_init(IDirect3DQuery9Impl *query, IDirect3DDevice9Impl *device, D3D
     query->ref = 1;
 
     wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateQuery(device->WineD3DDevice, type, &query->wineD3DQuery, (IUnknown *)query);
+    hr = IWineD3DDevice_CreateQuery(device->WineD3DDevice, type, &query->wineD3DQuery);
     wined3d_mutex_unlock();
     if (FAILED(hr))
     {
diff --git a/reactos/dll/directx/wine/d3d9/shader.c b/reactos/dll/directx/wine/d3d9/shader.c
new file mode 100644 (file)
index 0000000..c6656e5
--- /dev/null
@@ -0,0 +1,278 @@
+/*
+ * Copyright 2002-2003 Jason Edmeades
+ *                     Raphael Junqueira
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
+ */
+
+#include "config.h"
+#include "d3d9_private.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(d3d9);
+
+static HRESULT WINAPI d3d9_vertexshader_QueryInterface(IDirect3DVertexShader9 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    if (IsEqualGUID(riid, &IID_IDirect3DVertexShader9)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
+        IDirect3DVertexShader9_AddRef(iface);
+        *object = iface;
+        return S_OK;
+    }
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI d3d9_vertexshader_AddRef(IDirect3DVertexShader9 *iface)
+{
+    IDirect3DVertexShader9Impl *shader = (IDirect3DVertexShader9Impl *)iface;
+    ULONG refcount = InterlockedIncrement(&shader->ref);
+
+    TRACE("%p increasing refcount to %u.\n", iface, refcount);
+
+    if (refcount == 1)
+    {
+        IDirect3DDevice9Ex_AddRef(shader->parentDevice);
+        wined3d_mutex_lock();
+        IWineD3DVertexShader_AddRef(shader->wineD3DVertexShader);
+        wined3d_mutex_unlock();
+    }
+
+    return refcount;
+}
+
+static ULONG WINAPI d3d9_vertexshader_Release(IDirect3DVertexShader9 *iface)
+{
+    IDirect3DVertexShader9Impl *shader = (IDirect3DVertexShader9Impl *)iface;
+    ULONG refcount = InterlockedDecrement(&shader->ref);
+
+    TRACE("%p decreasing refcount to %u.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        IDirect3DDevice9Ex *device = shader->parentDevice;
+
+        wined3d_mutex_lock();
+        IWineD3DVertexShader_Release(shader->wineD3DVertexShader);
+        wined3d_mutex_unlock();
+
+        /* Release the device last, as it may cause the device to be destroyed. */
+        IDirect3DDevice9Ex_Release(device);
+    }
+
+    return refcount;
+}
+
+static HRESULT WINAPI d3d9_vertexshader_GetDevice(IDirect3DVertexShader9 *iface, IDirect3DDevice9 **device)
+{
+    TRACE("iface %p, device %p.\n", iface, device);
+
+    *device = (IDirect3DDevice9 *)((IDirect3DVertexShader9Impl *)iface)->parentDevice;
+    IDirect3DDevice9_AddRef(*device);
+
+    TRACE("Returning device %p.\n", *device);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d9_vertexshader_GetFunction(IDirect3DVertexShader9 *iface,
+        void *data, UINT *data_size)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, data %p, data_size %p.\n", iface, data, data_size);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DVertexShader_GetFunction(((IDirect3DVertexShader9Impl *)iface)->wineD3DVertexShader, data, data_size);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static const IDirect3DVertexShader9Vtbl d3d9_vertexshader_vtbl =
+{
+    /* IUnknown */
+    d3d9_vertexshader_QueryInterface,
+    d3d9_vertexshader_AddRef,
+    d3d9_vertexshader_Release,
+    /* IDirect3DVertexShader9 */
+    d3d9_vertexshader_GetDevice,
+    d3d9_vertexshader_GetFunction,
+};
+
+static void STDMETHODCALLTYPE d3d9_vertexshader_wined3d_object_destroyed(void *parent)
+{
+    HeapFree(GetProcessHeap(), 0, parent);
+}
+
+static const struct wined3d_parent_ops d3d9_vertexshader_wined3d_parent_ops =
+{
+    d3d9_vertexshader_wined3d_object_destroyed,
+};
+
+HRESULT vertexshader_init(IDirect3DVertexShader9Impl *shader, IDirect3DDevice9Impl *device, const DWORD *byte_code)
+{
+    HRESULT hr;
+
+    shader->ref = 1;
+    shader->lpVtbl = &d3d9_vertexshader_vtbl;
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_CreateVertexShader(device->WineD3DDevice, byte_code, NULL,
+            shader, &d3d9_vertexshader_wined3d_parent_ops, &shader->wineD3DVertexShader);
+    wined3d_mutex_unlock();
+    if (FAILED(hr))
+    {
+        WARN("Failed to create wined3d vertex shader, hr %#x.\n", hr);
+        return hr;
+    }
+
+    shader->parentDevice = (IDirect3DDevice9Ex *)device;
+    IDirect3DDevice9Ex_AddRef(shader->parentDevice);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d9_pixelshader_QueryInterface(IDirect3DPixelShader9 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    if (IsEqualGUID(riid, &IID_IDirect3DPixelShader9)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
+        IDirect3DPixelShader9_AddRef(iface);
+        *object = iface;
+        return S_OK;
+    }
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI d3d9_pixelshader_AddRef(IDirect3DPixelShader9 *iface)
+{
+    IDirect3DPixelShader9Impl *shader = (IDirect3DPixelShader9Impl *)iface;
+    ULONG refcount = InterlockedIncrement(&shader->ref);
+
+    TRACE("%p increasing refcount to %u.\n", iface, refcount);
+
+    if (refcount == 1)
+    {
+        IDirect3DDevice9Ex_AddRef(shader->parentDevice);
+        wined3d_mutex_lock();
+        IWineD3DPixelShader_AddRef(shader->wineD3DPixelShader);
+        wined3d_mutex_unlock();
+    }
+
+    return refcount;
+}
+
+static ULONG WINAPI d3d9_pixelshader_Release(IDirect3DPixelShader9 *iface)
+{
+    IDirect3DPixelShader9Impl *shader = (IDirect3DPixelShader9Impl *)iface;
+    ULONG refcount = InterlockedDecrement(&shader->ref);
+
+    TRACE("%p decreasing refcount to %u.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        IDirect3DDevice9Ex *device = shader->parentDevice;
+
+        wined3d_mutex_lock();
+        IWineD3DPixelShader_Release(shader->wineD3DPixelShader);
+        wined3d_mutex_unlock();
+
+        /* Release the device last, as it may cause the device to be destroyed. */
+        IDirect3DDevice9Ex_Release(device);
+    }
+
+    return refcount;
+}
+
+static HRESULT WINAPI d3d9_pixelshader_GetDevice(IDirect3DPixelShader9 *iface, IDirect3DDevice9 **device)
+{
+    TRACE("iface %p, device %p.\n", iface, device);
+
+    *device = (IDirect3DDevice9 *)((IDirect3DPixelShader9Impl *)iface)->parentDevice;
+    IDirect3DDevice9_AddRef(*device);
+
+    TRACE("Returning device %p.\n", *device);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d9_pixelshader_GetFunction(IDirect3DPixelShader9 *iface, void *data, UINT *data_size)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, data %p, data_size %p.\n", iface, data, data_size);
+
+    wined3d_mutex_lock();
+    hr = IWineD3DPixelShader_GetFunction(((IDirect3DPixelShader9Impl *)iface)->wineD3DPixelShader, data, data_size);
+    wined3d_mutex_unlock();
+
+    return hr;
+}
+
+static const IDirect3DPixelShader9Vtbl d3d9_pixelshader_vtbl =
+{
+    /* IUnknown */
+    d3d9_pixelshader_QueryInterface,
+    d3d9_pixelshader_AddRef,
+    d3d9_pixelshader_Release,
+    /* IDirect3DPixelShader9 */
+    d3d9_pixelshader_GetDevice,
+    d3d9_pixelshader_GetFunction,
+};
+
+static void STDMETHODCALLTYPE d3d9_pixelshader_wined3d_object_destroyed(void *parent)
+{
+    HeapFree(GetProcessHeap(), 0, parent);
+}
+
+static const struct wined3d_parent_ops d3d9_pixelshader_wined3d_parent_ops =
+{
+    d3d9_pixelshader_wined3d_object_destroyed,
+};
+
+HRESULT pixelshader_init(IDirect3DPixelShader9Impl *shader, IDirect3DDevice9Impl *device, const DWORD *byte_code)
+{
+    HRESULT hr;
+
+    shader->ref = 1;
+    shader->lpVtbl = &d3d9_pixelshader_vtbl;
+
+    wined3d_mutex_lock();
+    hr = IWineD3DDevice_CreatePixelShader(device->WineD3DDevice, byte_code, NULL, shader,
+            &d3d9_pixelshader_wined3d_parent_ops, &shader->wineD3DPixelShader);
+    wined3d_mutex_unlock();
+    if (FAILED(hr))
+    {
+        WARN("Failed to created wined3d pixel shader, hr %#x.\n", hr);
+        return hr;
+    }
+
+    shader->parentDevice = (IDirect3DDevice9Ex *)device;
+    IDirect3DDevice9Ex_AddRef(shader->parentDevice);
+
+    return D3D_OK;
+}
index c4941db..01a882e 100644 (file)
@@ -138,8 +138,8 @@ HRESULT stateblock_init(IDirect3DStateBlock9Impl *stateblock, IDirect3DDevice9Im
     else
     {
         wined3d_mutex_lock();
-        hr = IWineD3DDevice_CreateStateBlock(device->WineD3DDevice, (WINED3DSTATEBLOCKTYPE)type,
-                &stateblock->wineD3DStateBlock, (IUnknown *)stateblock);
+        hr = IWineD3DDevice_CreateStateBlock(device->WineD3DDevice,
+                (WINED3DSTATEBLOCKTYPE)type, &stateblock->wineD3DStateBlock);
         wined3d_mutex_unlock();
         if (FAILED(hr))
         {
index 210a0ee..de3fb77 100644 (file)
@@ -246,27 +246,23 @@ static HRESULT WINAPI IDirect3DSurface9Impl_GetContainer(LPDIRECT3DSURFACE9 ifac
 static HRESULT WINAPI IDirect3DSurface9Impl_GetDesc(LPDIRECT3DSURFACE9 iface, D3DSURFACE_DESC* pDesc) {
     IDirect3DSurface9Impl *This = (IDirect3DSurface9Impl *)iface;
     WINED3DSURFACE_DESC wined3ddesc;
-    HRESULT hr;
 
     TRACE("iface %p, desc %p.\n", iface, pDesc);
 
     wined3d_mutex_lock();
-    hr = IWineD3DSurface_GetDesc(This->wineD3DSurface, &wined3ddesc);
+    IWineD3DSurface_GetDesc(This->wineD3DSurface, &wined3ddesc);
     wined3d_mutex_unlock();
 
-    if (SUCCEEDED(hr))
-    {
-        pDesc->Format = d3dformat_from_wined3dformat(wined3ddesc.format);
-        pDesc->Type = wined3ddesc.resource_type;
-        pDesc->Usage = wined3ddesc.usage;
-        pDesc->Pool = wined3ddesc.pool;
-        pDesc->MultiSampleType = wined3ddesc.multisample_type;
-        pDesc->MultiSampleQuality = wined3ddesc.multisample_quality;
-        pDesc->Width = wined3ddesc.width;
-        pDesc->Height = wined3ddesc.height;
-    }
+    pDesc->Format = d3dformat_from_wined3dformat(wined3ddesc.format);
+    pDesc->Type = wined3ddesc.resource_type;
+    pDesc->Usage = wined3ddesc.usage;
+    pDesc->Pool = wined3ddesc.pool;
+    pDesc->MultiSampleType = wined3ddesc.multisample_type;
+    pDesc->MultiSampleQuality = wined3ddesc.multisample_quality;
+    pDesc->Width = wined3ddesc.width;
+    pDesc->Height = wined3ddesc.height;
 
-    return hr;
+    return D3D_OK;
 }
 
 static HRESULT WINAPI IDirect3DSurface9Impl_LockRect(LPDIRECT3DSURFACE9 iface, D3DLOCKED_RECT* pLockedRect, CONST RECT* pRect, DWORD Flags) {
@@ -403,9 +399,8 @@ HRESULT surface_init(IDirect3DSurface9Impl *surface, IDirect3DDevice9Impl *devic
 
     wined3d_mutex_lock();
     hr = IWineD3DDevice_CreateSurface(device->WineD3DDevice, width, height, wined3dformat_from_d3dformat(format),
-            lockable, discard, level, &surface->wineD3DSurface, usage & WINED3DUSAGE_MASK, (WINED3DPOOL)pool,
-            multisample_type, multisample_quality, SURFACE_OPENGL, (IUnknown *)surface,
-            &d3d9_surface_wined3d_parent_ops);
+            lockable, discard, level, usage & WINED3DUSAGE_MASK, (WINED3DPOOL)pool, multisample_type,
+            multisample_quality, SURFACE_OPENGL, surface, &d3d9_surface_wined3d_parent_ops, &surface->wineD3DSurface);
     wined3d_mutex_unlock();
     if (FAILED(hr))
     {
index c692371..0d52391 100644 (file)
@@ -106,24 +106,29 @@ static HRESULT WINAPI IDirect3DSwapChain9Impl_GetFrontBufferData(LPDIRECT3DSWAPC
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DSwapChain9Impl_GetBackBuffer(LPDIRECT3DSWAPCHAIN9 iface, UINT iBackBuffer, D3DBACKBUFFER_TYPE Type, IDirect3DSurface9** ppBackBuffer) {
+static HRESULT WINAPI IDirect3DSwapChain9Impl_GetBackBuffer(IDirect3DSwapChain9 *iface,
+        UINT iBackBuffer, D3DBACKBUFFER_TYPE Type, IDirect3DSurface9 **ppBackBuffer)
+{
     IDirect3DSwapChain9Impl *This = (IDirect3DSwapChain9Impl *)iface;
-    HRESULT hrc = D3D_OK;
     IWineD3DSurface *mySurface = NULL;
+    HRESULT hr;
 
     TRACE("iface %p, backbuffer_idx %u, backbuffer_type %#x, backbuffer %p.\n",
             iface, iBackBuffer, Type, ppBackBuffer);
 
     wined3d_mutex_lock();
-    hrc = IWineD3DSwapChain_GetBackBuffer(This->wineD3DSwapChain, iBackBuffer, (WINED3DBACKBUFFER_TYPE) Type, &mySurface);
-    if (hrc == D3D_OK && NULL != mySurface) {
-       IWineD3DSurface_GetParent(mySurface, (IUnknown **)ppBackBuffer);
+    hr = IWineD3DSwapChain_GetBackBuffer(This->wineD3DSwapChain, iBackBuffer,
+            (WINED3DBACKBUFFER_TYPE)Type, &mySurface);
+    if (SUCCEEDED(hr) && mySurface)
+    {
+       *ppBackBuffer = IWineD3DSurface_GetParent(mySurface);
+       IDirect3DSurface9_AddRef(*ppBackBuffer);
        IWineD3DSurface_Release(mySurface);
     }
     wined3d_mutex_unlock();
 
     /* Do not touch the **ppBackBuffer pointer otherwise! (see device test) */
-    return hrc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DSwapChain9Impl_GetRasterStatus(LPDIRECT3DSWAPCHAIN9 iface, D3DRASTER_STATUS* pRasterStatus) {
@@ -239,7 +244,7 @@ HRESULT swapchain_init(IDirect3DSwapChain9Impl *swapchain, IDirect3DDevice9Impl
 
     wined3d_mutex_lock();
     hr = IWineD3DDevice_CreateSwapChain(device->WineD3DDevice, &wined3d_parameters,
-            &swapchain->wineD3DSwapChain, (IUnknown *)swapchain, SURFACE_OPENGL);
+            SURFACE_OPENGL, swapchain, &swapchain->wineD3DSwapChain);
     wined3d_mutex_unlock();
 
     present_parameters->BackBufferWidth = wined3d_parameters.BackBufferWidth;
@@ -268,37 +273,3 @@ HRESULT swapchain_init(IDirect3DSwapChain9Impl *swapchain, IDirect3DDevice9Impl
 
     return D3D_OK;
 }
-
-HRESULT  WINAPI DECLSPEC_HOTPATCH IDirect3DDevice9Impl_GetSwapChain(LPDIRECT3DDEVICE9EX iface, UINT iSwapChain, IDirect3DSwapChain9** pSwapChain) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hrc = D3D_OK;
-    IWineD3DSwapChain *swapchain = NULL;
-
-    TRACE("iface %p, swapchain_idx %u, swapchain %p.\n",
-            iface, iSwapChain, pSwapChain);
-
-    wined3d_mutex_lock();
-    hrc = IWineD3DDevice_GetSwapChain(This->WineD3DDevice, iSwapChain, &swapchain);
-    if (hrc == D3D_OK && NULL != swapchain) {
-       IWineD3DSwapChain_GetParent(swapchain, (IUnknown **)pSwapChain);
-       IWineD3DSwapChain_Release(swapchain);
-    } else {
-        *pSwapChain = NULL;
-    }
-    wined3d_mutex_unlock();
-
-    return hrc;
-}
-
-UINT     WINAPI  IDirect3DDevice9Impl_GetNumberOfSwapChains(LPDIRECT3DDEVICE9EX iface) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    UINT ret;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    ret = IWineD3DDevice_GetNumberOfSwapChains(This->WineD3DDevice);
-    wined3d_mutex_unlock();
-
-    return ret;
-}
index 564057f..dbe9798 100644 (file)
@@ -289,22 +289,26 @@ static HRESULT WINAPI IDirect3DTexture9Impl_GetLevelDesc(LPDIRECT3DTEXTURE9 ifac
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DTexture9Impl_GetSurfaceLevel(LPDIRECT3DTEXTURE9 iface, UINT Level, IDirect3DSurface9** ppSurfaceLevel) {
+static HRESULT WINAPI IDirect3DTexture9Impl_GetSurfaceLevel(IDirect3DTexture9 *iface,
+        UINT Level, IDirect3DSurface9 **ppSurfaceLevel)
+{
     IDirect3DTexture9Impl *This = (IDirect3DTexture9Impl *)iface;
-    HRESULT hrc = D3D_OK;
     IWineD3DSurface *mySurface = NULL;
+    HRESULT hr;
 
     TRACE("iface %p, level %u, surface %p.\n", iface, Level, ppSurfaceLevel);
 
     wined3d_mutex_lock();
-    hrc = IWineD3DTexture_GetSurfaceLevel(This->wineD3DTexture, Level, &mySurface);
-    if (hrc == D3D_OK && NULL != ppSurfaceLevel) {
-       IWineD3DSurface_GetParent(mySurface, (IUnknown **)ppSurfaceLevel);
-       IWineD3DSurface_Release(mySurface);
+    hr = IWineD3DTexture_GetSurfaceLevel(This->wineD3DTexture, Level, &mySurface);
+    if (SUCCEEDED(hr) && ppSurfaceLevel)
+    {
+        *ppSurfaceLevel = IWineD3DSurface_GetParent(mySurface);
+        IDirect3DSurface9_AddRef(*ppSurfaceLevel);
+        IWineD3DSurface_Release(mySurface);
     }
     wined3d_mutex_unlock();
 
-    return hrc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DTexture9Impl_LockRect(LPDIRECT3DTEXTURE9 iface, UINT Level, D3DLOCKED_RECT* pLockedRect, CONST RECT* pRect, DWORD Flags) {
@@ -398,7 +402,7 @@ HRESULT texture_init(IDirect3DTexture9Impl *texture, IDirect3DDevice9Impl *devic
     wined3d_mutex_lock();
     hr = IWineD3DDevice_CreateTexture(device->WineD3DDevice, width, height, levels,
             usage & WINED3DUSAGE_MASK, wined3dformat_from_d3dformat(format), pool,
-            &texture->wineD3DTexture, (IUnknown *)texture, &d3d9_texture_wined3d_parent_ops);
+            texture, &d3d9_texture_wined3d_parent_ops, &texture->wineD3DTexture);
     wined3d_mutex_unlock();
     if (FAILED(hr))
     {
diff --git a/reactos/dll/directx/wine/d3d9/vertexbuffer.c b/reactos/dll/directx/wine/d3d9/vertexbuffer.c
deleted file mode 100644 (file)
index 1841bec..0000000
+++ /dev/null
@@ -1,289 +0,0 @@
-/*
- * IDirect3DVertexBuffer9 implementation
- *
- * Copyright 2002-2004 Jason Edmeades
- * Copyright 2002-2004 Raphael Junqueira
- * Copyright 2005 Oliver Stieber
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "d3d9_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d9);
-
-/* IDirect3DVertexBuffer9 IUnknown parts follow: */
-static HRESULT WINAPI IDirect3DVertexBuffer9Impl_QueryInterface(LPDIRECT3DVERTEXBUFFER9 iface, REFIID riid, LPVOID* ppobj) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-
-    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppobj);
-
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IDirect3DResource9)
-        || IsEqualGUID(riid, &IID_IDirect3DVertexBuffer9)) {
-        IDirect3DVertexBuffer9_AddRef(iface);
-        *ppobj = This;
-        return S_OK;
-    }
-
-    WARN("(%p)->(%s,%p),not found\n", This, debugstr_guid(riid), ppobj);
-    *ppobj = NULL;
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI IDirect3DVertexBuffer9Impl_AddRef(LPDIRECT3DVERTEXBUFFER9 iface) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    ULONG ref = InterlockedIncrement(&This->ref);
-
-    TRACE("%p increasing refcount to %u.\n", iface, ref);
-
-    if (ref == 1)
-    {
-        IDirect3DDevice9Ex_AddRef(This->parentDevice);
-        wined3d_mutex_lock();
-        IWineD3DBuffer_AddRef(This->wineD3DVertexBuffer);
-        wined3d_mutex_unlock();
-    }
-
-    return ref;
-}
-
-static ULONG WINAPI IDirect3DVertexBuffer9Impl_Release(LPDIRECT3DVERTEXBUFFER9 iface) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    ULONG ref = InterlockedDecrement(&This->ref);
-
-    TRACE("%p decreasing refcount to %u.\n", iface, ref);
-
-    if (ref == 0) {
-        IDirect3DDevice9Ex *parentDevice = This->parentDevice;
-
-        wined3d_mutex_lock();
-        IWineD3DBuffer_Release(This->wineD3DVertexBuffer);
-        wined3d_mutex_unlock();
-
-        /* Release the device last, as it may cause the device to be destroyed. */
-        IDirect3DDevice9Ex_Release(parentDevice);
-    }
-    return ref;
-}
-
-/* IDirect3DVertexBuffer9 IDirect3DResource9 Interface follow: */
-static HRESULT WINAPI IDirect3DVertexBuffer9Impl_GetDevice(IDirect3DVertexBuffer9 *iface, IDirect3DDevice9 **device)
-{
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-
-    TRACE("iface %p, device %p.\n", iface, device);
-
-    *device = (IDirect3DDevice9 *)This->parentDevice;
-    IDirect3DDevice9_AddRef(*device);
-
-    TRACE("Returning device %p.\n", *device);
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer9Impl_SetPrivateData(LPDIRECT3DVERTEXBUFFER9 iface, REFGUID refguid, CONST void* pData, DWORD SizeOfData, DWORD Flags) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s, data %p, data_size %u, flags %#x.\n",
-            iface, debugstr_guid(refguid), pData, SizeOfData, Flags);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_SetPrivateData(This->wineD3DVertexBuffer, refguid, pData, SizeOfData, Flags);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer9Impl_GetPrivateData(LPDIRECT3DVERTEXBUFFER9 iface, REFGUID refguid, void* pData, DWORD* pSizeOfData) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s, data %p, data_size %p.\n",
-            iface, debugstr_guid(refguid), pData, pSizeOfData);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_GetPrivateData(This->wineD3DVertexBuffer, refguid, pData, pSizeOfData);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer9Impl_FreePrivateData(LPDIRECT3DVERTEXBUFFER9 iface, REFGUID refguid) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(refguid));
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_FreePrivateData(This->wineD3DVertexBuffer, refguid);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static DWORD WINAPI IDirect3DVertexBuffer9Impl_SetPriority(LPDIRECT3DVERTEXBUFFER9 iface, DWORD PriorityNew) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, priority %u.\n", iface, PriorityNew);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_SetPriority(This->wineD3DVertexBuffer, PriorityNew);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static DWORD WINAPI IDirect3DVertexBuffer9Impl_GetPriority(LPDIRECT3DVERTEXBUFFER9 iface) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_GetPriority(This->wineD3DVertexBuffer);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static void WINAPI IDirect3DVertexBuffer9Impl_PreLoad(LPDIRECT3DVERTEXBUFFER9 iface) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    IWineD3DBuffer_PreLoad(This->wineD3DVertexBuffer);
-    wined3d_mutex_unlock();
-}
-
-static D3DRESOURCETYPE WINAPI IDirect3DVertexBuffer9Impl_GetType(IDirect3DVertexBuffer9 *iface)
-{
-    TRACE("iface %p.\n", iface);
-
-    return D3DRTYPE_VERTEXBUFFER;
-}
-
-/* IDirect3DVertexBuffer9 Interface follow: */
-static HRESULT WINAPI IDirect3DVertexBuffer9Impl_Lock(LPDIRECT3DVERTEXBUFFER9 iface, UINT OffsetToLock, UINT SizeToLock, void** ppbData, DWORD Flags) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, offset %u, size %u, data %p, flags %#x.\n",
-            iface, OffsetToLock, SizeToLock, ppbData, Flags);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_Map(This->wineD3DVertexBuffer, OffsetToLock, SizeToLock, (BYTE **)ppbData, Flags);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer9Impl_Unlock(LPDIRECT3DVERTEXBUFFER9 iface) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p.\n", iface);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_Unmap(This->wineD3DVertexBuffer);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-static HRESULT WINAPI IDirect3DVertexBuffer9Impl_GetDesc(LPDIRECT3DVERTEXBUFFER9 iface, D3DVERTEXBUFFER_DESC* pDesc) {
-    IDirect3DVertexBuffer9Impl *This = (IDirect3DVertexBuffer9Impl *)iface;
-    HRESULT hr;
-    WINED3DBUFFER_DESC desc;
-
-    TRACE("iface %p, desc %p.\n", iface, pDesc);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DBuffer_GetDesc(This->wineD3DVertexBuffer, &desc);
-    wined3d_mutex_unlock();
-
-    if (SUCCEEDED(hr)) {
-        pDesc->Format = D3DFMT_VERTEXDATA;
-        pDesc->Usage = desc.Usage;
-        pDesc->Pool = desc.Pool;
-        pDesc->Size = desc.Size;
-        pDesc->Type = D3DRTYPE_VERTEXBUFFER;
-        pDesc->FVF = This->fvf;
-    }
-
-
-    return hr;
-}
-
-static const IDirect3DVertexBuffer9Vtbl Direct3DVertexBuffer9_Vtbl =
-{
-    /* IUnknown */
-    IDirect3DVertexBuffer9Impl_QueryInterface,
-    IDirect3DVertexBuffer9Impl_AddRef,
-    IDirect3DVertexBuffer9Impl_Release,
-    /* IDirect3DResource9 */
-    IDirect3DVertexBuffer9Impl_GetDevice,
-    IDirect3DVertexBuffer9Impl_SetPrivateData,
-    IDirect3DVertexBuffer9Impl_GetPrivateData,
-    IDirect3DVertexBuffer9Impl_FreePrivateData,
-    IDirect3DVertexBuffer9Impl_SetPriority,
-    IDirect3DVertexBuffer9Impl_GetPriority,
-    IDirect3DVertexBuffer9Impl_PreLoad,
-    IDirect3DVertexBuffer9Impl_GetType,
-    /* IDirect3DVertexBuffer9 */
-    IDirect3DVertexBuffer9Impl_Lock,
-    IDirect3DVertexBuffer9Impl_Unlock,
-    IDirect3DVertexBuffer9Impl_GetDesc
-};
-
-static void STDMETHODCALLTYPE d3d9_vertexbuffer_wined3d_object_destroyed(void *parent)
-{
-    HeapFree(GetProcessHeap(), 0, parent);
-}
-
-static const struct wined3d_parent_ops d3d9_vertexbuffer_wined3d_parent_ops =
-{
-    d3d9_vertexbuffer_wined3d_object_destroyed,
-};
-
-HRESULT vertexbuffer_init(IDirect3DVertexBuffer9Impl *buffer, IDirect3DDevice9Impl *device,
-        UINT size, UINT usage, DWORD fvf, D3DPOOL pool)
-{
-    HRESULT hr;
-
-    buffer->lpVtbl = &Direct3DVertexBuffer9_Vtbl;
-    buffer->ref = 1;
-    buffer->fvf = fvf;
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateVertexBuffer(device->WineD3DDevice, size,
-            usage & WINED3DUSAGE_MASK, (WINED3DPOOL)pool, &buffer->wineD3DVertexBuffer,
-            (IUnknown *)buffer, &d3d9_vertexbuffer_wined3d_parent_ops);
-    wined3d_mutex_unlock();
-    if (FAILED(hr))
-    {
-        WARN("Failed to create wined3d buffer, hr %#x.\n", hr);
-        return hr;
-    }
-
-    buffer->parentDevice = (IDirect3DDevice9Ex *)device;
-    IDirect3DDevice9Ex_AddRef(buffer->parentDevice);
-
-    return D3D_OK;
-}
index d3ee1dc..88f912f 100644 (file)
@@ -26,7 +26,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d9);
 
 typedef struct _D3DDECLTYPE_INFO {
     D3DDECLTYPE d3dType;
-    WINED3DFORMAT format;
+    enum wined3d_format_id format;
     int         size;
     int         typesize;
 } D3DDECLTYPE_INFO;
@@ -395,9 +395,8 @@ HRESULT vertexdeclaration_init(IDirect3DVertexDeclaration9Impl *declaration,
     declaration->element_count = element_count;
 
     wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateVertexDeclaration(device->WineD3DDevice, &declaration->wineD3DVertexDeclaration,
-            (IUnknown *)declaration, &d3d9_vertexdeclaration_wined3d_parent_ops,
-            wined3d_elements, wined3d_element_count);
+    hr = IWineD3DDevice_CreateVertexDeclaration(device->WineD3DDevice, wined3d_elements, wined3d_element_count,
+            declaration, &d3d9_vertexdeclaration_wined3d_parent_ops, &declaration->wineD3DVertexDeclaration);
     wined3d_mutex_unlock();
     HeapFree(GetProcessHeap(), 0, wined3d_elements);
     if (FAILED(hr))
@@ -412,44 +411,3 @@ HRESULT vertexdeclaration_init(IDirect3DVertexDeclaration9Impl *declaration,
 
     return D3D_OK;
 }
-
-HRESULT  WINAPI  IDirect3DDevice9Impl_SetVertexDeclaration(LPDIRECT3DDEVICE9EX iface, IDirect3DVertexDeclaration9* pDecl) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    IDirect3DVertexDeclaration9Impl *pDeclImpl = (IDirect3DVertexDeclaration9Impl *)pDecl;
-    HRESULT hr = D3D_OK;
-
-    TRACE("iface %p, vertex declaration %p.\n", iface, pDecl);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_SetVertexDeclaration(This->WineD3DDevice, pDeclImpl == NULL ? NULL : pDeclImpl->wineD3DVertexDeclaration);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT  WINAPI  IDirect3DDevice9Impl_GetVertexDeclaration(LPDIRECT3DDEVICE9EX iface, IDirect3DVertexDeclaration9** ppDecl) {
-    IDirect3DDevice9Impl* This = (IDirect3DDevice9Impl*) iface;
-    IWineD3DVertexDeclaration* pTest = NULL;
-    HRESULT hr = D3D_OK;
-
-    TRACE("iface %p, declaration %p.\n", iface, ppDecl);
-
-    if (NULL == ppDecl) {
-      return D3DERR_INVALIDCALL;
-    }
-
-    *ppDecl = NULL;
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_GetVertexDeclaration(This->WineD3DDevice, &pTest);
-    if (hr == D3D_OK && NULL != pTest) {
-        IWineD3DVertexDeclaration_GetParent(pTest, (IUnknown **)ppDecl);
-        IWineD3DVertexDeclaration_Release(pTest);
-    } else {
-        *ppDecl = NULL;
-    }
-    wined3d_mutex_unlock();
-
-    TRACE("(%p) : returning %p\n", This, *ppDecl);
-    return hr;
-}
diff --git a/reactos/dll/directx/wine/d3d9/vertexshader.c b/reactos/dll/directx/wine/d3d9/vertexshader.c
deleted file mode 100644 (file)
index 21a4e87..0000000
+++ /dev/null
@@ -1,294 +0,0 @@
-/*
- * IDirect3DVertexShader9 implementation
- *
- * Copyright 2002-2003 Jason Edmeades
- *                     Raphael Junqueira
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "d3d9_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d9);
-
-/* IDirect3DVertexShader9 IUnknown parts follow: */
-static HRESULT WINAPI IDirect3DVertexShader9Impl_QueryInterface(LPDIRECT3DVERTEXSHADER9 iface, REFIID riid, LPVOID* ppobj) {
-    IDirect3DVertexShader9Impl *This = (IDirect3DVertexShader9Impl *)iface;
-
-    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppobj);
-
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IDirect3DVertexShader9)) {
-        IDirect3DVertexShader9_AddRef(iface);
-        *ppobj = This;
-        return S_OK;
-    }
-
-    WARN("(%p)->(%s,%p),not found\n", This, debugstr_guid(riid), ppobj);
-    *ppobj = NULL;
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI IDirect3DVertexShader9Impl_AddRef(LPDIRECT3DVERTEXSHADER9 iface) {
-    IDirect3DVertexShader9Impl *This = (IDirect3DVertexShader9Impl *)iface;
-    ULONG ref = InterlockedIncrement(&This->ref);
-
-    TRACE("%p increasing refcount to %u.\n", iface, ref);
-
-    if (ref == 1)
-    {
-        IDirect3DDevice9Ex_AddRef(This->parentDevice);
-        wined3d_mutex_lock();
-        IWineD3DVertexShader_AddRef(This->wineD3DVertexShader);
-        wined3d_mutex_unlock();
-    }
-
-    return ref;
-}
-
-static ULONG WINAPI IDirect3DVertexShader9Impl_Release(LPDIRECT3DVERTEXSHADER9 iface) {
-    IDirect3DVertexShader9Impl *This = (IDirect3DVertexShader9Impl *)iface;
-    ULONG ref = InterlockedDecrement(&This->ref);
-
-    TRACE("%p decreasing refcount to %u.\n", iface, ref);
-
-    if (ref == 0) {
-        IDirect3DDevice9Ex *parentDevice = This->parentDevice;
-
-        wined3d_mutex_lock();
-        IWineD3DVertexShader_Release(This->wineD3DVertexShader);
-        wined3d_mutex_unlock();
-
-        /* Release the device last, as it may cause the device to be destroyed. */
-        IDirect3DDevice9Ex_Release(parentDevice);
-    }
-    return ref;
-}
-
-/* IDirect3DVertexShader9 Interface follow: */
-static HRESULT WINAPI IDirect3DVertexShader9Impl_GetDevice(IDirect3DVertexShader9 *iface, IDirect3DDevice9 **device)
-{
-    IDirect3DVertexShader9Impl *This = (IDirect3DVertexShader9Impl *)iface;
-
-    TRACE("iface %p, device %p.\n", iface, device);
-
-    *device = (IDirect3DDevice9 *)This->parentDevice;
-    IDirect3DDevice9_AddRef(*device);
-
-    TRACE("Returning device %p.\n", *device);
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI IDirect3DVertexShader9Impl_GetFunction(LPDIRECT3DVERTEXSHADER9 iface, VOID* pData, UINT* pSizeOfData) {
-    IDirect3DVertexShader9Impl *This = (IDirect3DVertexShader9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, data %p, data_size %p.\n", iface, pData, pSizeOfData);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DVertexShader_GetFunction(This->wineD3DVertexShader, pData, pSizeOfData);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-
-static const IDirect3DVertexShader9Vtbl Direct3DVertexShader9_Vtbl =
-{
-    /* IUnknown */
-    IDirect3DVertexShader9Impl_QueryInterface,
-    IDirect3DVertexShader9Impl_AddRef,
-    IDirect3DVertexShader9Impl_Release,
-    /* IDirect3DVertexShader9 */
-    IDirect3DVertexShader9Impl_GetDevice,
-    IDirect3DVertexShader9Impl_GetFunction
-};
-
-static void STDMETHODCALLTYPE d3d9_vertexshader_wined3d_object_destroyed(void *parent)
-{
-    HeapFree(GetProcessHeap(), 0, parent);
-}
-
-static const struct wined3d_parent_ops d3d9_vertexshader_wined3d_parent_ops =
-{
-    d3d9_vertexshader_wined3d_object_destroyed,
-};
-
-HRESULT vertexshader_init(IDirect3DVertexShader9Impl *shader, IDirect3DDevice9Impl *device, const DWORD *byte_code)
-{
-    HRESULT hr;
-
-    shader->ref = 1;
-    shader->lpVtbl = &Direct3DVertexShader9_Vtbl;
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_CreateVertexShader(device->WineD3DDevice, byte_code,
-            NULL /* output signature */, &shader->wineD3DVertexShader,
-            (IUnknown *)shader, &d3d9_vertexshader_wined3d_parent_ops);
-    wined3d_mutex_unlock();
-    if (FAILED(hr))
-    {
-        WARN("Failed to create wined3d vertex shader, hr %#x.\n", hr);
-        return hr;
-    }
-
-    shader->parentDevice = (IDirect3DDevice9Ex *)device;
-    IDirect3DDevice9Ex_AddRef(shader->parentDevice);
-
-    return D3D_OK;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShader(LPDIRECT3DDEVICE9EX iface, IDirect3DVertexShader9* pShader) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hrc = D3D_OK;
-
-    TRACE("iface %p, shader %p.\n", iface, pShader);
-
-    wined3d_mutex_lock();
-    hrc =  IWineD3DDevice_SetVertexShader(This->WineD3DDevice, pShader==NULL?NULL:((IDirect3DVertexShader9Impl *)pShader)->wineD3DVertexShader);
-    wined3d_mutex_unlock();
-
-    TRACE("(%p) : returning hr(%u)\n", This, hrc);
-    return hrc;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShader(LPDIRECT3DDEVICE9EX iface, IDirect3DVertexShader9** ppShader) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    IWineD3DVertexShader *pShader;
-    HRESULT hrc = D3D_OK;
-
-    TRACE("iface %p, shader %p.\n", iface, ppShader);
-
-    wined3d_mutex_lock();
-    hrc = IWineD3DDevice_GetVertexShader(This->WineD3DDevice, &pShader);
-    if (SUCCEEDED(hrc))
-    {
-        if (pShader)
-        {
-            hrc = IWineD3DVertexShader_GetParent(pShader, (IUnknown **)ppShader);
-            IWineD3DVertexShader_Release(pShader);
-        }
-        else
-        {
-            *ppShader = NULL;
-        }
-    }
-    else
-    {
-        WARN("(%p) : Call to IWineD3DDevice_GetVertexShader failed %u (device %p)\n", This, hrc, This->WineD3DDevice);
-    }
-    wined3d_mutex_unlock();
-
-    TRACE("(%p) : returning %p\n", This, *ppShader);
-    return hrc;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShaderConstantF(LPDIRECT3DDEVICE9EX iface, UINT Register, CONST float* pConstantData, UINT Vector4fCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, Vector4fCount);
-
-    if(Register + Vector4fCount > D3D9_MAX_VERTEX_SHADER_CONSTANTF) {
-        WARN("Trying to access %u constants, but d3d9 only supports %u\n",
-             Register + Vector4fCount, D3D9_MAX_VERTEX_SHADER_CONSTANTF);
-        return D3DERR_INVALIDCALL;
-    }
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_SetVertexShaderConstantF(This->WineD3DDevice, Register, pConstantData, Vector4fCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShaderConstantF(LPDIRECT3DDEVICE9EX iface, UINT Register, float* pConstantData, UINT Vector4fCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, Vector4fCount);
-
-    if(Register + Vector4fCount > D3D9_MAX_VERTEX_SHADER_CONSTANTF) {
-        WARN("Trying to access %u constants, but d3d9 only supports %u\n",
-             Register + Vector4fCount, D3D9_MAX_VERTEX_SHADER_CONSTANTF);
-        return D3DERR_INVALIDCALL;
-    }
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_GetVertexShaderConstantF(This->WineD3DDevice, Register, pConstantData, Vector4fCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShaderConstantI(LPDIRECT3DDEVICE9EX iface, UINT Register, CONST int* pConstantData, UINT Vector4iCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, Vector4iCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_SetVertexShaderConstantI(This->WineD3DDevice, Register, pConstantData, Vector4iCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShaderConstantI(LPDIRECT3DDEVICE9EX iface, UINT Register, int* pConstantData, UINT Vector4iCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, Vector4iCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_GetVertexShaderConstantI(This->WineD3DDevice, Register, pConstantData, Vector4iCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_SetVertexShaderConstantB(LPDIRECT3DDEVICE9EX iface, UINT Register, CONST BOOL* pConstantData, UINT BoolCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, BoolCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_SetVertexShaderConstantB(This->WineD3DDevice, Register, pConstantData, BoolCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
-
-HRESULT WINAPI IDirect3DDevice9Impl_GetVertexShaderConstantB(LPDIRECT3DDEVICE9EX iface, UINT Register, BOOL* pConstantData, UINT BoolCount) {
-    IDirect3DDevice9Impl *This = (IDirect3DDevice9Impl *)iface;
-    HRESULT hr;
-
-    TRACE("iface %p, register %u, data %p, count %u.\n",
-            iface, Register, pConstantData, BoolCount);
-
-    wined3d_mutex_lock();
-    hr = IWineD3DDevice_GetVertexShaderConstantB(This->WineD3DDevice, Register, pConstantData, BoolCount);
-    wined3d_mutex_unlock();
-
-    return hr;
-}
index baa286b..1ecd2b2 100644 (file)
@@ -182,29 +182,25 @@ static HRESULT WINAPI IDirect3DVolume9Impl_GetContainer(LPDIRECT3DVOLUME9 iface,
 
 static HRESULT WINAPI IDirect3DVolume9Impl_GetDesc(LPDIRECT3DVOLUME9 iface, D3DVOLUME_DESC* pDesc) {
     IDirect3DVolume9Impl *This = (IDirect3DVolume9Impl *)iface;
-    WINED3DVOLUME_DESC     wined3ddesc;
-    HRESULT hr;
+    WINED3DVOLUME_DESC wined3ddesc;
 
     TRACE("iface %p, desc %p.\n", iface, pDesc);
 
     wined3d_mutex_lock();
 
-    hr = IWineD3DVolume_GetDesc(This->wineD3DVolume, &wined3ddesc);
+    IWineD3DVolume_GetDesc(This->wineD3DVolume, &wined3ddesc);
 
     wined3d_mutex_unlock();
 
-    if (SUCCEEDED(hr))
-    {
-        pDesc->Format = d3dformat_from_wined3dformat(wined3ddesc.Format);
-        pDesc->Type = wined3ddesc.Type;
-        pDesc->Usage = wined3ddesc.Usage;
-        pDesc->Pool = wined3ddesc.Pool;
-        pDesc->Width = wined3ddesc.Width;
-        pDesc->Height = wined3ddesc.Height;
-        pDesc->Depth = wined3ddesc.Depth;
-    }
+    pDesc->Format = d3dformat_from_wined3dformat(wined3ddesc.Format);
+    pDesc->Type = wined3ddesc.Type;
+    pDesc->Usage = wined3ddesc.Usage;
+    pDesc->Pool = wined3ddesc.Pool;
+    pDesc->Width = wined3ddesc.Width;
+    pDesc->Height = wined3ddesc.Height;
+    pDesc->Depth = wined3ddesc.Depth;
 
-    return hr;
+    return D3D_OK;
 }
 
 static HRESULT WINAPI IDirect3DVolume9Impl_LockBox(LPDIRECT3DVOLUME9 iface, D3DLOCKED_BOX* pLockedVolume, CONST D3DBOX* pBox, DWORD Flags) {
@@ -267,7 +263,7 @@ static const struct wined3d_parent_ops d3d9_volume_wined3d_parent_ops =
 };
 
 HRESULT volume_init(IDirect3DVolume9Impl *volume, IDirect3DDevice9Impl *device, UINT width, UINT height,
-        UINT depth, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool)
+        UINT depth, DWORD usage, enum wined3d_format_id format, WINED3DPOOL pool)
 {
     HRESULT hr;
 
@@ -275,7 +271,7 @@ HRESULT volume_init(IDirect3DVolume9Impl *volume, IDirect3DDevice9Impl *device,
     volume->ref = 1;
 
     hr = IWineD3DDevice_CreateVolume(device->WineD3DDevice, width, height, depth, usage & WINED3DUSAGE_MASK,
-            format, pool, &volume->wineD3DVolume, (IUnknown *)volume, &d3d9_volume_wined3d_parent_ops);
+            format, pool, volume, &d3d9_volume_wined3d_parent_ops, &volume->wineD3DVolume);
     if (FAILED(hr))
     {
         WARN("Failed to create wined3d volume, hr %#x.\n", hr);
index ca9ca9c..7ce4623 100644 (file)
@@ -315,24 +315,28 @@ static HRESULT WINAPI IDirect3DVolumeTexture9Impl_GetLevelDesc(LPDIRECT3DVOLUMET
     return hr;
 }
 
-static HRESULT WINAPI IDirect3DVolumeTexture9Impl_GetVolumeLevel(LPDIRECT3DVOLUMETEXTURE9 iface, UINT Level, IDirect3DVolume9** ppVolumeLevel) {
+static HRESULT WINAPI IDirect3DVolumeTexture9Impl_GetVolumeLevel(IDirect3DVolumeTexture9 *iface,
+        UINT Level, IDirect3DVolume9 **ppVolumeLevel)
+{
     IDirect3DVolumeTexture9Impl *This = (IDirect3DVolumeTexture9Impl *)iface;
-    HRESULT hrc = D3D_OK;
     IWineD3DVolume *myVolume = NULL;
+    HRESULT hr;
 
     TRACE("iface %p, level %u, volume %p.\n", iface, Level, ppVolumeLevel);
 
     wined3d_mutex_lock();
 
-    hrc = IWineD3DVolumeTexture_GetVolumeLevel(This->wineD3DVolumeTexture, Level, &myVolume);
-    if (hrc == D3D_OK && NULL != ppVolumeLevel) {
-       IWineD3DVolumeTexture_GetParent(myVolume, (IUnknown **)ppVolumeLevel);
+    hr = IWineD3DVolumeTexture_GetVolumeLevel(This->wineD3DVolumeTexture, Level, &myVolume);
+    if (SUCCEEDED(hr) && ppVolumeLevel)
+    {
+       *ppVolumeLevel = IWineD3DVolumeTexture_GetParent(myVolume);
+       IDirect3DVolumeTexture9_AddRef(*ppVolumeLevel);
        IWineD3DVolumeTexture_Release(myVolume);
     }
 
     wined3d_mutex_unlock();
 
-    return hrc;
+    return hr;
 }
 
 static HRESULT WINAPI IDirect3DVolumeTexture9Impl_LockBox(LPDIRECT3DVOLUMETEXTURE9 iface, UINT Level, D3DLOCKED_BOX* pLockedVolume, CONST D3DBOX* pBox, DWORD Flags) {
@@ -433,8 +437,8 @@ HRESULT volumetexture_init(IDirect3DVolumeTexture9Impl *texture, IDirect3DDevice
 
     wined3d_mutex_lock();
     hr = IWineD3DDevice_CreateVolumeTexture(device->WineD3DDevice, width, height, depth, levels,
-            usage & WINED3DUSAGE_MASK, wined3dformat_from_d3dformat(format), pool,
-            &texture->wineD3DVolumeTexture, (IUnknown *)texture, &d3d9_volumetexture_wined3d_parent_ops);
+            usage & WINED3DUSAGE_MASK, wined3dformat_from_d3dformat(format), pool, texture,
+            &d3d9_volumetexture_wined3d_parent_ops, &texture->wineD3DVolumeTexture);
     wined3d_mutex_unlock();
     if (FAILED(hr))
     {
index 4fa4c36..b4c493c 100644 (file)
  */
 
 #include "config.h"
-
-#include <stdarg.h>
-#include <stdlib.h>
-#include <string.h>
-
-#define COBJMACROS
-
-#include "windef.h"
-#include "winbase.h"
-#include "wingdi.h"
-#include "ddraw.h"
-#include "winerror.h"
+#include "wine/port.h"
 
 #include "ddraw_private.h"
 
-#include "wine/debug.h"
-
 WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
 /*****************************************************************************
@@ -62,17 +49,18 @@ WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 static HRESULT WINAPI IDirectDrawClipperImpl_QueryInterface(
     LPDIRECTDRAWCLIPPER iface, REFIID riid, LPVOID* ppvObj
 ) {
-    if (IsEqualGUID(&IID_IUnknown, riid)
-       || IsEqualGUID(&IID_IDirectDrawClipper, riid))
+
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppvObj);
+
+    if (IsEqualGUID(&IID_IDirectDrawClipper, riid)
+            || IsEqualGUID(&IID_IUnknown, riid))
     {
         IUnknown_AddRef(iface);
         *ppvObj = iface;
         return S_OK;
     }
-    else
-    {
-       return E_NOINTERFACE;
-    }
+
+    return E_NOINTERFACE;
 }
 
 /*****************************************************************************
@@ -86,7 +74,7 @@ static ULONG WINAPI IDirectDrawClipperImpl_AddRef( LPDIRECTDRAWCLIPPER iface )
     IDirectDrawClipperImpl *This = (IDirectDrawClipperImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    TRACE("(%p)->() incrementing from %u.\n", This, ref - 1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -102,7 +90,7 @@ static ULONG WINAPI IDirectDrawClipperImpl_Release(IDirectDrawClipper *iface) {
     IDirectDrawClipperImpl *This = (IDirectDrawClipperImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
 
-    TRACE("(%p)->() decrementing from %u.\n", This, ref + 1);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (ref == 0)
     {
@@ -135,7 +123,8 @@ static HRESULT WINAPI IDirectDrawClipperImpl_SetHwnd(
 ) {
     IDirectDrawClipperImpl *This = (IDirectDrawClipperImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p)\n", This, dwFlags, hWnd);
+
+    TRACE("iface %p, flags %#x, window %p.\n", iface, dwFlags, hWnd);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DClipper_SetHWnd(This->wineD3DClipper,
@@ -173,7 +162,9 @@ static HRESULT WINAPI IDirectDrawClipperImpl_GetClipList(
 {
     IDirectDrawClipperImpl *This = (IDirectDrawClipperImpl *)iface;
     HRESULT hr;
-    TRACE("(%p,%p,%p,%p)\n", This, lpRect, lpClipList, lpdwSize);
+
+    TRACE("iface %p, rect %s, clip_list %p, clip_list_size %p.\n",
+            iface, wine_dbgstr_rect(lpRect), lpClipList, lpdwSize);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DClipper_GetClipList(This->wineD3DClipper,
@@ -204,6 +195,8 @@ static HRESULT WINAPI IDirectDrawClipperImpl_SetClipList(
     IDirectDrawClipperImpl *This = (IDirectDrawClipperImpl *)iface;
     HRESULT hr;
 
+    TRACE("iface %p, clip_list %p, flags %#x.\n", iface, lprgn, dwFlag);
+
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DClipper_SetClipList(This->wineD3DClipper,
                                      lprgn,
@@ -228,7 +221,8 @@ static HRESULT WINAPI IDirectDrawClipperImpl_GetHWnd(
 ) {
     IDirectDrawClipperImpl *This = (IDirectDrawClipperImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p)\n", This, hWndPtr);
+
+    TRACE("iface %p, window %p.\n", iface, hWndPtr);
 
     EnterCriticalSection(&ddraw_cs);
     hr =  IWineD3DClipper_GetHWnd(This->wineD3DClipper,
@@ -254,19 +248,18 @@ static HRESULT WINAPI IDirectDrawClipperImpl_GetHWnd(
 static HRESULT WINAPI IDirectDrawClipperImpl_Initialize(
      LPDIRECTDRAWCLIPPER iface, LPDIRECTDRAW lpDD, DWORD dwFlags
 ) {
-    IDirectDrawImpl* pOwner;
     IDirectDrawClipperImpl *This = (IDirectDrawClipperImpl *)iface;
-    TRACE("(%p)->(%p,0x%08x)\n", This, lpDD, dwFlags);
+
+    TRACE("iface %p, ddraw %p, flags %#x.\n", iface, lpDD, dwFlags);
 
     EnterCriticalSection(&ddraw_cs);
-    if (This->ddraw_owner != NULL)
+    if (This->initialized)
     {
         LeaveCriticalSection(&ddraw_cs);
         return DDERR_ALREADYINITIALIZED;
     }
 
-    pOwner = lpDD ? ddraw_from_ddraw1(lpDD) : NULL;
-    This->ddraw_owner = pOwner;
+    This->initialized = TRUE;
 
     LeaveCriticalSection(&ddraw_cs);
     return DD_OK;
@@ -286,8 +279,7 @@ static HRESULT WINAPI IDirectDrawClipperImpl_Initialize(
 static HRESULT WINAPI IDirectDrawClipperImpl_IsClipListChanged(
     LPDIRECTDRAWCLIPPER iface, BOOL* lpbChanged
 ) {
-    IDirectDrawClipperImpl *This = (IDirectDrawClipperImpl *)iface;
-    FIXME("(%p)->(%p),stub!\n",This,lpbChanged);
+    FIXME("iface %p, changed %p stub!\n", iface, lpbChanged);
 
     /* XXX What is safest? */
     *lpbChanged = FALSE;
@@ -298,7 +290,7 @@ static HRESULT WINAPI IDirectDrawClipperImpl_IsClipListChanged(
 /*****************************************************************************
  * The VTable
  *****************************************************************************/
-const IDirectDrawClipperVtbl IDirectDrawClipper_Vtbl =
+static const struct IDirectDrawClipperVtbl ddraw_clipper_vtbl =
 {
     IDirectDrawClipperImpl_QueryInterface,
     IDirectDrawClipperImpl_AddRef,
@@ -310,3 +302,17 @@ const IDirectDrawClipperVtbl IDirectDrawClipper_Vtbl =
     IDirectDrawClipperImpl_SetClipList,
     IDirectDrawClipperImpl_SetHwnd
 };
+
+HRESULT ddraw_clipper_init(IDirectDrawClipperImpl *clipper)
+{
+    clipper->lpVtbl = &ddraw_clipper_vtbl;
+    clipper->ref = 1;
+    clipper->wineD3DClipper = pWineDirect3DCreateClipper();
+    if (!clipper->wineD3DClipper)
+    {
+        WARN("Failed to create wined3d clipper.\n");
+        return E_OUTOFMEMORY;
+    }
+
+    return DD_OK;
+}
index a7522f9..bef9cf0 100644 (file)
 #include "config.h"
 #include "wine/port.h"
 
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-#define NONAMELESSUNION
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
 #include "ddraw_private.h"
-#include "wine/debug.h"
 
 WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
-static BOOL IDirectDrawImpl_DDSD_Match(const DDSURFACEDESC2* requested, const DDSURFACEDESC2* provided);
-static HRESULT IDirectDrawImpl_AttachD3DDevice(IDirectDrawImpl *This, IDirectDrawSurfaceImpl *primary);
-static HRESULT IDirectDrawImpl_CreateNewSurface(IDirectDrawImpl *This, DDSURFACEDESC2 *pDDSD, IDirectDrawSurfaceImpl **ppSurf, UINT level);
-static HRESULT IDirectDrawImpl_CreateGDISwapChain(IDirectDrawImpl *This, IDirectDrawSurfaceImpl *primary);
-
 /* Device identifier. Don't relay it to WineD3D */
 static const DDDEVICEIDENTIFIER2 deviceidentifier =
 {
@@ -69,6 +46,26 @@ const struct wined3d_parent_ops ddraw_null_wined3d_parent_ops =
     ddraw_null_wined3d_object_destroyed,
 };
 
+static inline IDirectDrawImpl *ddraw_from_ddraw1(IDirectDraw *iface)
+{
+    return (IDirectDrawImpl *)((char*)iface - FIELD_OFFSET(IDirectDrawImpl, IDirectDraw_vtbl));
+}
+
+static inline IDirectDrawImpl *ddraw_from_ddraw2(IDirectDraw2 *iface)
+{
+    return (IDirectDrawImpl *)((char*)iface - FIELD_OFFSET(IDirectDrawImpl, IDirectDraw2_vtbl));
+}
+
+static inline IDirectDrawImpl *ddraw_from_ddraw3(IDirectDraw3 *iface)
+{
+    return (IDirectDrawImpl *)((char*)iface - FIELD_OFFSET(IDirectDrawImpl, IDirectDraw3_vtbl));
+}
+
+static inline IDirectDrawImpl *ddraw_from_ddraw4(IDirectDraw4 *iface)
+{
+    return (IDirectDrawImpl *)((char*)iface - FIELD_OFFSET(IDirectDrawImpl, IDirectDraw4_vtbl));
+}
+
 /*****************************************************************************
  * IUnknown Methods
  *****************************************************************************/
@@ -93,14 +90,11 @@ const struct wined3d_parent_ops ddraw_null_wined3d_parent_ops =
  *  E_NOINTERFACE if the requested interface wasn't found
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_QueryInterface(IDirectDraw7 *iface,
-                               REFIID refiid,
-                               void **obj)
+static HRESULT WINAPI ddraw7_QueryInterface(IDirectDraw7 *iface, REFIID refiid, void **obj)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
 
-    TRACE("(%p)->(%s,%p)\n", This, debugstr_guid(refiid), obj);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(refiid), obj);
 
     /* Can change surface impl type */
     EnterCriticalSection(&ddraw_cs);
@@ -220,6 +214,62 @@ IDirectDrawImpl_QueryInterface(IDirectDraw7 *iface,
     return S_OK;
 }
 
+static HRESULT WINAPI ddraw4_QueryInterface(IDirectDraw4 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw7_QueryInterface((IDirectDraw7 *)ddraw_from_ddraw4(iface), riid, object);
+}
+
+static HRESULT WINAPI ddraw3_QueryInterface(IDirectDraw3 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw7_QueryInterface((IDirectDraw7 *)ddraw_from_ddraw3(iface), riid, object);
+}
+
+static HRESULT WINAPI ddraw2_QueryInterface(IDirectDraw2 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw7_QueryInterface((IDirectDraw7 *)ddraw_from_ddraw2(iface), riid, object);
+}
+
+static HRESULT WINAPI ddraw1_QueryInterface(IDirectDraw *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw7_QueryInterface((IDirectDraw7 *)ddraw_from_ddraw1(iface), riid, object);
+}
+
+static HRESULT WINAPI d3d7_QueryInterface(IDirect3D7 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw7_QueryInterface((IDirectDraw7 *)ddraw_from_d3d7(iface), riid, object);
+}
+
+static HRESULT WINAPI d3d3_QueryInterface(IDirect3D3 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw7_QueryInterface((IDirectDraw7 *)ddraw_from_d3d3(iface), riid, object);
+}
+
+static HRESULT WINAPI d3d2_QueryInterface(IDirect3D2 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw7_QueryInterface((IDirectDraw7 *)ddraw_from_d3d2(iface), riid, object);
+}
+
+static HRESULT WINAPI d3d1_QueryInterface(IDirect3D *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw7_QueryInterface((IDirectDraw7 *)ddraw_from_d3d1(iface), riid, object);
+}
+
 /*****************************************************************************
  * IDirectDraw7::AddRef
  *
@@ -238,21 +288,96 @@ IDirectDrawImpl_QueryInterface(IDirectDraw7 *iface,
  * Returns: The new refcount
  *
  *****************************************************************************/
-static ULONG WINAPI
-IDirectDrawImpl_AddRef(IDirectDraw7 *iface)
+static ULONG WINAPI ddraw7_AddRef(IDirectDraw7 *iface)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref7);
 
-    TRACE("(%p) : incrementing IDirectDraw7 refcount from %u.\n", This, ref -1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     if(ref == 1) InterlockedIncrement(&This->numIfaces);
 
     return ref;
 }
 
+static ULONG WINAPI ddraw4_AddRef(IDirectDraw4 *iface)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw4(iface);
+    ULONG ref = InterlockedIncrement(&ddraw->ref4);
+
+    TRACE("%p increasing refcount to %u.\n", ddraw, ref);
+
+    if (ref == 1) InterlockedIncrement(&ddraw->numIfaces);
+
+    return ref;
+}
+
+static ULONG WINAPI ddraw3_AddRef(IDirectDraw3 *iface)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw3(iface);
+    ULONG ref = InterlockedIncrement(&ddraw->ref3);
+
+    TRACE("%p increasing refcount to %u.\n", ddraw, ref);
+
+    if (ref == 1) InterlockedIncrement(&ddraw->numIfaces);
+
+    return ref;
+}
+
+static ULONG WINAPI ddraw2_AddRef(IDirectDraw2 *iface)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw2(iface);
+    ULONG ref = InterlockedIncrement(&ddraw->ref2);
+
+    TRACE("%p increasing refcount to %u.\n", ddraw, ref);
+
+    if (ref == 1) InterlockedIncrement(&ddraw->numIfaces);
+
+    return ref;
+}
+
+static ULONG WINAPI ddraw1_AddRef(IDirectDraw *iface)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw1(iface);
+    ULONG ref = InterlockedIncrement(&ddraw->ref1);
+
+    TRACE("%p increasing refcount to %u.\n", ddraw, ref);
+
+    if (ref == 1) InterlockedIncrement(&ddraw->numIfaces);
+
+    return ref;
+}
+
+static ULONG WINAPI d3d7_AddRef(IDirect3D7 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_AddRef((IDirectDraw7 *)ddraw_from_d3d7(iface));
+}
+
+static ULONG WINAPI d3d3_AddRef(IDirect3D3 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw1_AddRef((IDirectDraw *)&ddraw_from_d3d3(iface)->IDirectDraw_vtbl);
+}
+
+static ULONG WINAPI d3d2_AddRef(IDirect3D2 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw1_AddRef((IDirectDraw *)&ddraw_from_d3d2(iface)->IDirectDraw_vtbl);
+}
+
+static ULONG WINAPI d3d1_AddRef(IDirect3D *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw1_AddRef((IDirectDraw *)&ddraw_from_d3d1(iface)->IDirectDraw_vtbl);
+}
+
 /*****************************************************************************
- * IDirectDrawImpl_Destroy
+ * ddraw_destroy
  *
  * Destroys a ddraw object if all refcounts are 0. This is to share code
  * between the IDirectDrawX::Release functions
@@ -261,8 +386,7 @@ IDirectDrawImpl_AddRef(IDirectDraw7 *iface)
  *  This: DirectDraw object to destroy
  *
  *****************************************************************************/
-void
-IDirectDrawImpl_Destroy(IDirectDrawImpl *This)
+static void ddraw_destroy(IDirectDrawImpl *This)
 {
     IDirectDraw7_SetCooperativeLevel((IDirectDraw7 *)This, NULL, DDSCL_NORMAL);
     IDirectDraw7_RestoreDisplayMode((IDirectDraw7 *)This);
@@ -275,9 +399,6 @@ IDirectDrawImpl_Destroy(IDirectDrawImpl *This)
         This->devicewindow = 0;
     }
 
-    /* Unregister the window class */
-    UnregisterClassA(This->classname, 0);
-
     EnterCriticalSection(&ddraw_cs);
     list_remove(&This->ddraw_list_entry);
     LeaveCriticalSection(&ddraw_cs);
@@ -297,23 +418,99 @@ IDirectDrawImpl_Destroy(IDirectDrawImpl *This)
  *
  * Returns: The new refcount
  *****************************************************************************/
-static ULONG WINAPI
-IDirectDrawImpl_Release(IDirectDraw7 *iface)
+static ULONG WINAPI ddraw7_Release(IDirectDraw7 *iface)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref7);
 
-    TRACE("(%p)->() decrementing IDirectDraw7 refcount from %u.\n", This, ref +1);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
-    if(ref == 0)
-    {
-        ULONG ifacecount = InterlockedDecrement(&This->numIfaces);
-        if(ifacecount == 0) IDirectDrawImpl_Destroy(This);
-    }
+    if (!ref && !InterlockedDecrement(&This->numIfaces))
+        ddraw_destroy(This);
+
+    return ref;
+}
+
+static ULONG WINAPI ddraw4_Release(IDirectDraw4 *iface)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw4(iface);
+    ULONG ref = InterlockedDecrement(&ddraw->ref4);
+
+    TRACE("%p decreasing refcount to %u.\n", ddraw, ref);
+
+    if (!ref && !InterlockedDecrement(&ddraw->numIfaces))
+        ddraw_destroy(ddraw);
+
+    return ref;
+}
+
+static ULONG WINAPI ddraw3_Release(IDirectDraw3 *iface)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw3(iface);
+    ULONG ref = InterlockedDecrement(&ddraw->ref3);
+
+    TRACE("%p decreasing refcount to %u.\n", ddraw, ref);
+
+    if (!ref && !InterlockedDecrement(&ddraw->numIfaces))
+        ddraw_destroy(ddraw);
+
+    return ref;
+}
+
+static ULONG WINAPI ddraw2_Release(IDirectDraw2 *iface)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw2(iface);
+    ULONG ref = InterlockedDecrement(&ddraw->ref2);
+
+    TRACE("%p decreasing refcount to %u.\n", ddraw, ref);
+
+    if (!ref && !InterlockedDecrement(&ddraw->numIfaces))
+        ddraw_destroy(ddraw);
+
+    return ref;
+}
+
+static ULONG WINAPI ddraw1_Release(IDirectDraw *iface)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw1(iface);
+    ULONG ref = InterlockedDecrement(&ddraw->ref1);
+
+    TRACE("%p decreasing refcount to %u.\n", ddraw, ref);
+
+    if (!ref && !InterlockedDecrement(&ddraw->numIfaces))
+        ddraw_destroy(ddraw);
 
     return ref;
 }
 
+static ULONG WINAPI d3d7_Release(IDirect3D7 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_Release((IDirectDraw7 *)ddraw_from_d3d7(iface));
+}
+
+static ULONG WINAPI d3d3_Release(IDirect3D3 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw1_Release((IDirectDraw *)&ddraw_from_d3d3(iface)->IDirectDraw_vtbl);
+}
+
+static ULONG WINAPI d3d2_Release(IDirect3D2 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw1_Release((IDirectDraw *)&ddraw_from_d3d2(iface)->IDirectDraw_vtbl);
+}
+
+static ULONG WINAPI d3d1_Release(IDirect3D *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw1_Release((IDirectDraw *)&ddraw_from_d3d1(iface)->IDirectDraw_vtbl);
+}
+
 /*****************************************************************************
  * IDirectDraw methods
  *****************************************************************************/
@@ -348,7 +545,7 @@ IDirectDrawImpl_Release(IDirectDraw7 *iface)
  *  DDSCL_SETDEVICEWINDOW: Sets a window specially used for rendering (I don't
  *  expect any difference to a normal window for wine)
  *  DDSCL_CREATEDEVICEWINDOW: Tells ddraw to create its own window for
- *  rendering (Possible test case: Half-life)
+ *  rendering (Possible test case: Half-Life)
  *
  * Unsure about these: DDSCL_FPUSETUP DDSCL_FPURESERVE
  *
@@ -362,15 +559,12 @@ IDirectDrawImpl_Release(IDirectDraw7 *iface)
  *   (Probably others too, have to investigate)
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_SetCooperativeLevel(IDirectDraw7 *iface,
-                                    HWND hwnd,
-                                    DWORD cooplevel)
+static HRESULT WINAPI ddraw7_SetCooperativeLevel(IDirectDraw7 *iface, HWND hwnd, DWORD cooplevel)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     HWND window;
 
-    TRACE("(%p)->(%p,%08x)\n",This,hwnd,cooplevel);
+    TRACE("iface %p, window %p, flags %#x.\n", iface, hwnd, cooplevel);
     DDRAW_dump_cooperativelevel(cooplevel);
 
     EnterCriticalSection(&ddraw_cs);
@@ -504,11 +698,15 @@ IDirectDrawImpl_SetCooperativeLevel(IDirectDraw7 *iface,
         /* Don't create a device window if a focus window is set */
         if( !(This->focuswindow) )
         {
-            HWND devicewindow = CreateWindowExA(0, This->classname, "DDraw device window",
-                                                WS_POPUP, 0, 0,
-                                                GetSystemMetrics(SM_CXSCREEN),
-                                                GetSystemMetrics(SM_CYSCREEN),
-                                                NULL, NULL, GetModuleHandleA(0), NULL);
+            HWND devicewindow = CreateWindowExA(0, DDRAW_WINDOW_CLASS_NAME, "DDraw device window",
+                    WS_POPUP, 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN),
+                    NULL, NULL, NULL, NULL);
+            if (!devicewindow)
+            {
+                ERR("Failed to create window, last error %#x.\n", GetLastError());
+                LeaveCriticalSection(&ddraw_cs);
+                return E_FAIL;
+            }
 
             ShowWindow(devicewindow, SW_SHOW);   /* Just to be sure */
             TRACE("(%p) Created a DDraw device window. HWND=%p\n", This, devicewindow);
@@ -539,35 +737,60 @@ IDirectDrawImpl_SetCooperativeLevel(IDirectDraw7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_SetCooperativeLevel(IDirectDraw4 *iface, HWND window, DWORD flags)
+{
+    TRACE("iface %p, window %p, flags %#x.\n", iface, window, flags);
+
+    return ddraw7_SetCooperativeLevel((IDirectDraw7 *)ddraw_from_ddraw4(iface), window, flags);
+}
+
+static HRESULT WINAPI ddraw3_SetCooperativeLevel(IDirectDraw3 *iface, HWND window, DWORD flags)
+{
+    TRACE("iface %p, window %p, flags %#x.\n", iface, window, flags);
+
+    return ddraw7_SetCooperativeLevel((IDirectDraw7 *)ddraw_from_ddraw3(iface), window, flags);
+}
+
+static HRESULT WINAPI ddraw2_SetCooperativeLevel(IDirectDraw2 *iface, HWND window, DWORD flags)
+{
+    TRACE("iface %p, window %p, flags %#x.\n", iface, window, flags);
+
+    return ddraw7_SetCooperativeLevel((IDirectDraw7 *)ddraw_from_ddraw2(iface), window, flags);
+}
+
+static HRESULT WINAPI ddraw1_SetCooperativeLevel(IDirectDraw *iface, HWND window, DWORD flags)
+{
+    TRACE("iface %p, window %p, flags %#x.\n", iface, window, flags);
+
+    return ddraw7_SetCooperativeLevel((IDirectDraw7 *)ddraw_from_ddraw1(iface), window, flags);
+}
+
 /*****************************************************************************
  *
  * Helper function for SetDisplayMode and RestoreDisplayMode
  *
  * Implements DirectDraw's SetDisplayMode, but ignores the value of
  * ForceRefreshRate, since it is already handled by
- * IDirectDrawImpl_SetDisplayMode.  RestoreDisplayMode can use this function
+ * ddraw7_SetDisplayMode.  RestoreDisplayMode can use this function
  * without worrying that ForceRefreshRate will override the refresh rate.  For
  * argument and return value documentation, see
- * IDirectDrawImpl_SetDisplayMode.
+ * ddraw7_SetDisplayMode.
  *
  *****************************************************************************/
-static HRESULT
-IDirectDrawImpl_SetDisplayModeNoOverride(IDirectDraw7 *iface,
-                                         DWORD Width,
-                                         DWORD Height,
-                                         DWORD BPP,
-                                         DWORD RefreshRate,
-                                         DWORD Flags)
+static HRESULT ddraw_set_display_mode(IDirectDraw7 *iface, DWORD Width, DWORD Height,
+        DWORD BPP, DWORD RefreshRate, DWORD Flags)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     WINED3DDISPLAYMODE Mode;
     HRESULT hr;
-    TRACE("(%p)->(%d,%d,%d,%d,%x): Relay!\n", This, Width, Height, BPP, RefreshRate, Flags);
+
+    TRACE("iface %p, width %u, height %u, bpp %u, refresh_rate %u, flags %#x.\n",
+            iface, Width, Height, BPP, RefreshRate, Flags);
 
     EnterCriticalSection(&ddraw_cs);
     if( !Width || !Height )
     {
-        ERR("Width=%d, Height=%d, what to do?\n", Width, Height);
+        ERR("Width %u, Height %u, what to do?\n", Width, Height);
         /* It looks like Need for Speed Porsche Unleashed expects DD_OK here */
         LeaveCriticalSection(&ddraw_cs);
         return DD_OK;
@@ -633,22 +856,57 @@ IDirectDrawImpl_SetDisplayModeNoOverride(IDirectDraw7 *iface,
  *  DD_OK on success
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_SetDisplayMode(IDirectDraw7 *iface,
-                               DWORD Width,
-                               DWORD Height,
-                               DWORD BPP,
-                               DWORD RefreshRate,
-                               DWORD Flags)
+static HRESULT WINAPI ddraw7_SetDisplayMode(IDirectDraw7 *iface, DWORD Width, DWORD Height,
+        DWORD BPP, DWORD RefreshRate, DWORD Flags)
 {
+    TRACE("iface %p, width %u, height %u, bpp %u, refresh_rate %u, flags %#x.\n",
+            iface, Width, Height, BPP, RefreshRate, Flags);
+
     if (force_refresh_rate != 0)
     {
-        TRACE("ForceRefreshRate overriding passed-in refresh rate (%d Hz) to %d Hz\n", RefreshRate, force_refresh_rate);
+        TRACE("ForceRefreshRate overriding passed-in refresh rate (%u Hz) to %u Hz\n",
+                RefreshRate, force_refresh_rate);
         RefreshRate = force_refresh_rate;
     }
 
-    return IDirectDrawImpl_SetDisplayModeNoOverride(iface, Width, Height, BPP,
-                                                    RefreshRate, Flags);
+    return ddraw_set_display_mode(iface, Width, Height, BPP, RefreshRate, Flags);
+}
+
+static HRESULT WINAPI ddraw4_SetDisplayMode(IDirectDraw4 *iface,
+        DWORD width, DWORD height, DWORD bpp, DWORD refresh_rate, DWORD flags)
+{
+    TRACE("iface %p, width %u, height %u, bpp %u, refresh_rate %u, flags %#x.\n",
+            iface, width, height, bpp, refresh_rate, flags);
+
+    return ddraw7_SetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw4(iface),
+            width, height, bpp, refresh_rate, flags);
+}
+
+static HRESULT WINAPI ddraw3_SetDisplayMode(IDirectDraw3 *iface,
+        DWORD width, DWORD height, DWORD bpp, DWORD refresh_rate, DWORD flags)
+{
+    TRACE("iface %p, width %u, height %u, bpp %u, refresh_rate %u, flags %#x.\n",
+            iface, width, height, bpp, refresh_rate, flags);
+
+    return ddraw7_SetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw3(iface),
+            width, height, bpp, refresh_rate, flags);
+}
+
+static HRESULT WINAPI ddraw2_SetDisplayMode(IDirectDraw2 *iface,
+        DWORD width, DWORD height, DWORD bpp, DWORD refresh_rate, DWORD flags)
+{
+    TRACE("iface %p, width %u, height %u, bpp %u, refresh_rate %u, flags %#x.\n",
+            iface, width, height, bpp, refresh_rate, flags);
+
+    return ddraw7_SetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw2(iface),
+            width, height, bpp, refresh_rate, flags);
+}
+
+static HRESULT WINAPI ddraw1_SetDisplayMode(IDirectDraw *iface, DWORD width, DWORD height, DWORD bpp)
+{
+    TRACE("iface %p, width %u, height %u, bpp %u.\n", iface, width, height, bpp);
+
+    return ddraw7_SetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw1(iface), width, height, bpp, 0, 0);
 }
 
 /*****************************************************************************
@@ -672,14 +930,41 @@ IDirectDrawImpl_SetDisplayMode(IDirectDraw7 *iface,
  *  DDERR_NOEXCLUSIVE mode if the device isn't in fullscreen mode
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_RestoreDisplayMode(IDirectDraw7 *iface)
+static HRESULT WINAPI ddraw7_RestoreDisplayMode(IDirectDraw7 *iface)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    TRACE("(%p)\n", This);
 
-    return IDirectDrawImpl_SetDisplayModeNoOverride(iface,
-            This->orig_width, This->orig_height, This->orig_bpp, 0, 0);
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_set_display_mode(iface, This->orig_width, This->orig_height, This->orig_bpp, 0, 0);
+}
+
+static HRESULT WINAPI ddraw4_RestoreDisplayMode(IDirectDraw4 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_RestoreDisplayMode((IDirectDraw7 *)ddraw_from_ddraw4(iface));
+}
+
+static HRESULT WINAPI ddraw3_RestoreDisplayMode(IDirectDraw3 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_RestoreDisplayMode((IDirectDraw7 *)ddraw_from_ddraw3(iface));
+}
+
+static HRESULT WINAPI ddraw2_RestoreDisplayMode(IDirectDraw2 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_RestoreDisplayMode((IDirectDraw7 *)ddraw_from_ddraw2(iface));
+}
+
+static HRESULT WINAPI ddraw1_RestoreDisplayMode(IDirectDraw *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_RestoreDisplayMode((IDirectDraw7 *)ddraw_from_ddraw1(iface));
 }
 
 /*****************************************************************************
@@ -697,10 +982,7 @@ IDirectDrawImpl_RestoreDisplayMode(IDirectDraw7 *iface)
  *  This implementation returns DD_OK only
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_GetCaps(IDirectDraw7 *iface,
-                        DDCAPS *DriverCaps,
-                        DDCAPS *HELCaps)
+static HRESULT WINAPI ddraw7_GetCaps(IDirectDraw7 *iface, DDCAPS *DriverCaps, DDCAPS *HELCaps)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     DDCAPS caps;
@@ -709,10 +991,12 @@ IDirectDrawImpl_GetCaps(IDirectDraw7 *iface,
     DDSCAPS2 ddscaps = {0, 0, 0, {0}};
     TRACE("(%p)->(%p,%p)\n", This, DriverCaps, HELCaps);
 
+    TRACE("iface %p, driver_caps %p, hel_caps %p.\n", iface, DriverCaps, HELCaps);
+
     /* One structure must be != NULL */
     if( (!DriverCaps) && (!HELCaps) )
     {
-        ERR("(%p) Invalid params to IDirectDrawImpl_GetCaps\n", This);
+        ERR("(%p) Invalid params to ddraw7_GetCaps\n", This);
         return DDERR_INVALIDPARAMS;
     }
 
@@ -785,6 +1069,34 @@ IDirectDrawImpl_GetCaps(IDirectDraw7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_GetCaps(IDirectDraw4 *iface, DDCAPS *driver_caps, DDCAPS *hel_caps)
+{
+    TRACE("iface %p, driver_caps %p, hel_caps %p.\n", iface, driver_caps, hel_caps);
+
+    return ddraw7_GetCaps((IDirectDraw7 *)ddraw_from_ddraw4(iface), driver_caps, hel_caps);
+}
+
+static HRESULT WINAPI ddraw3_GetCaps(IDirectDraw3 *iface, DDCAPS *driver_caps, DDCAPS *hel_caps)
+{
+    TRACE("iface %p, driver_caps %p, hel_caps %p.\n", iface, driver_caps, hel_caps);
+
+    return ddraw7_GetCaps((IDirectDraw7 *)ddraw_from_ddraw3(iface), driver_caps, hel_caps);
+}
+
+static HRESULT WINAPI ddraw2_GetCaps(IDirectDraw2 *iface, DDCAPS *driver_caps, DDCAPS *hel_caps)
+{
+    TRACE("iface %p, driver_caps %p, hel_caps %p.\n", iface, driver_caps, hel_caps);
+
+    return ddraw7_GetCaps((IDirectDraw7 *)ddraw_from_ddraw2(iface), driver_caps, hel_caps);
+}
+
+static HRESULT WINAPI ddraw1_GetCaps(IDirectDraw *iface, DDCAPS *driver_caps, DDCAPS *hel_caps)
+{
+    TRACE("iface %p, driver_caps %p, hel_caps %p.\n", iface, driver_caps, hel_caps);
+
+    return ddraw7_GetCaps((IDirectDraw7 *)ddraw_from_ddraw1(iface), driver_caps, hel_caps);
+}
+
 /*****************************************************************************
  * IDirectDraw7::Compact
  *
@@ -794,15 +1106,41 @@ IDirectDrawImpl_GetCaps(IDirectDraw7 *iface,
  *  DD_OK, but this is unchecked
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_Compact(IDirectDraw7 *iface)
+static HRESULT WINAPI ddraw7_Compact(IDirectDraw7 *iface)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    TRACE("(%p)\n", This);
+    TRACE("iface %p.\n", iface);
 
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_Compact(IDirectDraw4 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_Compact((IDirectDraw7 *)ddraw_from_ddraw4(iface));
+}
+
+static HRESULT WINAPI ddraw3_Compact(IDirectDraw3 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_Compact((IDirectDraw7 *)ddraw_from_ddraw3(iface));
+}
+
+static HRESULT WINAPI ddraw2_Compact(IDirectDraw2 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_Compact((IDirectDraw7 *)ddraw_from_ddraw2(iface));
+}
+
+static HRESULT WINAPI ddraw1_Compact(IDirectDraw *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_Compact((IDirectDraw7 *)ddraw_from_ddraw1(iface));
+}
+
 /*****************************************************************************
  * IDirectDraw7::GetDisplayMode
  *
@@ -817,15 +1155,14 @@ IDirectDrawImpl_Compact(IDirectDraw7 *iface)
  *  DD_OK
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_GetDisplayMode(IDirectDraw7 *iface,
-                               DDSURFACEDESC2 *DDSD)
+static HRESULT WINAPI ddraw7_GetDisplayMode(IDirectDraw7 *iface, DDSURFACEDESC2 *DDSD)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     HRESULT hr;
     WINED3DDISPLAYMODE Mode;
     DWORD Size;
-    TRACE("(%p)->(%p): Relay\n", This, DDSD);
+
+    TRACE("iface %p, surface_desc %p.\n", iface, DDSD);
 
     EnterCriticalSection(&ddraw_cs);
     /* This seems sane */
@@ -871,14 +1208,42 @@ IDirectDrawImpl_GetDisplayMode(IDirectDraw7 *iface,
     return DD_OK;
 }
 
-/*****************************************************************************
- * IDirectDraw7::GetFourCCCodes
- *
- * Returns an array of supported FourCC codes.
- *
- * Exists in Version 1, 2, 4 and 7
- *
- * Params:
+static HRESULT WINAPI ddraw4_GetDisplayMode(IDirectDraw4 *iface, DDSURFACEDESC2 *surface_desc)
+{
+    TRACE("iface %p, surface_desc %p.\n", iface, surface_desc);
+
+    return ddraw7_GetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw4(iface), surface_desc);
+}
+
+static HRESULT WINAPI ddraw3_GetDisplayMode(IDirectDraw3 *iface, DDSURFACEDESC *surface_desc)
+{
+    TRACE("iface %p, surface_desc %p.\n", iface, surface_desc);
+
+    return ddraw7_GetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw3(iface), (DDSURFACEDESC2 *)surface_desc);
+}
+
+static HRESULT WINAPI ddraw2_GetDisplayMode(IDirectDraw2 *iface, DDSURFACEDESC *surface_desc)
+{
+    TRACE("iface %p, surface_desc %p.\n", iface, surface_desc);
+
+    return ddraw7_GetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw2(iface), (DDSURFACEDESC2 *)surface_desc);
+}
+
+static HRESULT WINAPI ddraw1_GetDisplayMode(IDirectDraw *iface, DDSURFACEDESC *surface_desc)
+{
+    TRACE("iface %p, surface_desc %p.\n", iface, surface_desc);
+
+    return ddraw7_GetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw1(iface), (DDSURFACEDESC2 *)surface_desc);
+}
+
+/*****************************************************************************
+ * IDirectDraw7::GetFourCCCodes
+ *
+ * Returns an array of supported FourCC codes.
+ *
+ * Exists in Version 1, 2, 4 and 7
+ *
+ * Params:
  *  NumCodes: Contains the number of Codes that Codes can carry. Returns the number
  *            of enumerated codes
  *  Codes: Pointer to an array of DWORDs where the supported codes are written
@@ -888,12 +1253,11 @@ IDirectDrawImpl_GetDisplayMode(IDirectDraw7 *iface,
  *  Always returns DD_OK, as it's a stub for now
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_GetFourCCCodes(IDirectDraw7 *iface,
-                               DWORD *NumCodes, DWORD *Codes)
+static HRESULT WINAPI ddraw7_GetFourCCCodes(IDirectDraw7 *iface, DWORD *NumCodes, DWORD *Codes)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    WINED3DFORMAT formats[] = {
+    static const enum wined3d_format_id formats[] =
+    {
         WINED3DFMT_YUY2, WINED3DFMT_UYVY, WINED3DFMT_YV12,
         WINED3DFMT_DXT1, WINED3DFMT_DXT2, WINED3DFMT_DXT3, WINED3DFMT_DXT4, WINED3DFMT_DXT5,
         WINED3DFMT_ATI2N, WINED3DFMT_NVHU, WINED3DFMT_NVHS
@@ -902,7 +1266,8 @@ IDirectDrawImpl_GetFourCCCodes(IDirectDraw7 *iface,
     HRESULT hr;
     WINED3DDISPLAYMODE d3ddm;
     WINED3DSURFTYPE type = This->ImplType;
-    TRACE("(%p)->(%p, %p)\n", This, NumCodes, Codes);
+
+    TRACE("iface %p, codes_count %p, codes %p.\n", iface, NumCodes, Codes);
 
     IWineD3DDevice_GetDisplayMode(This->wineD3DDevice,
                                   0 /* swapchain 0 */,
@@ -936,6 +1301,34 @@ IDirectDrawImpl_GetFourCCCodes(IDirectDraw7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_GetFourCCCodes(IDirectDraw4 *iface, DWORD *codes_count, DWORD *codes)
+{
+    TRACE("iface %p, codes_count %p, codes %p.\n", iface, codes_count, codes);
+
+    return ddraw7_GetFourCCCodes((IDirectDraw7 *)ddraw_from_ddraw4(iface), codes_count, codes);
+}
+
+static HRESULT WINAPI ddraw3_GetFourCCCodes(IDirectDraw3 *iface, DWORD *codes_count, DWORD *codes)
+{
+    TRACE("iface %p, codes_count %p, codes %p.\n", iface, codes_count, codes);
+
+    return ddraw7_GetFourCCCodes((IDirectDraw7 *)ddraw_from_ddraw3(iface), codes_count, codes);
+}
+
+static HRESULT WINAPI ddraw2_GetFourCCCodes(IDirectDraw2 *iface, DWORD *codes_count, DWORD *codes)
+{
+    TRACE("iface %p, codes_count %p, codes %p.\n", iface, codes_count, codes);
+
+    return ddraw7_GetFourCCCodes((IDirectDraw7 *)ddraw_from_ddraw2(iface), codes_count, codes);
+}
+
+static HRESULT WINAPI ddraw1_GetFourCCCodes(IDirectDraw *iface, DWORD *codes_count, DWORD *codes)
+{
+    TRACE("iface %p, codes_count %p, codes %p.\n", iface, codes_count, codes);
+
+    return ddraw7_GetFourCCCodes((IDirectDraw7 *)ddraw_from_ddraw1(iface), codes_count, codes);
+}
+
 /*****************************************************************************
  * IDirectDraw7::GetMonitorFrequency
  *
@@ -950,12 +1343,9 @@ IDirectDrawImpl_GetFourCCCodes(IDirectDraw7 *iface,
  *  Always returns DD_OK
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_GetMonitorFrequency(IDirectDraw7 *iface,
-                                    DWORD *Freq)
+static HRESULT WINAPI ddraw7_GetMonitorFrequency(IDirectDraw7 *iface, DWORD *Freq)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    TRACE("(%p)->(%p)\n", This, Freq);
+    FIXME("iface %p, frequency %p stub!\n", iface, Freq);
 
     /* Ideally this should be in WineD3D, as it concerns the screen setup,
      * but for now this should make the games happy
@@ -964,6 +1354,34 @@ IDirectDrawImpl_GetMonitorFrequency(IDirectDraw7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_GetMonitorFrequency(IDirectDraw4 *iface, DWORD *frequency)
+{
+    TRACE("iface %p, frequency %p.\n", iface, frequency);
+
+    return ddraw7_GetMonitorFrequency((IDirectDraw7 *)ddraw_from_ddraw4(iface), frequency);
+}
+
+static HRESULT WINAPI ddraw3_GetMonitorFrequency(IDirectDraw3 *iface, DWORD *frequency)
+{
+    TRACE("iface %p, frequency %p.\n", iface, frequency);
+
+    return ddraw7_GetMonitorFrequency((IDirectDraw7 *)ddraw_from_ddraw3(iface), frequency);
+}
+
+static HRESULT WINAPI ddraw2_GetMonitorFrequency(IDirectDraw2 *iface, DWORD *frequency)
+{
+    TRACE("iface %p, frequency %p.\n", iface, frequency);
+
+    return ddraw7_GetMonitorFrequency((IDirectDraw7 *)ddraw_from_ddraw2(iface), frequency);
+}
+
+static HRESULT WINAPI ddraw1_GetMonitorFrequency(IDirectDraw *iface, DWORD *frequency)
+{
+    TRACE("iface %p, frequency %p.\n", iface, frequency);
+
+    return ddraw7_GetMonitorFrequency((IDirectDraw7 *)ddraw_from_ddraw1(iface), frequency);
+}
+
 /*****************************************************************************
  * IDirectDraw7::GetVerticalBlankStatus
  *
@@ -978,12 +1396,11 @@ IDirectDrawImpl_GetMonitorFrequency(IDirectDraw7 *iface,
  *  DDERR_INVALIDPARAMS if status is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_GetVerticalBlankStatus(IDirectDraw7 *iface,
-                                       BOOL *status)
+static HRESULT WINAPI ddraw7_GetVerticalBlankStatus(IDirectDraw7 *iface, BOOL *status)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    TRACE("(%p)->(%p)\n", This, status);
+
+    TRACE("iface %p, status %p.\n", iface, status);
 
     /* This looks sane, the MSDN suggests it too */
     EnterCriticalSection(&ddraw_cs);
@@ -999,6 +1416,34 @@ IDirectDrawImpl_GetVerticalBlankStatus(IDirectDraw7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_GetVerticalBlankStatus(IDirectDraw4 *iface, BOOL *status)
+{
+    TRACE("iface %p, status %p.\n", iface, status);
+
+    return ddraw7_GetVerticalBlankStatus((IDirectDraw7 *)ddraw_from_ddraw4(iface), status);
+}
+
+static HRESULT WINAPI ddraw3_GetVerticalBlankStatus(IDirectDraw3 *iface, BOOL *status)
+{
+    TRACE("iface %p, status %p.\n", iface, status);
+
+    return ddraw7_GetVerticalBlankStatus((IDirectDraw7 *)ddraw_from_ddraw3(iface), status);
+}
+
+static HRESULT WINAPI ddraw2_GetVerticalBlankStatus(IDirectDraw2 *iface, BOOL *status)
+{
+    TRACE("iface %p, status %p.\n", iface, status);
+
+    return ddraw7_GetVerticalBlankStatus((IDirectDraw7 *)ddraw_from_ddraw2(iface), status);
+}
+
+static HRESULT WINAPI ddraw1_GetVerticalBlankStatus(IDirectDraw *iface, BOOL *status)
+{
+    TRACE("iface %p, status %p.\n", iface, status);
+
+    return ddraw7_GetVerticalBlankStatus((IDirectDraw7 *)ddraw_from_ddraw1(iface), status);
+}
+
 /*****************************************************************************
  * IDirectDraw7::GetAvailableVidMem
  *
@@ -1014,11 +1459,11 @@ IDirectDrawImpl_GetVerticalBlankStatus(IDirectDraw7 *iface,
  *  DDERR_INVALIDPARAMS of free and total are NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_GetAvailableVidMem(IDirectDraw7 *iface, DDSCAPS2 *Caps, DWORD *total, DWORD *free)
+static HRESULT WINAPI ddraw7_GetAvailableVidMem(IDirectDraw7 *iface, DDSCAPS2 *Caps, DWORD *total, DWORD *free)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    TRACE("(%p)->(%p, %p, %p)\n", This, Caps, total, free);
+
+    TRACE("iface %p, caps %p, total %p, free %p.\n", iface, Caps, total, free);
 
     if(TRACE_ON(ddraw))
     {
@@ -1045,6 +1490,36 @@ IDirectDrawImpl_GetAvailableVidMem(IDirectDraw7 *iface, DDSCAPS2 *Caps, DWORD *t
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_GetAvailableVidMem(IDirectDraw4 *iface,
+        DDSCAPS2 *caps, DWORD *total, DWORD *free)
+{
+    TRACE("iface %p, caps %p, total %p, free %p.\n", iface, caps, total, free);
+
+    return ddraw7_GetAvailableVidMem((IDirectDraw7 *)ddraw_from_ddraw4(iface), caps, total, free);
+}
+
+static HRESULT WINAPI ddraw3_GetAvailableVidMem(IDirectDraw3 *iface,
+        DDSCAPS *caps, DWORD *total, DWORD *free)
+{
+    DDSCAPS2 caps2;
+
+    TRACE("iface %p, caps %p, total %p, free %p.\n", iface, caps, total, free);
+
+    DDRAW_Convert_DDSCAPS_1_To_2(caps, &caps2);
+    return ddraw7_GetAvailableVidMem((IDirectDraw7 *)ddraw_from_ddraw3(iface), &caps2, total, free);
+}
+
+static HRESULT WINAPI ddraw2_GetAvailableVidMem(IDirectDraw2 *iface,
+        DDSCAPS *caps, DWORD *total, DWORD *free)
+{
+    DDSCAPS2 caps2;
+
+    TRACE("iface %p, caps %p, total %p, free %p.\n", iface, caps, total, free);
+
+    DDRAW_Convert_DDSCAPS_1_To_2(caps, &caps2);
+    return ddraw7_GetAvailableVidMem((IDirectDraw7 *)ddraw_from_ddraw2(iface), &caps2, total, free);
+}
+
 /*****************************************************************************
  * IDirectDraw7::Initialize
  *
@@ -1059,12 +1534,11 @@ IDirectDrawImpl_GetAvailableVidMem(IDirectDraw7 *iface, DDSCAPS2 *Caps, DWORD *t
  *  DDERR_ALREADYINITIALIZED on repeated calls
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_Initialize(IDirectDraw7 *iface,
-                           GUID *Guid)
+static HRESULT WINAPI ddraw7_Initialize(IDirectDraw7 *iface, GUID *Guid)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    TRACE("(%p)->(%s): No-op\n", This, debugstr_guid(Guid));
+
+    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(Guid));
 
     if(This->initialized)
     {
@@ -1076,6 +1550,41 @@ IDirectDrawImpl_Initialize(IDirectDraw7 *iface,
     }
 }
 
+static HRESULT WINAPI ddraw4_Initialize(IDirectDraw4 *iface, GUID *guid)
+{
+    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(guid));
+
+    return ddraw7_Initialize((IDirectDraw7 *)ddraw_from_ddraw4(iface), guid);
+}
+
+static HRESULT WINAPI ddraw3_Initialize(IDirectDraw3 *iface, GUID *guid)
+{
+    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(guid));
+
+    return ddraw7_Initialize((IDirectDraw7 *)ddraw_from_ddraw3(iface), guid);
+}
+
+static HRESULT WINAPI ddraw2_Initialize(IDirectDraw2 *iface, GUID *guid)
+{
+    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(guid));
+
+    return ddraw7_Initialize((IDirectDraw7 *)ddraw_from_ddraw2(iface), guid);
+}
+
+static HRESULT WINAPI ddraw1_Initialize(IDirectDraw *iface, GUID *guid)
+{
+    TRACE("iface %p, guid %s.\n", iface, debugstr_guid(guid));
+
+    return ddraw7_Initialize((IDirectDraw7 *)ddraw_from_ddraw1(iface), guid);
+}
+
+static HRESULT WINAPI d3d1_Initialize(IDirect3D *iface, REFIID riid)
+{
+    TRACE("iface %p, riid %s.\n", iface, debugstr_guid(riid));
+
+    return D3D_OK;
+}
+
 /*****************************************************************************
  * IDirectDraw7::FlipToGDISurface
  *
@@ -1089,15 +1598,41 @@ IDirectDrawImpl_Initialize(IDirectDraw7 *iface,
  *  Always returns DD_OK
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_FlipToGDISurface(IDirectDraw7 *iface)
+static HRESULT WINAPI ddraw7_FlipToGDISurface(IDirectDraw7 *iface)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    TRACE("(%p)\n", This);
+    FIXME("iface %p stub!\n", iface);
 
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_FlipToGDISurface(IDirectDraw4 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_FlipToGDISurface((IDirectDraw7 *)ddraw_from_ddraw4(iface));
+}
+
+static HRESULT WINAPI ddraw3_FlipToGDISurface(IDirectDraw3 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_FlipToGDISurface((IDirectDraw7 *)ddraw_from_ddraw3(iface));
+}
+
+static HRESULT WINAPI ddraw2_FlipToGDISurface(IDirectDraw2 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_FlipToGDISurface((IDirectDraw7 *)ddraw_from_ddraw2(iface));
+}
+
+static HRESULT WINAPI ddraw1_FlipToGDISurface(IDirectDraw *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_FlipToGDISurface((IDirectDraw7 *)ddraw_from_ddraw1(iface));
+}
+
 /*****************************************************************************
  * IDirectDraw7::WaitForVerticalBlank
  *
@@ -1115,18 +1650,16 @@ IDirectDrawImpl_FlipToGDISurface(IDirectDraw7 *iface)
  *  Always returns DD_OK
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_WaitForVerticalBlank(IDirectDraw7 *iface,
-                                     DWORD Flags,
-                                     HANDLE h)
+static HRESULT WINAPI ddraw7_WaitForVerticalBlank(IDirectDraw7 *iface, DWORD Flags, HANDLE event)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    static BOOL hide = FALSE;
+    static BOOL hide;
+
+    TRACE("iface %p, flags %#x, event %p.\n", iface, Flags, event);
 
     /* This function is called often, so print the fixme only once */
     if(!hide)
     {
-        FIXME("(%p)->(%x,%p): Stub\n", This, Flags, h);
+        FIXME("iface %p, flags %#x, event %p stub!\n", iface, Flags, event);
         hide = TRUE;
     }
 
@@ -1137,6 +1670,34 @@ IDirectDrawImpl_WaitForVerticalBlank(IDirectDraw7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_WaitForVerticalBlank(IDirectDraw4 *iface, DWORD flags, HANDLE event)
+{
+    TRACE("iface %p, flags %#x, event %p.\n", iface, flags, event);
+
+    return ddraw7_WaitForVerticalBlank((IDirectDraw7 *)ddraw_from_ddraw4(iface), flags, event);
+}
+
+static HRESULT WINAPI ddraw3_WaitForVerticalBlank(IDirectDraw3 *iface, DWORD flags, HANDLE event)
+{
+    TRACE("iface %p, flags %#x, event %p.\n", iface, flags, event);
+
+    return ddraw7_WaitForVerticalBlank((IDirectDraw7 *)ddraw_from_ddraw3(iface), flags, event);
+}
+
+static HRESULT WINAPI ddraw2_WaitForVerticalBlank(IDirectDraw2 *iface, DWORD flags, HANDLE event)
+{
+    TRACE("iface %p, flags %#x, event %p.\n", iface, flags, event);
+
+    return ddraw7_WaitForVerticalBlank((IDirectDraw7 *)ddraw_from_ddraw2(iface), flags, event);
+}
+
+static HRESULT WINAPI ddraw1_WaitForVerticalBlank(IDirectDraw *iface, DWORD flags, HANDLE event)
+{
+    TRACE("iface %p, flags %#x, event %p.\n", iface, flags, event);
+
+    return ddraw7_WaitForVerticalBlank((IDirectDraw7 *)ddraw_from_ddraw1(iface), flags, event);
+}
+
 /*****************************************************************************
  * IDirectDraw7::GetScanLine
  *
@@ -1149,17 +1710,19 @@ IDirectDrawImpl_WaitForVerticalBlank(IDirectDraw7 *iface,
  *  Always returns DD_OK
  *
  *****************************************************************************/
-static HRESULT WINAPI IDirectDrawImpl_GetScanLine(IDirectDraw7 *iface, DWORD *Scanline)
+static HRESULT WINAPI ddraw7_GetScanLine(IDirectDraw7 *iface, DWORD *Scanline)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     static BOOL hide = FALSE;
     WINED3DDISPLAYMODE Mode;
 
+    TRACE("iface %p, line %p.\n", iface, Scanline);
+
     /* This function is called often, so print the fixme only once */
     EnterCriticalSection(&ddraw_cs);
     if(!hide)
     {
-        FIXME("(%p)->(%p): Semi-Stub\n", This, Scanline);
+        FIXME("iface %p, line %p partial stub!\n", iface, Scanline);
         hide = TRUE;
     }
 
@@ -1178,6 +1741,34 @@ static HRESULT WINAPI IDirectDrawImpl_GetScanLine(IDirectDraw7 *iface, DWORD *Sc
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_GetScanLine(IDirectDraw4 *iface, DWORD *line)
+{
+    TRACE("iface %p, line %p.\n", iface, line);
+
+    return ddraw7_GetScanLine((IDirectDraw7 *)ddraw_from_ddraw4(iface), line);
+}
+
+static HRESULT WINAPI ddraw3_GetScanLine(IDirectDraw3 *iface, DWORD *line)
+{
+    TRACE("iface %p, line %p.\n", iface, line);
+
+    return ddraw7_GetScanLine((IDirectDraw7 *)ddraw_from_ddraw3(iface), line);
+}
+
+static HRESULT WINAPI ddraw2_GetScanLine(IDirectDraw2 *iface, DWORD *line)
+{
+    TRACE("iface %p, line %p.\n", iface, line);
+
+    return ddraw7_GetScanLine((IDirectDraw7 *)ddraw_from_ddraw2(iface), line);
+}
+
+static HRESULT WINAPI ddraw1_GetScanLine(IDirectDraw *iface, DWORD *line)
+{
+    TRACE("iface %p, line %p.\n", iface, line);
+
+    return ddraw7_GetScanLine((IDirectDraw7 *)ddraw_from_ddraw1(iface), line);
+}
+
 /*****************************************************************************
  * IDirectDraw7::TestCooperativeLevel
  *
@@ -1190,14 +1781,20 @@ static HRESULT WINAPI IDirectDrawImpl_GetScanLine(IDirectDraw7 *iface, DWORD *Sc
  *  if the state is not correct(See below)
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_TestCooperativeLevel(IDirectDraw7 *iface)
+static HRESULT WINAPI ddraw7_TestCooperativeLevel(IDirectDraw7 *iface)
 {
     TRACE("iface %p.\n", iface);
 
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_TestCooperativeLevel(IDirectDraw4 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_TestCooperativeLevel((IDirectDraw7 *)ddraw_from_ddraw4(iface));
+}
+
 /*****************************************************************************
  * IDirectDraw7::GetGDISurface
  *
@@ -1212,16 +1809,15 @@ IDirectDrawImpl_TestCooperativeLevel(IDirectDraw7 *iface)
  *  DDERR_NOTFOUND if the GDI surface wasn't found
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_GetGDISurface(IDirectDraw7 *iface,
-                              IDirectDrawSurface7 **GDISurface)
+static HRESULT WINAPI ddraw7_GetGDISurface(IDirectDraw7 *iface, IDirectDrawSurface7 **GDISurface)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     IWineD3DSurface *Surf;
     IDirectDrawSurface7 *ddsurf;
     HRESULT hr;
     DDSCAPS2 ddsCaps;
-    TRACE("(%p)->(%p)\n", This, GDISurface);
+
+    TRACE("iface %p, surface %p.\n", iface, GDISurface);
 
     /* Get the back buffer from the wineD3DDevice and search its
      * attached surfaces for the front buffer
@@ -1241,13 +1837,9 @@ IDirectDrawImpl_GetGDISurface(IDirectDraw7 *iface,
         return DDERR_NOTFOUND;
     }
 
-    /* GetBackBuffer AddRef()ed the surface, release it */
+    ddsurf = IWineD3DSurface_GetParent(Surf);
     IWineD3DSurface_Release(Surf);
 
-    IWineD3DSurface_GetParent(Surf,
-                              (IUnknown **) &ddsurf);
-    IDirectDrawSurface7_Release(ddsurf);  /* For the GetParent */
-
     /* Find the front buffer */
     ddsCaps.dwCaps = DDSCAPS_FRONTBUFFER;
     hr = IDirectDrawSurface7_GetAttachedSurface(ddsurf,
@@ -1263,6 +1855,69 @@ IDirectDrawImpl_GetGDISurface(IDirectDraw7 *iface,
     return hr;
 }
 
+static HRESULT WINAPI ddraw4_GetGDISurface(IDirectDraw4 *iface, IDirectDrawSurface4 **surface)
+{
+    TRACE("iface %p, surface %p.\n", iface, surface);
+
+    return ddraw7_GetGDISurface((IDirectDraw7 *)ddraw_from_ddraw4(iface), (IDirectDrawSurface7 **)surface);
+}
+
+static HRESULT WINAPI ddraw3_GetGDISurface(IDirectDraw3 *iface, IDirectDrawSurface **surface)
+{
+    IDirectDrawSurface7 *surface7;
+    HRESULT hr;
+
+    TRACE("iface %p, surface %p.\n", iface, surface);
+
+    hr = ddraw7_GetGDISurface((IDirectDraw7 *)ddraw_from_ddraw3(iface), &surface7);
+    *surface = surface7 ? (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)surface7)->IDirectDrawSurface3_vtbl : NULL;
+
+    return hr;
+}
+
+static HRESULT WINAPI ddraw2_GetGDISurface(IDirectDraw2 *iface, IDirectDrawSurface **surface)
+{
+    IDirectDrawSurface7 *surface7;
+    HRESULT hr;
+
+    TRACE("iface %p, surface %p.\n", iface, surface);
+
+    hr = ddraw7_GetGDISurface((IDirectDraw7 *)ddraw_from_ddraw2(iface), &surface7);
+    *surface = surface7 ? (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)surface7)->IDirectDrawSurface3_vtbl : NULL;
+
+    return hr;
+}
+
+static HRESULT WINAPI ddraw1_GetGDISurface(IDirectDraw *iface, IDirectDrawSurface **surface)
+{
+    IDirectDrawSurface7 *surface7;
+    HRESULT hr;
+
+    TRACE("iface %p, surface %p.\n", iface, surface);
+
+    hr = ddraw7_GetGDISurface((IDirectDraw7 *)ddraw_from_ddraw1(iface), &surface7);
+    *surface = surface7 ? (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)surface7)->IDirectDrawSurface3_vtbl : NULL;
+
+    return hr;
+}
+
+struct displaymodescallback_context
+{
+    LPDDENUMMODESCALLBACK func;
+    void *context;
+};
+
+static HRESULT CALLBACK EnumDisplayModesCallbackThunk(DDSURFACEDESC2 *surface_desc, void *context)
+{
+    struct displaymodescallback_context *cbcontext = context;
+    DDSURFACEDESC desc;
+
+    memcpy(&desc, surface_desc, sizeof(desc));
+    desc.dwSize = sizeof(desc);
+
+    return cbcontext->func(&desc, cbcontext->context);
+}
+
 /*****************************************************************************
  * IDirectDraw7::EnumDisplayModes
  *
@@ -1280,29 +1935,26 @@ IDirectDrawImpl_GetGDISurface(IDirectDraw7 *iface,
  *  DDERR_INVALIDPARAMS if the callback wasn't set
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_EnumDisplayModes(IDirectDraw7 *iface,
-                                 DWORD Flags,
-                                 DDSURFACEDESC2 *DDSD,
-                                 void *Context,
-                                 LPDDENUMMODESCALLBACK2 cb)
+static HRESULT WINAPI ddraw7_EnumDisplayModes(IDirectDraw7 *iface, DWORD Flags,
+        DDSURFACEDESC2 *DDSD, void *Context, LPDDENUMMODESCALLBACK2 cb)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     unsigned int modenum, fmt;
-    WINED3DFORMAT pixelformat = WINED3DFMT_UNKNOWN;
+    enum wined3d_format_id pixelformat = WINED3DFMT_UNKNOWN;
     WINED3DDISPLAYMODE mode;
     DDSURFACEDESC2 callback_sd;
     WINED3DDISPLAYMODE *enum_modes = NULL;
     unsigned enum_mode_count = 0, enum_mode_array_size = 0;
 
-    WINED3DFORMAT checkFormatList[] =
+    static const enum wined3d_format_id checkFormatList[] =
     {
         WINED3DFMT_B8G8R8X8_UNORM,
         WINED3DFMT_B5G6R5_UNORM,
         WINED3DFMT_P8_UINT,
     };
 
-    TRACE("(%p)->(%p,%p,%p): Relay\n", This, DDSD, Context, cb);
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, Flags, DDSD, Context, cb);
 
     EnterCriticalSection(&ddraw_cs);
     /* This looks sane */
@@ -1434,6 +2086,61 @@ IDirectDrawImpl_EnumDisplayModes(IDirectDraw7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_EnumDisplayModes(IDirectDraw4 *iface, DWORD flags,
+        DDSURFACEDESC2 *surface_desc, void *context, LPDDENUMMODESCALLBACK2 callback)
+{
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, flags, surface_desc, context, callback);
+
+    return ddraw7_EnumDisplayModes((IDirectDraw7 *)ddraw_from_ddraw4(iface), flags,
+            surface_desc, context, callback);
+}
+
+static HRESULT WINAPI ddraw3_EnumDisplayModes(IDirectDraw3 *iface, DWORD flags,
+        DDSURFACEDESC *surface_desc, void *context, LPDDENUMMODESCALLBACK callback)
+{
+    struct displaymodescallback_context cbcontext;
+
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, flags, surface_desc, context, callback);
+
+    cbcontext.func = callback;
+    cbcontext.context = context;
+
+    return ddraw7_EnumDisplayModes((IDirectDraw7 *)ddraw_from_ddraw3(iface), flags,
+            (DDSURFACEDESC2 *)surface_desc, &cbcontext, EnumDisplayModesCallbackThunk);
+}
+
+static HRESULT WINAPI ddraw2_EnumDisplayModes(IDirectDraw2 *iface, DWORD flags,
+        DDSURFACEDESC *surface_desc, void *context, LPDDENUMMODESCALLBACK callback)
+{
+    struct displaymodescallback_context cbcontext;
+
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, flags, surface_desc, context, callback);
+
+    cbcontext.func = callback;
+    cbcontext.context = context;
+
+    return ddraw7_EnumDisplayModes((IDirectDraw7 *)ddraw_from_ddraw2(iface), flags,
+            (DDSURFACEDESC2 *)surface_desc, &cbcontext, EnumDisplayModesCallbackThunk);
+}
+
+static HRESULT WINAPI ddraw1_EnumDisplayModes(IDirectDraw *iface, DWORD flags,
+        DDSURFACEDESC *surface_desc, void *context, LPDDENUMMODESCALLBACK callback)
+{
+    struct displaymodescallback_context cbcontext;
+
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, flags, surface_desc, context, callback);
+
+    cbcontext.func = callback;
+    cbcontext.context = context;
+
+    return ddraw7_EnumDisplayModes((IDirectDraw7 *)ddraw_from_ddraw1(iface), flags,
+            (DDSURFACEDESC2 *)surface_desc, &cbcontext, EnumDisplayModesCallbackThunk);
+}
+
 /*****************************************************************************
  * IDirectDraw7::EvaluateMode
  *
@@ -1450,13 +2157,9 @@ IDirectDrawImpl_EnumDisplayModes(IDirectDraw7 *iface,
  *  This implementation always DD_OK, because it's a stub
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_EvaluateMode(IDirectDraw7 *iface,
-                             DWORD Flags,
-                             DWORD *Timeout)
+static HRESULT WINAPI ddraw7_EvaluateMode(IDirectDraw7 *iface, DWORD Flags, DWORD *Timeout)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    FIXME("(%p)->(%d,%p): Stub!\n", This, Flags, Timeout);
+    FIXME("iface %p, flags %#x, timeout %p stub!\n", iface, Flags, Timeout);
 
     /* When implementing this, implement it in WineD3D */
 
@@ -1478,13 +2181,10 @@ IDirectDrawImpl_EvaluateMode(IDirectDraw7 *iface,
  *  DDERR_INVALIDPARAMS if DDDI is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_GetDeviceIdentifier(IDirectDraw7 *iface,
-                                    DDDEVICEIDENTIFIER2 *DDDI,
-                                    DWORD Flags)
+static HRESULT WINAPI ddraw7_GetDeviceIdentifier(IDirectDraw7 *iface,
+        DDDEVICEIDENTIFIER2 *DDDI, DWORD Flags)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    TRACE("(%p)->(%p,%08x)\n", This, DDDI, Flags);
+    TRACE("iface %p, device_identifier %p, flags %#x.\n", iface, DDDI, Flags);
 
     if(!DDDI)
         return DDERR_INVALIDPARAMS;
@@ -1500,6 +2200,20 @@ IDirectDrawImpl_GetDeviceIdentifier(IDirectDraw7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_GetDeviceIdentifier(IDirectDraw4 *iface,
+        DDDEVICEIDENTIFIER *identifier, DWORD flags)
+{
+    DDDEVICEIDENTIFIER2 identifier2;
+    HRESULT hr;
+
+    TRACE("iface %p, identifier %p, flags %#x.\n", iface, identifier, flags);
+
+    hr = ddraw7_GetDeviceIdentifier((IDirectDraw7 *)ddraw_from_ddraw4(iface), &identifier2, flags);
+    DDRAW_Convert_DDDEVICEIDENTIFIER_2_To_1(&identifier2, identifier);
+
+    return hr;
+}
+
 /*****************************************************************************
  * IDirectDraw7::GetSurfaceFromDC
  *
@@ -1514,10 +2228,7 @@ IDirectDrawImpl_GetDeviceIdentifier(IDirectDraw7 *iface,
  *  Always returns DD_OK because it's a stub
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_GetSurfaceFromDC(IDirectDraw7 *iface,
-                                 HDC hdc,
-                                 IDirectDrawSurface7 **Surface)
+static HRESULT WINAPI ddraw7_GetSurfaceFromDC(IDirectDraw7 *iface, HDC hdc, IDirectDrawSurface7 **Surface)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     IWineD3DSurface *wined3d_surface;
@@ -1535,27 +2246,49 @@ IDirectDrawImpl_GetSurfaceFromDC(IDirectDraw7 *iface,
         return DDERR_NOTFOUND;
     }
 
-    IWineD3DSurface_GetParent(wined3d_surface, (IUnknown **)Surface);
+    *Surface = IWineD3DSurface_GetParent(wined3d_surface);
+    IDirectDrawSurface7_AddRef(*Surface);
     TRACE("Returning surface %p.\n", Surface);
     return DD_OK;
 }
 
-/*****************************************************************************
- * IDirectDraw7::RestoreAllSurfaces
- *
- * Calls the restore method of all surfaces
- *
- * Params:
- *
- * Returns:
- *  Always returns DD_OK because it's a stub
- *
+static HRESULT WINAPI ddraw4_GetSurfaceFromDC(IDirectDraw4 *iface, HDC dc, IDirectDrawSurface4 **surface)
+{
+    IDirectDrawSurface7 *surface7;
+    HRESULT hr;
+
+    TRACE("iface %p, dc %p, surface %p.\n", iface, dc, surface);
+
+    if (!surface) return E_INVALIDARG;
+
+    hr = ddraw7_GetSurfaceFromDC((IDirectDraw7 *)ddraw_from_ddraw4(iface), dc, &surface7);
+    *surface = surface7 ? (IDirectDrawSurface4 *)&((IDirectDrawSurfaceImpl *)surface7)->IDirectDrawSurface3_vtbl : NULL;
+
+    return hr;
+}
+
+static HRESULT WINAPI ddraw3_GetSurfaceFromDC(IDirectDraw3 *iface, HDC dc, IDirectDrawSurface **surface)
+{
+    TRACE("iface %p, dc %p, surface %p.\n", iface, dc, surface);
+
+    return ddraw7_GetSurfaceFromDC((IDirectDraw7 *)ddraw_from_ddraw3(iface),
+            dc, (IDirectDrawSurface7 **)surface);
+}
+
+/*****************************************************************************
+ * IDirectDraw7::RestoreAllSurfaces
+ *
+ * Calls the restore method of all surfaces
+ *
+ * Params:
+ *
+ * Returns:
+ *  Always returns DD_OK because it's a stub
+ *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_RestoreAllSurfaces(IDirectDraw7 *iface)
+static HRESULT WINAPI ddraw7_RestoreAllSurfaces(IDirectDraw7 *iface)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    FIXME("(%p): Stub\n", This);
+    FIXME("iface %p stub!\n", iface);
 
     /* This isn't hard to implement: Enumerate all WineD3D surfaces,
      * get their parent and call their restore method. Do not implement
@@ -1565,6 +2298,13 @@ IDirectDrawImpl_RestoreAllSurfaces(IDirectDraw7 *iface)
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw4_RestoreAllSurfaces(IDirectDraw4 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw7_RestoreAllSurfaces((IDirectDraw7 *)ddraw_from_ddraw4(iface));
+}
+
 /*****************************************************************************
  * IDirectDraw7::StartModeTest
  *
@@ -1587,14 +2327,10 @@ IDirectDrawImpl_RestoreAllSurfaces(IDirectDraw7 *iface)
  *  otherwise DD_OK
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_StartModeTest(IDirectDraw7 *iface,
-                              SIZE *Modes,
-                              DWORD NumModes,
-                              DWORD Flags)
+static HRESULT WINAPI ddraw7_StartModeTest(IDirectDraw7 *iface, SIZE *Modes, DWORD NumModes, DWORD Flags)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    WARN("(%p)->(%p, %d, %x): Semi-Stub, most likely harmless\n", This, Modes, NumModes, Flags);
+    FIXME("iface %p, modes %p, mode_count %u, flags %#x partial stub!\n",
+            iface, Modes, NumModes, Flags);
 
     /* This looks sane */
     if( (!Modes) || (NumModes == 0) ) return DDERR_INVALIDPARAMS;
@@ -1611,27 +2347,24 @@ IDirectDrawImpl_StartModeTest(IDirectDraw7 *iface,
 }
 
 /*****************************************************************************
- * IDirectDrawImpl_RecreateSurfacesCallback
+ * ddraw_recreate_surfaces_cb
  *
- * Enumeration callback for IDirectDrawImpl_RecreateAllSurfaces.
+ * Enumeration callback for ddraw_recreate_surface.
  * It re-recreates the WineD3DSurface. It's pretty straightforward
  *
  *****************************************************************************/
-HRESULT WINAPI
-IDirectDrawImpl_RecreateSurfacesCallback(IDirectDrawSurface7 *surf,
-                                         DDSURFACEDESC2 *desc,
-                                         void *Context)
+HRESULT WINAPI ddraw_recreate_surfaces_cb(IDirectDrawSurface7 *surf, DDSURFACEDESC2 *desc, void *Context)
 {
     IDirectDrawSurfaceImpl *surfImpl = (IDirectDrawSurfaceImpl *)surf;
     IDirectDrawImpl *This = surfImpl->ddraw;
-    IUnknown *Parent;
     IWineD3DSurface *wineD3DSurface;
     IWineD3DSwapChain *swapchain;
+    void *parent;
     HRESULT hr;
     IWineD3DClipper *clipper = NULL;
 
     WINED3DSURFACE_DESC     Desc;
-    WINED3DFORMAT           Format;
+    enum wined3d_format_id Format;
     DWORD                   Usage;
     WINED3DPOOL             Pool;
 
@@ -1640,7 +2373,8 @@ IDirectDrawImpl_RecreateSurfacesCallback(IDirectDrawSurface7 *surf,
     UINT                    Width;
     UINT                    Height;
 
-    TRACE("(%p): Enumerated Surface %p\n", This, surfImpl);
+    TRACE("surface %p, surface_desc %p, context %p.\n",
+            surf, desc, Context);
 
     /* For the enumeration */
     IDirectDrawSurface7_Release(surf);
@@ -1656,8 +2390,7 @@ IDirectDrawImpl_RecreateSurfacesCallback(IDirectDrawSurface7 *surf,
     IWineD3DSurface_GetClipper(wineD3DSurface, &clipper);
 
     /* Get the surface properties */
-    hr = IWineD3DSurface_GetDesc(wineD3DSurface, &Desc);
-    if(hr != D3D_OK) return hr;
+    IWineD3DSurface_GetDesc(wineD3DSurface, &Desc);
 
     Format = Desc.format;
     Usage = Desc.usage;
@@ -1667,13 +2400,10 @@ IDirectDrawImpl_RecreateSurfacesCallback(IDirectDrawSurface7 *surf,
     Width = Desc.width;
     Height = Desc.height;
 
-    IWineD3DSurface_GetParent(wineD3DSurface, &Parent);
-
-    /* Create the new surface */
-    hr = IWineD3DDevice_CreateSurface(This->wineD3DDevice, Width, Height, Format,
-            TRUE /* Lockable */, FALSE /* Discard */, surfImpl->mipmap_level, &surfImpl->WineD3DSurface, Usage, Pool,
-            MultiSampleType, MultiSampleQuality, This->ImplType, Parent, &ddraw_null_wined3d_parent_ops);
-    IUnknown_Release(Parent);
+    parent = IWineD3DSurface_GetParent(wineD3DSurface);
+    hr = IWineD3DDevice_CreateSurface(This->wineD3DDevice, Width, Height, Format, TRUE /* Lockable */,
+            FALSE /* Discard */, surfImpl->mipmap_level, Usage, Pool, MultiSampleType, MultiSampleQuality,
+            This->ImplType, parent, &ddraw_null_wined3d_parent_ops, &surfImpl->WineD3DSurface);
     if (FAILED(hr))
     {
         surfImpl->WineD3DSurface = wineD3DSurface;
@@ -1712,15 +2442,14 @@ IDirectDrawImpl_RecreateSurfacesCallback(IDirectDrawSurface7 *surf,
 }
 
 /*****************************************************************************
- * IDirectDrawImpl_RecreateAllSurfaces
+ * ddraw_recreate_surfaces
  *
  * A function, that converts all wineD3DSurfaces to the new implementation type
  * It enumerates all surfaces with IWineD3DDevice::EnumSurfaces, creates a
  * new WineD3DSurface, copies the content and releases the old surface
  *
  *****************************************************************************/
-static HRESULT
-IDirectDrawImpl_RecreateAllSurfaces(IDirectDrawImpl *This)
+static HRESULT ddraw_recreate_surfaces(IDirectDrawImpl *This)
 {
     DDSURFACEDESC2 desc;
     TRACE("(%p): Switch to implementation %d\n", This, This->ImplType);
@@ -1737,20 +2466,21 @@ IDirectDrawImpl_RecreateAllSurfaces(IDirectDrawImpl *This)
     memset(&desc, 0, sizeof(desc));
     desc.dwSize = sizeof(desc);
 
-    return IDirectDraw7_EnumSurfaces((IDirectDraw7 *)This, 0, &desc, This, IDirectDrawImpl_RecreateSurfacesCallback);
+    return IDirectDraw7_EnumSurfaces((IDirectDraw7 *)This, 0, &desc, This, ddraw_recreate_surfaces_cb);
 }
 
-ULONG WINAPI D3D7CB_DestroySwapChain(IWineD3DSwapChain *pSwapChain) {
-    IUnknown* swapChainParent;
-    TRACE("(%p) call back\n", pSwapChain);
+ULONG WINAPI D3D7CB_DestroySwapChain(IWineD3DSwapChain *pSwapChain)
+{
+    IUnknown *swapChainParent;
+
+    TRACE("swapchain %p.\n", pSwapChain);
 
-    IWineD3DSwapChain_GetParent(pSwapChain, &swapChainParent);
-    IUnknown_Release(swapChainParent);
+    swapChainParent = IWineD3DSwapChain_GetParent(pSwapChain);
     return IUnknown_Release(swapChainParent);
 }
 
 /*****************************************************************************
- * IDirectDrawImpl_CreateNewSurface
+ * ddraw_create_surface
  *
  * A helper function for IDirectDraw7::CreateSurface. It creates a new surface
  * with the passed parameters.
@@ -1763,19 +2493,14 @@ ULONG WINAPI D3D7CB_DestroySwapChain(IWineD3DSwapChain *pSwapChain) {
  *  DD_OK on success
  *
  *****************************************************************************/
-static HRESULT
-IDirectDrawImpl_CreateNewSurface(IDirectDrawImpl *This,
-                                 DDSURFACEDESC2 *pDDSD,
-                                 IDirectDrawSurfaceImpl **ppSurf,
-                                 UINT level)
+static HRESULT ddraw_create_surface(IDirectDrawImpl *This, DDSURFACEDESC2 *pDDSD,
+        IDirectDrawSurfaceImpl **ppSurf, UINT level)
 {
-    HRESULT hr;
-    UINT Width, Height;
-    WINED3DFORMAT Format = WINED3DFMT_UNKNOWN;
-    DWORD Usage = 0;
     WINED3DSURFTYPE ImplType = This->ImplType;
-    WINED3DSURFACE_DESC Desc;
-    WINED3DPOOL Pool = WINED3DPOOL_DEFAULT;
+    HRESULT hr;
+
+    TRACE("ddraw %p, surface_desc %p, surface %p, level %u.\n",
+            This, pDDSD, ppSurf, level);
 
     if (TRACE_ON(ddraw))
     {
@@ -1828,7 +2553,7 @@ IDirectDrawImpl_CreateNewSurface(IDirectDrawImpl *This,
             ImplType = SURFACE_OPENGL;
             This->ImplType = ImplType;
             TRACE("(%p) Re-creating all surfaces\n", This);
-            IDirectDrawImpl_RecreateAllSurfaces(This);
+            ddraw_recreate_surfaces(This);
             TRACE("(%p) Done recreating all surfaces\n", This);
         }
         else if(This->ImplType != SURFACE_OPENGL && pDDSD->ddsCaps.dwCaps & DDSCAPS_3DDEVICE)
@@ -1838,57 +2563,6 @@ IDirectDrawImpl_CreateNewSurface(IDirectDrawImpl *This,
         }
     }
 
-    if (!(pDDSD->ddsCaps.dwCaps & (DDSCAPS_VIDEOMEMORY | DDSCAPS_SYSTEMMEMORY)) &&
-        !((pDDSD->ddsCaps.dwCaps & DDSCAPS_TEXTURE) && (pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_TEXTUREMANAGE)) )
-    {
-        /* Tests show surfaces without memory flags get these flags added right after creation. */
-        pDDSD->ddsCaps.dwCaps |= DDSCAPS_LOCALVIDMEM | DDSCAPS_VIDEOMEMORY;
-    }
-    /* Get the correct wined3d usage */
-    if (pDDSD->ddsCaps.dwCaps & (DDSCAPS_PRIMARYSURFACE |
-                                 DDSCAPS_3DDEVICE       ) )
-    {
-        Usage |= WINED3DUSAGE_RENDERTARGET;
-
-        pDDSD->ddsCaps.dwCaps |= DDSCAPS_VISIBLE;
-    }
-    if (pDDSD->ddsCaps.dwCaps & (DDSCAPS_OVERLAY))
-    {
-        Usage |= WINED3DUSAGE_OVERLAY;
-    }
-    if(This->depthstencil || (pDDSD->ddsCaps.dwCaps & DDSCAPS_ZBUFFER) )
-    {
-        /* The depth stencil creation callback sets this flag.
-         * Set the WineD3D usage to let it know that it's a depth
-         * Stencil surface.
-         */
-        Usage |= WINED3DUSAGE_DEPTHSTENCIL;
-    }
-    if(pDDSD->ddsCaps.dwCaps & DDSCAPS_SYSTEMMEMORY)
-    {
-        Pool = WINED3DPOOL_SYSTEMMEM;
-    }
-    else if(pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_TEXTUREMANAGE)
-    {
-        Pool = WINED3DPOOL_MANAGED;
-        /* Managed textures have the system memory flag set */
-        pDDSD->ddsCaps.dwCaps |= DDSCAPS_SYSTEMMEMORY;
-    }
-    else if(pDDSD->ddsCaps.dwCaps & DDSCAPS_VIDEOMEMORY)
-    {
-        /* Videomemory adds localvidmem, this is mutually exclusive with systemmemory
-         * and texturemanage
-         */
-        pDDSD->ddsCaps.dwCaps |= DDSCAPS_LOCALVIDMEM;
-    }
-
-    Format = PixelFormat_DD2WineD3D(&pDDSD->u4.ddpfPixelFormat);
-    if(Format == WINED3DFMT_UNKNOWN)
-    {
-        ERR("Unsupported / Unknown pixelformat\n");
-        return DDERR_INVALIDPIXELFORMAT;
-    }
-
     /* Create the Surface object */
     *ppSurf = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IDirectDrawSurfaceImpl));
     if(!*ppSurf)
@@ -1896,41 +2570,12 @@ IDirectDrawImpl_CreateNewSurface(IDirectDrawImpl *This,
         ERR("(%p) Error allocating memory for a surface\n", This);
         return DDERR_OUTOFVIDEOMEMORY;
     }
-    (*ppSurf)->lpVtbl = &IDirectDrawSurface7_Vtbl;
-    (*ppSurf)->IDirectDrawSurface3_vtbl = &IDirectDrawSurface3_Vtbl;
-    (*ppSurf)->IDirectDrawGammaControl_vtbl = &IDirectDrawGammaControl_Vtbl;
-    (*ppSurf)->IDirect3DTexture2_vtbl = &IDirect3DTexture2_Vtbl;
-    (*ppSurf)->IDirect3DTexture_vtbl = &IDirect3DTexture1_Vtbl;
-    (*ppSurf)->ref = 1;
-    (*ppSurf)->version = 7;
-    TRACE("%p->version = %d\n", (*ppSurf), (*ppSurf)->version);
-    (*ppSurf)->ddraw = This;
-    (*ppSurf)->surface_desc.dwSize = sizeof(DDSURFACEDESC2);
-    (*ppSurf)->surface_desc.u4.ddpfPixelFormat.dwSize = sizeof(DDPIXELFORMAT);
-    DD_STRUCT_COPY_BYSIZE(&(*ppSurf)->surface_desc, pDDSD);
-
-    /* Surface attachments */
-    (*ppSurf)->next_attached = NULL;
-    (*ppSurf)->first_attached = *ppSurf;
-
-    /* Needed to re-create the surface on an implementation change */
-    (*ppSurf)->ImplType = ImplType;
-
-    /* For D3DDevice creation */
-    (*ppSurf)->isRenderTarget = FALSE;
-
-    /* A trace message for debugging */
-    TRACE("(%p) Created IDirectDrawSurface implementation structure at %p\n", This, *ppSurf);
-
-    /* Now create the WineD3D Surface */
-    hr = IWineD3DDevice_CreateSurface(This->wineD3DDevice, pDDSD->dwWidth, pDDSD->dwHeight, Format,
-            TRUE /* Lockable */, FALSE /* Discard */, level, &(*ppSurf)->WineD3DSurface,
-            Usage, Pool, WINED3DMULTISAMPLE_NONE, 0 /* MultiSampleQuality */, ImplType,
-            (IUnknown *)*ppSurf, &ddraw_null_wined3d_parent_ops);
-
-    if(hr != D3D_OK)
-    {
-        ERR("IWineD3DDevice::CreateSurface failed. hr = %08x\n", hr);
+
+    hr = ddraw_surface_init(*ppSurf, This, pDDSD, level, ImplType);
+    if (FAILED(hr))
+    {
+        WARN("Failed to initialize surface, hr %#x.\n", hr);
+        HeapFree(GetProcessHeap(), 0, *ppSurf);
         return hr;
     }
 
@@ -1938,93 +2583,7 @@ IDirectDrawImpl_CreateNewSurface(IDirectDrawImpl *This,
     InterlockedIncrement(&This->surfaces);
     list_add_head(&This->surface_list, &(*ppSurf)->surface_list_entry);
 
-    /* Here we could store all created surfaces in the DirectDrawImpl structure,
-     * But this could also be delegated to WineDDraw, as it keeps track of all its
-     * resources. Not implemented for now, as there are more important things ;)
-     */
-
-    /* Get the pixel format of the WineD3DSurface and store it.
-     * Don't use the Format choosen above, WineD3D might have
-     * changed it
-     */
-    (*ppSurf)->surface_desc.dwFlags |= DDSD_PIXELFORMAT;
-    hr = IWineD3DSurface_GetDesc((*ppSurf)->WineD3DSurface, &Desc);
-    if(hr != D3D_OK)
-    {
-        ERR("IWineD3DSurface::GetDesc failed\n");
-        IDirectDrawSurface7_Release( (IDirectDrawSurface7 *) *ppSurf);
-        return hr;
-    }
-
-    Format = Desc.format;
-    Width = Desc.width;
-    Height = Desc.height;
-
-    if(Format == WINED3DFMT_UNKNOWN)
-    {
-        FIXME("IWineD3DSurface::GetDesc returned WINED3DFMT_UNKNOWN\n");
-    }
-    PixelFormat_WineD3DtoDD( &(*ppSurf)->surface_desc.u4.ddpfPixelFormat, Format);
-
-    /* Anno 1602 stores the pitch right after surface creation, so make sure it's there.
-     * I can't LockRect() the surface here because if OpenGL surfaces are in use, the
-     * WineD3DDevice might not be usable for 3D yet, so an extra method was created.
-     * TODO: Test other fourcc formats
-     */
-    if(Format == WINED3DFMT_DXT1 || Format == WINED3DFMT_DXT2 || Format == WINED3DFMT_DXT3 ||
-       Format == WINED3DFMT_DXT4 || Format == WINED3DFMT_DXT5)
-    {
-        (*ppSurf)->surface_desc.dwFlags |= DDSD_LINEARSIZE;
-        if(Format == WINED3DFMT_DXT1)
-        {
-            (*ppSurf)->surface_desc.u1.dwLinearSize = max(4, Width) * max(4, Height) / 2;
-        }
-        else
-        {
-            (*ppSurf)->surface_desc.u1.dwLinearSize = max(4, Width) * max(4, Height);
-        }
-    }
-    else
-    {
-        (*ppSurf)->surface_desc.dwFlags |= DDSD_PITCH;
-        (*ppSurf)->surface_desc.u1.lPitch = IWineD3DSurface_GetPitch((*ppSurf)->WineD3DSurface);
-    }
-
-    /* Application passed a color key? Set it! */
-    if(pDDSD->dwFlags & DDSD_CKDESTOVERLAY)
-    {
-        IWineD3DSurface_SetColorKey((*ppSurf)->WineD3DSurface,
-                                    DDCKEY_DESTOVERLAY,
-                                    (WINEDDCOLORKEY *) &pDDSD->u3.ddckCKDestOverlay);
-    }
-    if(pDDSD->dwFlags & DDSD_CKDESTBLT)
-    {
-        IWineD3DSurface_SetColorKey((*ppSurf)->WineD3DSurface,
-                                    DDCKEY_DESTBLT,
-                                    (WINEDDCOLORKEY *) &pDDSD->ddckCKDestBlt);
-    }
-    if(pDDSD->dwFlags & DDSD_CKSRCOVERLAY)
-    {
-        IWineD3DSurface_SetColorKey((*ppSurf)->WineD3DSurface,
-                                    DDCKEY_SRCOVERLAY,
-                                    (WINEDDCOLORKEY *) &pDDSD->ddckCKSrcOverlay);
-    }
-    if(pDDSD->dwFlags & DDSD_CKSRCBLT)
-    {
-        IWineD3DSurface_SetColorKey((*ppSurf)->WineD3DSurface,
-                                    DDCKEY_SRCBLT,
-                                    (WINEDDCOLORKEY *) &pDDSD->ddckCKSrcBlt);
-    }
-    if ( pDDSD->dwFlags & DDSD_LPSURFACE)
-    {
-        hr = IWineD3DSurface_SetMem((*ppSurf)->WineD3DSurface, pDDSD->lpSurface);
-        if(hr != WINED3D_OK)
-        {
-            /* No need for a trace here, wined3d does that for us */
-            IDirectDrawSurface7_Release((IDirectDrawSurface7 *)*ppSurf);
-            return hr;
-        }
-    }
+    TRACE("Created surface %p.\n", *ppSurf);
 
     return DD_OK;
 }
@@ -2074,10 +2633,7 @@ CreateAdditionalSurfaces(IDirectDrawImpl *This,
         }
         CubeFaceRoot = FALSE;
 
-        hr = IDirectDrawImpl_CreateNewSurface(This,
-                                              &DDSD,
-                                              &object2,
-                                              level);
+        hr = ddraw_create_surface(This, &DDSD, &object2, level);
         if(hr != DD_OK)
         {
             return hr;
@@ -2101,6 +2657,153 @@ CreateAdditionalSurfaces(IDirectDrawImpl *This,
     return DD_OK;
 }
 
+/* Must set all attached surfaces (e.g. mipmaps) versions as well */
+static void ddraw_set_surface_version(IDirectDrawSurfaceImpl *surface, UINT version)
+{
+    unsigned int i;
+
+    TRACE("surface %p, version %u -> %u.\n", surface, surface->version, version);
+
+    surface->version = version;
+    for (i = 0; i < MAX_COMPLEX_ATTACHED; ++i)
+    {
+        if (!surface->complex_array[i]) break;
+        ddraw_set_surface_version(surface->complex_array[i], version);
+    }
+    while ((surface = surface->next_attached))
+    {
+        ddraw_set_surface_version(surface, version);
+    }
+}
+
+/*****************************************************************************
+ * ddraw_attach_d3d_device
+ *
+ * Initializes the D3D capabilities of WineD3D
+ *
+ * Params:
+ *  primary: The primary surface for D3D
+ *
+ * Returns
+ *  DD_OK on success,
+ *  DDERR_* otherwise
+ *
+ *****************************************************************************/
+static HRESULT ddraw_attach_d3d_device(IDirectDrawImpl *ddraw, IDirectDrawSurfaceImpl *primary)
+{
+    WINED3DPRESENT_PARAMETERS localParameters;
+    HWND window = ddraw->dest_window;
+    HRESULT hr;
+
+    TRACE("ddraw %p, primary %p.\n", ddraw, primary);
+
+    if (!window || window == GetDesktopWindow())
+    {
+        window = CreateWindowExA(0, DDRAW_WINDOW_CLASS_NAME, "Hidden D3D Window",
+                WS_DISABLED, 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN),
+                NULL, NULL, NULL, NULL);
+        if (!window)
+        {
+            ERR("Failed to create window, last error %#x.\n", GetLastError());
+            return E_FAIL;
+        }
+
+        ShowWindow(window, SW_HIDE);   /* Just to be sure */
+        WARN("No window for the Direct3DDevice, created hidden window %p.\n", window);
+    }
+    else
+    {
+        TRACE("Using existing window %p for Direct3D rendering.\n", window);
+    }
+    ddraw->d3d_window = window;
+
+    /* Store the future Render Target surface */
+    ddraw->d3d_target = primary;
+
+    /* Use the surface description for the device parameters, not the device
+     * settings. The application might render to an offscreen surface. */
+    localParameters.BackBufferWidth = primary->surface_desc.dwWidth;
+    localParameters.BackBufferHeight = primary->surface_desc.dwHeight;
+    localParameters.BackBufferFormat = PixelFormat_DD2WineD3D(&primary->surface_desc.u4.ddpfPixelFormat);
+    localParameters.BackBufferCount = (primary->surface_desc.dwFlags & DDSD_BACKBUFFERCOUNT)
+            ? primary->surface_desc.u5.dwBackBufferCount : 0;
+    localParameters.MultiSampleType = WINED3DMULTISAMPLE_NONE;
+    localParameters.MultiSampleQuality = 0;
+    localParameters.SwapEffect = WINED3DSWAPEFFECT_COPY;
+    localParameters.hDeviceWindow = window;
+    localParameters.Windowed = !(ddraw->cooperative_level & DDSCL_FULLSCREEN);
+    localParameters.EnableAutoDepthStencil = TRUE;
+    localParameters.AutoDepthStencilFormat = WINED3DFMT_D16_UNORM;
+    localParameters.Flags = 0;
+    localParameters.FullScreen_RefreshRateInHz = WINED3DPRESENT_RATE_DEFAULT;
+    localParameters.PresentationInterval = WINED3DPRESENT_INTERVAL_DEFAULT;
+
+    /* Set this NOW, otherwise creating the depth stencil surface will cause a
+     * recursive loop until ram or emulated video memory is full. */
+    ddraw->d3d_initialized = TRUE;
+    hr = IWineD3DDevice_Init3D(ddraw->wineD3DDevice, &localParameters);
+    if (FAILED(hr))
+    {
+        ddraw->d3d_target = NULL;
+        ddraw->d3d_initialized = FALSE;
+        return hr;
+    }
+
+    ddraw->declArraySize = 2;
+    ddraw->decls = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*ddraw->decls) * ddraw->declArraySize);
+    if (!ddraw->decls)
+    {
+        ERR("Error allocating an array for the converted vertex decls.\n");
+        ddraw->declArraySize = 0;
+        hr = IWineD3DDevice_Uninit3D(ddraw->wineD3DDevice, D3D7CB_DestroySwapChain);
+        return E_OUTOFMEMORY;
+    }
+
+    TRACE("Successfully initialized 3D.\n");
+
+    return DD_OK;
+}
+
+static HRESULT ddraw_create_gdi_swapchain(IDirectDrawImpl *ddraw, IDirectDrawSurfaceImpl *primary)
+{
+    WINED3DPRESENT_PARAMETERS presentation_parameters;
+    HWND window;
+    HRESULT hr;
+
+    window = ddraw->dest_window;
+
+    memset(&presentation_parameters, 0, sizeof(presentation_parameters));
+
+    /* Use the surface description for the device parameters, not the device
+     * settings. The application might render to an offscreen surface. */
+    presentation_parameters.BackBufferWidth = primary->surface_desc.dwWidth;
+    presentation_parameters.BackBufferHeight = primary->surface_desc.dwHeight;
+    presentation_parameters.BackBufferFormat = PixelFormat_DD2WineD3D(&primary->surface_desc.u4.ddpfPixelFormat);
+    presentation_parameters.BackBufferCount = (primary->surface_desc.dwFlags & DDSD_BACKBUFFERCOUNT)
+            ? primary->surface_desc.u5.dwBackBufferCount : 0;
+    presentation_parameters.MultiSampleType = WINED3DMULTISAMPLE_NONE;
+    presentation_parameters.MultiSampleQuality = 0;
+    presentation_parameters.SwapEffect = WINED3DSWAPEFFECT_FLIP;
+    presentation_parameters.hDeviceWindow = window;
+    presentation_parameters.Windowed = !(ddraw->cooperative_level & DDSCL_FULLSCREEN);
+    presentation_parameters.EnableAutoDepthStencil = FALSE; /* Not on GDI swapchains */
+    presentation_parameters.AutoDepthStencilFormat = 0;
+    presentation_parameters.Flags = 0;
+    presentation_parameters.FullScreen_RefreshRateInHz = WINED3DPRESENT_RATE_DEFAULT;
+    presentation_parameters.PresentationInterval = WINED3DPRESENT_INTERVAL_DEFAULT;
+
+    ddraw->d3d_target = primary;
+    hr = IWineD3DDevice_InitGDI(ddraw->wineD3DDevice, &presentation_parameters);
+    ddraw->d3d_target = NULL;
+    if (FAILED(hr))
+    {
+        WARN("Failed to initialize GDI ddraw implementation, hr %#x.\n", hr);
+        primary->wineD3DSwapChain = NULL;
+    }
+
+    return hr;
+}
+
 /*****************************************************************************
  * IDirectDraw7::CreateSurface
  *
@@ -2178,11 +2881,8 @@ CreateAdditionalSurfaces(IDirectDrawImpl *This,
  *  DDERR_* if an error occurs
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_CreateSurface(IDirectDraw7 *iface,
-                              DDSURFACEDESC2 *DDSD,
-                              IDirectDrawSurface7 **Surf,
-                              IUnknown *UnkOuter)
+static HRESULT CreateSurface(IDirectDraw7 *iface,
+        DDSURFACEDESC2 *DDSD, IDirectDrawSurface7 **Surf, IUnknown *UnkOuter)
 {
     IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
     IDirectDrawSurfaceImpl *object = NULL;
@@ -2192,7 +2892,8 @@ IDirectDrawImpl_CreateSurface(IDirectDraw7 *iface,
     WINED3DDISPLAYMODE Mode;
     const DWORD sysvidmem = DDSCAPS_VIDEOMEMORY | DDSCAPS_SYSTEMMEMORY;
 
-    TRACE("(%p)->(%p,%p,%p)\n", This, DDSD, Surf, UnkOuter);
+    TRACE("iface %p, surface_desc %p, surface %p, outer_unknown %p.\n",
+            iface, DDSD, Surf, UnkOuter);
 
     /* Some checks before we start */
     if (TRACE_ON(ddraw))
@@ -2244,8 +2945,9 @@ IDirectDrawImpl_CreateSurface(IDirectDraw7 *iface,
         return DDERR_NOEXCLUSIVEMODE;
     }
 
-    if(DDSD->ddsCaps.dwCaps & (DDSCAPS_FRONTBUFFER | DDSCAPS_BACKBUFFER)) {
-        WARN("Application tried to create an explicit front or back buffer\n");
+    if((DDSD->ddsCaps.dwCaps & (DDSCAPS_BACKBUFFER | DDSCAPS_PRIMARYSURFACE)) == (DDSCAPS_BACKBUFFER | DDSCAPS_PRIMARYSURFACE))
+    {
+        WARN("Application wanted to create back buffer primary surface\n");
         LeaveCriticalSection(&ddraw_cs);
         return DDERR_INVALIDCAPS;
     }
@@ -2436,10 +3138,10 @@ IDirectDrawImpl_CreateSurface(IDirectDraw7 *iface,
     }
 
     /* Create the first surface */
-    hr = IDirectDrawImpl_CreateNewSurface(This, &desc2, &object, 0);
-    if( hr != DD_OK)
+    hr = ddraw_create_surface(This, &desc2, &object, 0);
+    if (FAILED(hr))
     {
-        ERR("IDirectDrawImpl_CreateNewSurface failed with %08x\n", hr);
+        WARN("ddraw_create_surface failed, hr %#x.\n", hr);
         LeaveCriticalSection(&ddraw_cs);
         return hr;
     }
@@ -2520,11 +3222,11 @@ IDirectDrawImpl_CreateSurface(IDirectDraw7 *iface,
         }
 
         TRACE("(%p) Attaching a D3DDevice, rendertarget = %p\n", This, target);
-        hr = IDirectDrawImpl_AttachD3DDevice(This, target);
-        if(hr != D3D_OK)
+        hr = ddraw_attach_d3d_device(This, target);
+        if (hr != D3D_OK)
         {
             IDirectDrawSurfaceImpl *release_surf;
-            ERR("IDirectDrawImpl_AttachD3DDevice failed, hr = %x\n", hr);
+            ERR("ddraw_attach_d3d_device failed, hr %#x\n", hr);
             *Surf = NULL;
 
             /* The before created surface structures are in an incomplete state here.
@@ -2538,13 +3240,15 @@ IDirectDrawImpl_CreateSurface(IDirectDraw7 *iface,
             {
                 release_surf = object;
                 object = object->complex_array[0];
-                IDirectDrawSurfaceImpl_Destroy(release_surf);
+                ddraw_surface_destroy(release_surf);
             }
             LeaveCriticalSection(&ddraw_cs);
             return hr;
         }
-    } else if(!(This->d3d_initialized) && desc2.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) {
-        IDirectDrawImpl_CreateGDISwapChain(This, object);
+    }
+    else if(!(This->d3d_initialized) && desc2.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE)
+    {
+        ddraw_create_gdi_swapchain(This, object);
     }
 
     /* Addref the ddraw interface to keep an reference for each surface */
@@ -2554,8 +3258,8 @@ IDirectDrawImpl_CreateSurface(IDirectDraw7 *iface,
     /* Create a WineD3DTexture if a texture was requested */
     if(desc2.ddsCaps.dwCaps & DDSCAPS_TEXTURE)
     {
+        enum wined3d_format_id Format;
         UINT levels;
-        WINED3DFORMAT Format;
         WINED3DPOOL Pool = WINED3DPOOL_DEFAULT;
 
         This->tex_root = object;
@@ -2586,15 +3290,15 @@ IDirectDrawImpl_CreateSurface(IDirectDraw7 *iface,
          */
         if(desc2.ddsCaps.dwCaps2 & DDSCAPS2_CUBEMAP)
         {
-            hr = IWineD3DDevice_CreateCubeTexture(This->wineD3DDevice, DDSD->dwWidth /* Edgelength */,
-                    levels, 0 /* usage */, Format, Pool, (IWineD3DCubeTexture **)&object->wineD3DTexture,
-                    (IUnknown *)object, &ddraw_null_wined3d_parent_ops);
+            hr = IWineD3DDevice_CreateCubeTexture(This->wineD3DDevice, DDSD->dwWidth /* Edgelength */, levels,
+                    0 /* usage */, Format, Pool, object, &ddraw_null_wined3d_parent_ops,
+                    (IWineD3DCubeTexture **)&object->wineD3DTexture);
         }
         else
         {
             hr = IWineD3DDevice_CreateTexture(This->wineD3DDevice, DDSD->dwWidth, DDSD->dwHeight, levels,
-                    0 /* usage */, Format, Pool, (IWineD3DTexture **)&object->wineD3DTexture,
-                    (IUnknown *)object, &ddraw_null_wined3d_parent_ops);
+                    0 /* usage */, Format, Pool, object, &ddraw_null_wined3d_parent_ops,
+                    (IWineD3DTexture **)&object->wineD3DTexture);
         }
         This->tex_root = NULL;
     }
@@ -2603,75 +3307,268 @@ IDirectDrawImpl_CreateSurface(IDirectDraw7 *iface,
     return hr;
 }
 
-#define DDENUMSURFACES_SEARCHTYPE (DDENUMSURFACES_CANBECREATED|DDENUMSURFACES_DOESEXIST)
-#define DDENUMSURFACES_MATCHTYPE (DDENUMSURFACES_ALL|DDENUMSURFACES_MATCH|DDENUMSURFACES_NOMATCH)
-
-static BOOL
-Main_DirectDraw_DDPIXELFORMAT_Match(const DDPIXELFORMAT *requested,
-                                    const DDPIXELFORMAT *provided)
+static HRESULT WINAPI ddraw7_CreateSurface(IDirectDraw7 *iface,
+        DDSURFACEDESC2 *surface_desc, IDirectDrawSurface7 **surface, IUnknown *outer_unknown)
 {
-    /* Some flags must be present in both or neither for a match. */
-    static const DWORD must_match = DDPF_PALETTEINDEXED1 | DDPF_PALETTEINDEXED2
-        | DDPF_PALETTEINDEXED4 | DDPF_PALETTEINDEXED8 | DDPF_FOURCC
-        | DDPF_ZBUFFER | DDPF_STENCILBUFFER;
+    TRACE("iface %p, surface_desc %p, surface %p, outer_unknown %p.\n",
+            iface, surface_desc, surface, outer_unknown);
 
-    if ((requested->dwFlags & provided->dwFlags) != requested->dwFlags)
-        return FALSE;
+    if(surface_desc == NULL || surface_desc->dwSize != sizeof(DDSURFACEDESC2))
+    {
+        WARN("Application supplied invalid surface descriptor\n");
+        return DDERR_INVALIDPARAMS;
+    }
 
-    if ((requested->dwFlags & must_match) != (provided->dwFlags & must_match))
-        return FALSE;
+    if(surface_desc->ddsCaps.dwCaps & (DDSCAPS_FRONTBUFFER | DDSCAPS_BACKBUFFER))
+    {
+        if (TRACE_ON(ddraw))
+        {
+            TRACE(" (%p) Requesting surface desc :\n", iface);
+            DDRAW_dump_surface_desc(surface_desc);
+        }
 
-    if (requested->dwFlags & DDPF_FOURCC)
-        if (requested->dwFourCC != provided->dwFourCC)
-            return FALSE;
+        WARN("Application tried to create an explicit front or back buffer\n");
+        return DDERR_INVALIDCAPS;
+    }
 
-    if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_ZBUFFER|DDPF_ALPHA
-                              |DDPF_LUMINANCE|DDPF_BUMPDUDV))
-        if (requested->u1.dwRGBBitCount != provided->u1.dwRGBBitCount)
-            return FALSE;
+    return CreateSurface(iface, surface_desc, surface, outer_unknown);
+}
 
-    if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_STENCILBUFFER
-                              |DDPF_LUMINANCE|DDPF_BUMPDUDV))
-        if (requested->u2.dwRBitMask != provided->u2.dwRBitMask)
-            return FALSE;
+static HRESULT WINAPI ddraw4_CreateSurface(IDirectDraw4 *iface,
+        DDSURFACEDESC2 *surface_desc, IDirectDrawSurface4 **surface, IUnknown *outer_unknown)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw4(iface);
+    IDirectDrawSurfaceImpl *impl;
+    HRESULT hr;
 
-    if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_ZBUFFER|DDPF_BUMPDUDV))
-        if (requested->u3.dwGBitMask != provided->u3.dwGBitMask)
-            return FALSE;
+    TRACE("iface %p, surface_desc %p, surface %p, outer_unknown %p.\n",
+            iface, surface_desc, surface, outer_unknown);
 
-    /* I could be wrong about the bumpmapping. MSDN docs are vague. */
-    if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_STENCILBUFFER
-                              |DDPF_BUMPDUDV))
-        if (requested->u4.dwBBitMask != provided->u4.dwBBitMask)
-            return FALSE;
+    if(surface_desc == NULL || surface_desc->dwSize != sizeof(DDSURFACEDESC2))
+    {
+        WARN("Application supplied invalid surface descriptor\n");
+        return DDERR_INVALIDPARAMS;
+    }
 
-    if (requested->dwFlags & (DDPF_ALPHAPIXELS|DDPF_ZPIXELS))
-        if (requested->u5.dwRGBAlphaBitMask != provided->u5.dwRGBAlphaBitMask)
-            return FALSE;
+    if(surface_desc->ddsCaps.dwCaps & (DDSCAPS_FRONTBUFFER | DDSCAPS_BACKBUFFER))
+    {
+        if (TRACE_ON(ddraw))
+        {
+            TRACE(" (%p) Requesting surface desc :\n", iface);
+            DDRAW_dump_surface_desc(surface_desc);
+        }
 
-    return TRUE;
+        WARN("Application tried to create an explicit front or back buffer\n");
+        return DDERR_INVALIDCAPS;
+    }
+
+    hr = CreateSurface((IDirectDraw7 *)ddraw, surface_desc, (IDirectDrawSurface7 **)surface, outer_unknown);
+    impl = (IDirectDrawSurfaceImpl *)*surface;
+    if (SUCCEEDED(hr) && impl)
+    {
+        ddraw_set_surface_version(impl, 4);
+        IDirectDraw7_Release((IDirectDraw7 *)ddraw);
+        IDirectDraw4_AddRef(iface);
+        impl->ifaceToRelease = (IUnknown *)iface;
+    }
+
+    return hr;
 }
 
-static BOOL
-IDirectDrawImpl_DDSD_Match(const DDSURFACEDESC2* requested,
-                           const DDSURFACEDESC2* provided)
+static HRESULT WINAPI ddraw3_CreateSurface(IDirectDraw3 *iface,
+        DDSURFACEDESC *surface_desc, IDirectDrawSurface **surface, IUnknown *outer_unknown)
 {
-    struct compare_info
-    {
-        DWORD flag;
-        ptrdiff_t offset;
-        size_t size;
-    };
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw3(iface);
+    IDirectDrawSurface7 *surface7;
+    IDirectDrawSurfaceImpl *impl;
+    HRESULT hr;
 
-#define CMP(FLAG, FIELD)                                \
-        { DDSD_##FLAG, offsetof(DDSURFACEDESC2, FIELD), \
-          sizeof(((DDSURFACEDESC2 *)(NULL))->FIELD) }
+    TRACE("iface %p, surface_desc %p, surface %p, outer_unknown %p.\n",
+            iface, surface_desc, surface, outer_unknown);
 
-    static const struct compare_info compare[] =
+    if(surface_desc == NULL || surface_desc->dwSize != sizeof(DDSURFACEDESC))
     {
-        CMP(ALPHABITDEPTH, dwAlphaBitDepth),
-        CMP(BACKBUFFERCOUNT, u5.dwBackBufferCount),
-        CMP(CAPS, ddsCaps),
+        WARN("Application supplied invalid surface descriptor\n");
+        return DDERR_INVALIDPARAMS;
+    }
+
+    if(surface_desc->ddsCaps.dwCaps & (DDSCAPS_FRONTBUFFER | DDSCAPS_BACKBUFFER))
+    {
+        if (TRACE_ON(ddraw))
+        {
+            TRACE(" (%p) Requesting surface desc :\n", iface);
+            DDRAW_dump_surface_desc((LPDDSURFACEDESC2)surface_desc);
+        }
+
+        WARN("Application tried to create an explicit front or back buffer\n");
+        return DDERR_INVALIDCAPS;
+    }
+
+    hr = CreateSurface((IDirectDraw7 *)ddraw, (DDSURFACEDESC2 *)surface_desc, &surface7, outer_unknown);
+    if (FAILED(hr))
+    {
+        *surface = NULL;
+        return hr;
+    }
+
+    impl = (IDirectDrawSurfaceImpl *)surface7;
+    *surface = (IDirectDrawSurface *)&impl->IDirectDrawSurface3_vtbl;
+    ddraw_set_surface_version(impl, 3);
+    IDirectDraw7_Release((IDirectDraw7 *)ddraw);
+    IDirectDraw3_AddRef(iface);
+    impl->ifaceToRelease = (IUnknown *)iface;
+
+    return hr;
+}
+
+static HRESULT WINAPI ddraw2_CreateSurface(IDirectDraw2 *iface,
+        DDSURFACEDESC *surface_desc, IDirectDrawSurface **surface, IUnknown *outer_unknown)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw2(iface);
+    IDirectDrawSurface7 *surface7;
+    IDirectDrawSurfaceImpl *impl;
+    HRESULT hr;
+
+    TRACE("iface %p, surface_desc %p, surface %p, outer_unknown %p.\n",
+            iface, surface_desc, surface, outer_unknown);
+
+    if(surface_desc == NULL || surface_desc->dwSize != sizeof(DDSURFACEDESC))
+    {
+        WARN("Application supplied invalid surface descriptor\n");
+        return DDERR_INVALIDPARAMS;
+    }
+
+    if(surface_desc->ddsCaps.dwCaps & (DDSCAPS_FRONTBUFFER | DDSCAPS_BACKBUFFER))
+    {
+        if (TRACE_ON(ddraw))
+        {
+            TRACE(" (%p) Requesting surface desc :\n", iface);
+            DDRAW_dump_surface_desc((LPDDSURFACEDESC2)surface_desc);
+        }
+
+        WARN("Application tried to create an explicit front or back buffer\n");
+        return DDERR_INVALIDCAPS;
+    }
+
+    hr = CreateSurface((IDirectDraw7 *)ddraw, (DDSURFACEDESC2 *)surface_desc, &surface7, outer_unknown);
+    if (FAILED(hr))
+    {
+        *surface = NULL;
+        return hr;
+    }
+
+    impl = (IDirectDrawSurfaceImpl *)surface7;
+    *surface = (IDirectDrawSurface *)&impl->IDirectDrawSurface3_vtbl;
+    ddraw_set_surface_version(impl, 2);
+    IDirectDraw7_Release((IDirectDraw7 *)ddraw);
+    impl->ifaceToRelease = NULL;
+
+    return hr;
+}
+
+static HRESULT WINAPI ddraw1_CreateSurface(IDirectDraw *iface,
+        DDSURFACEDESC *surface_desc, IDirectDrawSurface **surface, IUnknown *outer_unknown)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw1(iface);
+    IDirectDrawSurface7 *surface7;
+    IDirectDrawSurfaceImpl *impl;
+    HRESULT hr;
+
+    TRACE("iface %p, surface_desc %p, surface %p, outer_unknown %p.\n",
+            iface, surface_desc, surface, outer_unknown);
+
+    if(surface_desc == NULL || surface_desc->dwSize != sizeof(DDSURFACEDESC))
+    {
+        WARN("Application supplied invalid surface descriptor\n");
+        return DDERR_INVALIDPARAMS;
+    }
+
+    /* Remove front buffer flag, this causes failure in v7, and its added to normal
+     * primaries anyway. */
+    surface_desc->ddsCaps.dwCaps &= ~DDSCAPS_FRONTBUFFER;
+    hr = CreateSurface((IDirectDraw7 *)ddraw, (DDSURFACEDESC2 *)surface_desc, &surface7, outer_unknown);
+    if (FAILED(hr))
+    {
+        *surface = NULL;
+        return hr;
+    }
+
+    impl = (IDirectDrawSurfaceImpl *)surface7;
+    *surface = (IDirectDrawSurface *)&impl->IDirectDrawSurface3_vtbl;
+    ddraw_set_surface_version(impl, 1);
+    IDirectDraw7_Release((IDirectDraw7 *)ddraw);
+    impl->ifaceToRelease = NULL;
+
+    return hr;
+}
+
+#define DDENUMSURFACES_SEARCHTYPE (DDENUMSURFACES_CANBECREATED|DDENUMSURFACES_DOESEXIST)
+#define DDENUMSURFACES_MATCHTYPE (DDENUMSURFACES_ALL|DDENUMSURFACES_MATCH|DDENUMSURFACES_NOMATCH)
+
+static BOOL
+Main_DirectDraw_DDPIXELFORMAT_Match(const DDPIXELFORMAT *requested,
+                                    const DDPIXELFORMAT *provided)
+{
+    /* Some flags must be present in both or neither for a match. */
+    static const DWORD must_match = DDPF_PALETTEINDEXED1 | DDPF_PALETTEINDEXED2
+        | DDPF_PALETTEINDEXED4 | DDPF_PALETTEINDEXED8 | DDPF_FOURCC
+        | DDPF_ZBUFFER | DDPF_STENCILBUFFER;
+
+    if ((requested->dwFlags & provided->dwFlags) != requested->dwFlags)
+        return FALSE;
+
+    if ((requested->dwFlags & must_match) != (provided->dwFlags & must_match))
+        return FALSE;
+
+    if (requested->dwFlags & DDPF_FOURCC)
+        if (requested->dwFourCC != provided->dwFourCC)
+            return FALSE;
+
+    if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_ZBUFFER|DDPF_ALPHA
+                              |DDPF_LUMINANCE|DDPF_BUMPDUDV))
+        if (requested->u1.dwRGBBitCount != provided->u1.dwRGBBitCount)
+            return FALSE;
+
+    if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_STENCILBUFFER
+                              |DDPF_LUMINANCE|DDPF_BUMPDUDV))
+        if (requested->u2.dwRBitMask != provided->u2.dwRBitMask)
+            return FALSE;
+
+    if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_ZBUFFER|DDPF_BUMPDUDV))
+        if (requested->u3.dwGBitMask != provided->u3.dwGBitMask)
+            return FALSE;
+
+    /* I could be wrong about the bumpmapping. MSDN docs are vague. */
+    if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_STENCILBUFFER
+                              |DDPF_BUMPDUDV))
+        if (requested->u4.dwBBitMask != provided->u4.dwBBitMask)
+            return FALSE;
+
+    if (requested->dwFlags & (DDPF_ALPHAPIXELS|DDPF_ZPIXELS))
+        if (requested->u5.dwRGBAlphaBitMask != provided->u5.dwRGBAlphaBitMask)
+            return FALSE;
+
+    return TRUE;
+}
+
+static BOOL ddraw_match_surface_desc(const DDSURFACEDESC2 *requested, const DDSURFACEDESC2 *provided)
+{
+    struct compare_info
+    {
+        DWORD flag;
+        ptrdiff_t offset;
+        size_t size;
+    };
+
+#define CMP(FLAG, FIELD)                                \
+        { DDSD_##FLAG, offsetof(DDSURFACEDESC2, FIELD), \
+          sizeof(((DDSURFACEDESC2 *)(NULL))->FIELD) }
+
+    static const struct compare_info compare[] =
+    {
+        CMP(ALPHABITDEPTH, dwAlphaBitDepth),
+        CMP(BACKBUFFERCOUNT, u5.dwBackBufferCount),
+        CMP(CAPS, ddsCaps),
         CMP(CKDESTBLT, ddckCKDestBlt),
         CMP(CKDESTOVERLAY, u3 /* ddckCKDestOverlay */),
         CMP(CKSRCBLT, ddckCKSrcBlt),
@@ -2717,6 +3614,21 @@ IDirectDrawImpl_DDSD_Match(const DDSURFACEDESC2* requested,
 #undef DDENUMSURFACES_SEARCHTYPE
 #undef DDENUMSURFACES_MATCHTYPE
 
+struct surfacescallback_context
+{
+    LPDDENUMSURFACESCALLBACK func;
+    void *context;
+};
+
+static HRESULT CALLBACK EnumSurfacesCallbackThunk(IDirectDrawSurface7 *surface,
+        DDSURFACEDESC2 *surface_desc, void *context)
+{
+    struct surfacescallback_context *cbcontext = context;
+
+    return cbcontext->func((IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)surface)->IDirectDrawSurface3_vtbl,
+            (DDSURFACEDESC *)surface_desc, cbcontext->context);
+}
+
 /*****************************************************************************
  * IDirectDraw7::EnumSurfaces
  *
@@ -2736,12 +3648,8 @@ IDirectDrawImpl_DDSD_Match(const DDSURFACEDESC2* requested,
  *  DD_OK on success
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_EnumSurfaces(IDirectDraw7 *iface,
-                             DWORD Flags,
-                             DDSURFACEDESC2 *DDSD,
-                             void *Context,
-                             LPDDENUMSURFACESCALLBACK7 Callback)
+static HRESULT WINAPI ddraw7_EnumSurfaces(IDirectDraw7 *iface, DWORD Flags,
+        DDSURFACEDESC2 *DDSD, void *Context, LPDDENUMSURFACESCALLBACK7 Callback)
 {
     /* The surface enumeration is handled by WineDDraw,
      * because it keeps track of all surfaces attached to
@@ -2755,10 +3663,12 @@ IDirectDrawImpl_EnumSurfaces(IDirectDraw7 *iface,
     DDSURFACEDESC2 desc;
     struct list *entry, *entry2;
 
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, Flags, DDSD, Context, Callback);
+
     all = Flags & DDENUMSURFACES_ALL;
     nomatch = Flags & DDENUMSURFACES_NOMATCH;
 
-    TRACE("(%p)->(%x,%p,%p,%p)\n", This, Flags, DDSD, Context, Callback);
     EnterCriticalSection(&ddraw_cs);
 
     if(!Callback)
@@ -2771,7 +3681,7 @@ IDirectDrawImpl_EnumSurfaces(IDirectDraw7 *iface,
     LIST_FOR_EACH_SAFE(entry, entry2, &This->surface_list)
     {
         surf = LIST_ENTRY(entry, IDirectDrawSurfaceImpl, surface_list_entry);
-        if (all || (nomatch != IDirectDrawImpl_DDSD_Match(DDSD, &surf->surface_desc)))
+        if (all || (nomatch != ddraw_match_surface_desc(DDSD, &surf->surface_desc)))
         {
             desc = surf->surface_desc;
             IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)surf);
@@ -2786,391 +3696,1724 @@ IDirectDrawImpl_EnumSurfaces(IDirectDraw7 *iface,
     return DD_OK;
 }
 
-static HRESULT WINAPI
-findRenderTarget(IDirectDrawSurface7 *surface,
-                 DDSURFACEDESC2 *desc,
-                 void *ctx)
+static HRESULT WINAPI ddraw4_EnumSurfaces(IDirectDraw4 *iface, DWORD flags,
+        DDSURFACEDESC2 *surface_desc, void *context, LPDDENUMSURFACESCALLBACK2 callback)
 {
-    IDirectDrawSurfaceImpl *surf = (IDirectDrawSurfaceImpl *)surface;
-    IDirectDrawSurfaceImpl **target = ctx;
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, flags, surface_desc, context, callback);
 
-    if(!surf->isRenderTarget) {
-        *target = surf;
-        IDirectDrawSurface7_Release(surface);
-        return DDENUMRET_CANCEL;
+    return ddraw7_EnumSurfaces((IDirectDraw7 *)ddraw_from_ddraw4(iface),
+            flags, surface_desc, context, (LPDDENUMSURFACESCALLBACK7)callback);
+}
+
+static HRESULT WINAPI ddraw3_EnumSurfaces(IDirectDraw3 *iface, DWORD flags,
+        DDSURFACEDESC *surface_desc, void *context, LPDDENUMSURFACESCALLBACK callback)
+{
+    struct surfacescallback_context cbcontext;
+
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, flags, surface_desc, context, callback);
+
+    cbcontext.func = callback;
+    cbcontext.context = context;
+
+    return ddraw7_EnumSurfaces((IDirectDraw7 *)ddraw_from_ddraw3(iface), flags,
+            (DDSURFACEDESC2 *)surface_desc, &cbcontext, EnumSurfacesCallbackThunk);
+}
+
+static HRESULT WINAPI ddraw2_EnumSurfaces(IDirectDraw2 *iface, DWORD flags,
+        DDSURFACEDESC *surface_desc, void *context, LPDDENUMSURFACESCALLBACK callback)
+{
+    struct surfacescallback_context cbcontext;
+
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, flags, surface_desc, context, callback);
+
+    cbcontext.func = callback;
+    cbcontext.context = context;
+
+    return ddraw7_EnumSurfaces((IDirectDraw7 *)ddraw_from_ddraw2(iface), flags,
+            (DDSURFACEDESC2 *)surface_desc, &cbcontext, EnumSurfacesCallbackThunk);
+}
+
+static HRESULT WINAPI ddraw1_EnumSurfaces(IDirectDraw *iface, DWORD flags,
+        DDSURFACEDESC *surface_desc, void *context, LPDDENUMSURFACESCALLBACK callback)
+{
+    struct surfacescallback_context cbcontext;
+
+    TRACE("iface %p, flags %#x, surface_desc %p, context %p, callback %p.\n",
+            iface, flags, surface_desc, context, callback);
+
+    cbcontext.func = callback;
+    cbcontext.context = context;
+
+    return ddraw7_EnumSurfaces((IDirectDraw7 *)ddraw_from_ddraw1(iface), flags,
+            (DDSURFACEDESC2 *)surface_desc, &cbcontext, EnumSurfacesCallbackThunk);
+}
+
+/*****************************************************************************
+ * DirectDrawCreateClipper (DDRAW.@)
+ *
+ * Creates a new IDirectDrawClipper object.
+ *
+ * Params:
+ *  Clipper: Address to write the interface pointer to
+ *  UnkOuter: For aggregation support, which ddraw doesn't have. Has to be
+ *            NULL
+ *
+ * Returns:
+ *  CLASS_E_NOAGGREGATION if UnkOuter != NULL
+ *  E_OUTOFMEMORY if allocating the object failed
+ *
+ *****************************************************************************/
+HRESULT WINAPI
+DirectDrawCreateClipper(DWORD Flags,
+                        LPDIRECTDRAWCLIPPER *Clipper,
+                        IUnknown *UnkOuter)
+{
+    IDirectDrawClipperImpl* object;
+    HRESULT hr;
+
+    TRACE("flags %#x, clipper %p, outer_unknown %p.\n",
+            Flags, Clipper, UnkOuter);
+
+    EnterCriticalSection(&ddraw_cs);
+    if (UnkOuter != NULL)
+    {
+        LeaveCriticalSection(&ddraw_cs);
+        return CLASS_E_NOAGGREGATION;
     }
 
-    /* Recurse into the surface tree */
-    IDirectDrawSurface7_EnumAttachedSurfaces(surface, ctx, findRenderTarget);
+    if (!LoadWineD3D())
+    {
+        LeaveCriticalSection(&ddraw_cs);
+        return DDERR_NODIRECTDRAWSUPPORT;
+    }
 
-    IDirectDrawSurface7_Release(surface);
-    if(*target) return DDENUMRET_CANCEL;
-    else return DDENUMRET_OK; /* Continue with the next neighbor surface */
+    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
+                     sizeof(IDirectDrawClipperImpl));
+    if (object == NULL)
+    {
+        LeaveCriticalSection(&ddraw_cs);
+        return E_OUTOFMEMORY;
+    }
+
+    hr = ddraw_clipper_init(object);
+    if (FAILED(hr))
+    {
+        WARN("Failed to initialize clipper, hr %#x.\n", hr);
+        HeapFree(GetProcessHeap(), 0, object);
+        LeaveCriticalSection(&ddraw_cs);
+        return hr;
+    }
+
+    TRACE("Created clipper %p.\n", object);
+    *Clipper = (IDirectDrawClipper *) object;
+    LeaveCriticalSection(&ddraw_cs);
+    return DD_OK;
+}
+
+/*****************************************************************************
+ * IDirectDraw7::CreateClipper
+ *
+ * Creates a DDraw clipper. See DirectDrawCreateClipper for details
+ *
+ *****************************************************************************/
+static HRESULT WINAPI ddraw7_CreateClipper(IDirectDraw7 *iface, DWORD Flags,
+        IDirectDrawClipper **Clipper, IUnknown *UnkOuter)
+{
+    TRACE("iface %p, flags %#x, clipper %p, outer_unknown %p.\n",
+            iface, Flags, Clipper, UnkOuter);
+
+    return DirectDrawCreateClipper(Flags, Clipper, UnkOuter);
+}
+
+static HRESULT WINAPI ddraw4_CreateClipper(IDirectDraw4 *iface,
+        DWORD flags, IDirectDrawClipper **clipper, IUnknown *outer_unknown)
+{
+    TRACE("iface %p, flags %#x, clipper %p, outer_unknown %p.\n",
+            iface, flags, clipper, outer_unknown);
+
+    return ddraw7_CreateClipper((IDirectDraw7 *)ddraw_from_ddraw4(iface), flags, clipper, outer_unknown);
+}
+
+static HRESULT WINAPI ddraw3_CreateClipper(IDirectDraw3 *iface,
+        DWORD flags, IDirectDrawClipper **clipper, IUnknown *outer_unknown)
+{
+    TRACE("iface %p, flags %#x, clipper %p, outer_unknown %p.\n",
+            iface, flags, clipper, outer_unknown);
+
+    return ddraw7_CreateClipper((IDirectDraw7 *)ddraw_from_ddraw3(iface), flags, clipper, outer_unknown);
+}
+
+static HRESULT WINAPI ddraw2_CreateClipper(IDirectDraw2 *iface,
+        DWORD flags, IDirectDrawClipper **clipper, IUnknown *outer_unknown)
+{
+    TRACE("iface %p, flags %#x, clipper %p, outer_unknown %p.\n",
+            iface, flags, clipper, outer_unknown);
+
+    return ddraw7_CreateClipper((IDirectDraw7 *)ddraw_from_ddraw2(iface), flags, clipper, outer_unknown);
+}
+
+static HRESULT WINAPI ddraw1_CreateClipper(IDirectDraw *iface,
+        DWORD flags, IDirectDrawClipper **clipper, IUnknown *outer_unknown)
+{
+    TRACE("iface %p, flags %#x, clipper %p, outer_unknown %p.\n",
+            iface, flags, clipper, outer_unknown);
+
+    return ddraw7_CreateClipper((IDirectDraw7 *)ddraw_from_ddraw1(iface), flags, clipper, outer_unknown);
+}
+
+/*****************************************************************************
+ * IDirectDraw7::CreatePalette
+ *
+ * Creates a new IDirectDrawPalette object
+ *
+ * Params:
+ *  Flags: The flags for the new clipper
+ *  ColorTable: Color table to assign to the new clipper
+ *  Palette: Address to write the interface pointer to
+ *  UnkOuter: For aggregation support, which ddraw doesn't have. Has to be
+ *            NULL
+ *
+ * Returns:
+ *  CLASS_E_NOAGGREGATION if UnkOuter != NULL
+ *  E_OUTOFMEMORY if allocating the object failed
+ *
+ *****************************************************************************/
+static HRESULT WINAPI ddraw7_CreatePalette(IDirectDraw7 *iface, DWORD Flags,
+        PALETTEENTRY *ColorTable, IDirectDrawPalette **Palette, IUnknown *pUnkOuter)
+{
+    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
+    IDirectDrawPaletteImpl *object;
+    HRESULT hr;
+
+    TRACE("iface %p, flags %#x, color_table %p, palette %p, outer_unknown %p.\n",
+            iface, Flags, ColorTable, Palette, pUnkOuter);
+
+    EnterCriticalSection(&ddraw_cs);
+    if(pUnkOuter != NULL)
+    {
+        WARN("pUnkOuter is %p, returning CLASS_E_NOAGGREGATION\n", pUnkOuter);
+        LeaveCriticalSection(&ddraw_cs);
+        return CLASS_E_NOAGGREGATION;
+    }
+
+    /* The refcount test shows that a cooplevel is required for this */
+    if(!This->cooperative_level)
+    {
+        WARN("No cooperative level set, returning DDERR_NOCOOPERATIVELEVELSET\n");
+        LeaveCriticalSection(&ddraw_cs);
+        return DDERR_NOCOOPERATIVELEVELSET;
+    }
+
+    object = HeapAlloc(GetProcessHeap(), 0, sizeof(IDirectDrawPaletteImpl));
+    if(!object)
+    {
+        ERR("Out of memory when allocating memory for a palette implementation\n");
+        LeaveCriticalSection(&ddraw_cs);
+        return E_OUTOFMEMORY;
+    }
+
+    hr = ddraw_palette_init(object, This, Flags, ColorTable);
+    if (FAILED(hr))
+    {
+        WARN("Failed to initialize palette, hr %#x.\n", hr);
+        HeapFree(GetProcessHeap(), 0, object);
+        LeaveCriticalSection(&ddraw_cs);
+        return hr;
+    }
+
+    TRACE("Created palette %p.\n", object);
+    *Palette = (IDirectDrawPalette *)object;
+    LeaveCriticalSection(&ddraw_cs);
+    return DD_OK;
+}
+
+static HRESULT WINAPI ddraw4_CreatePalette(IDirectDraw4 *iface, DWORD flags,
+        PALETTEENTRY *entries, IDirectDrawPalette **palette, IUnknown *outer_unknown)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw4(iface);
+    HRESULT hr;
+
+    TRACE("iface %p, flags %#x, entries %p, palette %p, outer_unknown %p.\n",
+            iface, flags, entries, palette, outer_unknown);
+
+    hr = ddraw7_CreatePalette((IDirectDraw7 *)ddraw, flags, entries, palette, outer_unknown);
+    if (SUCCEEDED(hr) && *palette)
+    {
+        IDirectDrawPaletteImpl *impl = (IDirectDrawPaletteImpl *)*palette;
+        IDirectDraw7_Release((IDirectDraw7 *)ddraw);
+        IDirectDraw4_AddRef(iface);
+        impl->ifaceToRelease = (IUnknown *)iface;
+    }
+    return hr;
+}
+
+static HRESULT WINAPI ddraw3_CreatePalette(IDirectDraw3 *iface, DWORD flags,
+        PALETTEENTRY *entries, IDirectDrawPalette **palette, IUnknown *outer_unknown)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw3(iface);
+    HRESULT hr;
+
+    TRACE("iface %p, flags %#x, entries %p, palette %p, outer_unknown %p.\n",
+            iface, flags, entries, palette, outer_unknown);
+
+    hr = ddraw7_CreatePalette((IDirectDraw7 *)ddraw, flags, entries, palette, outer_unknown);
+    if (SUCCEEDED(hr) && *palette)
+    {
+        IDirectDrawPaletteImpl *impl = (IDirectDrawPaletteImpl *)*palette;
+        IDirectDraw7_Release((IDirectDraw7 *)ddraw);
+        IDirectDraw4_AddRef(iface);
+        impl->ifaceToRelease = (IUnknown *)iface;
+    }
+
+    return hr;
+}
+
+static HRESULT WINAPI ddraw2_CreatePalette(IDirectDraw2 *iface, DWORD flags,
+        PALETTEENTRY *entries, IDirectDrawPalette **palette, IUnknown *outer_unknown)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw2(iface);
+    HRESULT hr;
+
+    TRACE("iface %p, flags %#x, entries %p, palette %p, outer_unknown %p.\n",
+            iface, flags, entries, palette, outer_unknown);
+
+    hr = ddraw7_CreatePalette((IDirectDraw7 *)ddraw, flags, entries, palette, outer_unknown);
+    if (SUCCEEDED(hr) && *palette)
+    {
+        IDirectDrawPaletteImpl *impl = (IDirectDrawPaletteImpl *)*palette;
+        IDirectDraw7_Release((IDirectDraw7 *)ddraw);
+        impl->ifaceToRelease = NULL;
+    }
+
+    return hr;
+}
+
+static HRESULT WINAPI ddraw1_CreatePalette(IDirectDraw *iface, DWORD flags,
+        PALETTEENTRY *entries, IDirectDrawPalette **palette, IUnknown *outer_unknown)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_ddraw1(iface);
+    HRESULT hr;
+
+    TRACE("iface %p, flags %#x, entries %p, palette %p, outer_unknown %p.\n",
+            iface, flags, entries, palette, outer_unknown);
+
+    hr = ddraw7_CreatePalette((IDirectDraw7 *)ddraw, flags, entries, palette, outer_unknown);
+    if (SUCCEEDED(hr) && *palette)
+    {
+        IDirectDrawPaletteImpl *impl = (IDirectDrawPaletteImpl *)*palette;
+        IDirectDraw7_Release((IDirectDraw7 *)ddraw);
+        impl->ifaceToRelease = NULL;
+    }
+
+    return hr;
+}
+
+/*****************************************************************************
+ * IDirectDraw7::DuplicateSurface
+ *
+ * Duplicates a surface. The surface memory points to the same memory as
+ * the original surface, and it's released when the last surface referencing
+ * it is released. I guess that's beyond Wine's surface management right now
+ * (Idea: create a new DDraw surface with the same WineD3DSurface. I need a
+ * test application to implement this)
+ *
+ * Params:
+ *  Src: Address of the source surface
+ *  Dest: Address to write the new surface pointer to
+ *
+ * Returns:
+ *  See IDirectDraw7::CreateSurface
+ *
+ *****************************************************************************/
+static HRESULT WINAPI ddraw7_DuplicateSurface(IDirectDraw7 *iface,
+        IDirectDrawSurface7 *Src, IDirectDrawSurface7 **Dest)
+{
+    IDirectDrawSurfaceImpl *Surf = (IDirectDrawSurfaceImpl *)Src;
+
+    FIXME("iface %p, src %p, dst %p partial stub!\n", iface, Src, Dest);
+
+    /* For now, simply create a new, independent surface */
+    return IDirectDraw7_CreateSurface(iface,
+                                      &Surf->surface_desc,
+                                      Dest,
+                                      NULL);
+}
+
+static HRESULT WINAPI ddraw4_DuplicateSurface(IDirectDraw4 *iface,
+        IDirectDrawSurface4 *src, IDirectDrawSurface4 **dst)
+{
+    TRACE("iface %p, src %p, dst %p.\n", iface, src, dst);
+
+    return ddraw7_DuplicateSurface((IDirectDraw7 *)ddraw_from_ddraw4(iface),
+            (IDirectDrawSurface7 *)src, (IDirectDrawSurface7 **)dst);
+}
+
+static HRESULT WINAPI ddraw3_DuplicateSurface(IDirectDraw3 *iface,
+        IDirectDrawSurface *src, IDirectDrawSurface **dst)
+{
+    IDirectDrawSurface7 *src7, *dst7;
+    HRESULT hr;
+
+    TRACE("iface %p, src %p, dst %p.\n", iface, src, dst);
+    src7 = (IDirectDrawSurface7 *)surface_from_surface3((IDirectDrawSurface3 *)src);
+    hr = ddraw7_DuplicateSurface((IDirectDraw7 *)ddraw_from_ddraw3(iface), src7, &dst7);
+    if (FAILED(hr))
+        return hr;
+    *dst = (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)dst7)->IDirectDrawSurface3_vtbl;
+    return hr;
+}
+
+static HRESULT WINAPI ddraw2_DuplicateSurface(IDirectDraw2 *iface,
+        IDirectDrawSurface *src, IDirectDrawSurface **dst)
+{
+    IDirectDrawSurface7 *src7, *dst7;
+    HRESULT hr;
+
+    TRACE("iface %p, src %p, dst %p.\n", iface, src, dst);
+    src7 = (IDirectDrawSurface7 *)surface_from_surface3((IDirectDrawSurface3 *)src);
+    hr = ddraw7_DuplicateSurface((IDirectDraw7 *)ddraw_from_ddraw2(iface), src7, &dst7);
+    if (FAILED(hr))
+        return hr;
+    *dst = (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)dst7)->IDirectDrawSurface3_vtbl;
+    return hr;
+}
+
+static HRESULT WINAPI ddraw1_DuplicateSurface(IDirectDraw *iface,
+        IDirectDrawSurface *src, IDirectDrawSurface **dst)
+{
+    IDirectDrawSurface7 *src7, *dst7;
+    HRESULT hr;
+
+    TRACE("iface %p, src %p, dst %p.\n", iface, src, dst);
+    src7 = (IDirectDrawSurface7 *)surface_from_surface3((IDirectDrawSurface3 *)src);
+    hr = ddraw7_DuplicateSurface((IDirectDraw7 *)ddraw_from_ddraw1(iface), src7, &dst7);
+    if (FAILED(hr))
+        return hr;
+    *dst = (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)dst7)->IDirectDrawSurface3_vtbl;
+    return hr;
+}
+
+/*****************************************************************************
+ * IDirect3D7::EnumDevices
+ *
+ * The EnumDevices method for IDirect3D7. It enumerates all supported
+ * D3D7 devices. Currently the T&L, HAL and RGB devices are enumerated.
+ *
+ * Params:
+ *  callback: Function to call for each enumerated device
+ *  context: Pointer to pass back to the app
+ *
+ * Returns:
+ *  D3D_OK, or the return value of the GetCaps call
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d7_EnumDevices(IDirect3D7 *iface, LPD3DENUMDEVICESCALLBACK7 callback, void *context)
+{
+    char interface_name_tnl[] = "WINE Direct3D7 Hardware Transform and Lighting acceleration using WineD3D";
+    char device_name_tnl[] = "Wine D3D7 T&L HAL";
+    char interface_name_hal[] = "WINE Direct3D7 Hardware acceleration using WineD3D";
+    char device_name_hal[] = "Wine D3D7 HAL";
+    char interface_name_rgb[] = "WINE Direct3D7 RGB Software Emulation using WineD3D";
+    char device_name_rgb[] = "Wine D3D7 RGB";
+
+    IDirectDrawImpl *ddraw = ddraw_from_d3d7(iface);
+    D3DDEVICEDESC7 device_desc7;
+    D3DDEVICEDESC device_desc1;
+    HRESULT hr;
+
+    TRACE("iface %p, callback %p, context %p.\n", iface, callback, context);
+
+    EnterCriticalSection(&ddraw_cs);
+
+    hr = IDirect3DImpl_GetCaps(ddraw->wineD3D, &device_desc1, &device_desc7);
+    if (hr != D3D_OK)
+    {
+        LeaveCriticalSection(&ddraw_cs);
+        return hr;
+    }
+    callback(interface_name_tnl, device_name_tnl, &device_desc7, context);
+
+    device_desc7.deviceGUID = IID_IDirect3DHALDevice;
+    callback(interface_name_hal, device_name_hal, &device_desc7, context);
+
+    device_desc7.deviceGUID = IID_IDirect3DRGBDevice;
+    callback(interface_name_rgb, device_name_rgb, &device_desc7, context);
+
+    TRACE("End of enumeration.\n");
+
+    LeaveCriticalSection(&ddraw_cs);
+
+    return D3D_OK;
+}
+
+/*****************************************************************************
+ * IDirect3D3::EnumDevices
+ *
+ * Enumerates all supported Direct3DDevice interfaces. This is the
+ * implementation for Direct3D 1 to Direc3D 3, Version 7 has its own.
+ *
+ * Version 1, 2 and 3
+ *
+ * Params:
+ *  callback: Application-provided routine to call for each enumerated device
+ *  Context: Pointer to pass to the callback
+ *
+ * Returns:
+ *  D3D_OK on success,
+ *  The result of IDirect3DImpl_GetCaps if it failed
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d3_EnumDevices(IDirect3D3 *iface, LPD3DENUMDEVICESCALLBACK callback, void *context)
+{
+    static CHAR wined3d_description[] = "Wine D3DDevice using WineD3D and OpenGL";
+
+    IDirectDrawImpl *ddraw = ddraw_from_d3d3(iface);
+    D3DDEVICEDESC device_desc1, hal_desc, hel_desc;
+    D3DDEVICEDESC7 device_desc7;
+    HRESULT hr;
+
+    /* Some games (Motoracer 2 demo) have the bad idea to modify the device
+     * name string. Let's put the string in a sufficiently sized array in
+     * writable memory. */
+    char device_name[50];
+    strcpy(device_name,"Direct3D HEL");
+
+    TRACE("iface %p, callback %p, context %p.\n", iface, callback, context);
+
+    EnterCriticalSection(&ddraw_cs);
+
+    hr = IDirect3DImpl_GetCaps(ddraw->wineD3D, &device_desc1, &device_desc7);
+    if (hr != D3D_OK)
+    {
+        LeaveCriticalSection(&ddraw_cs);
+        return hr;
+    }
+
+    /* Do I have to enumerate the reference id? Note from old d3d7:
+     * "It seems that enumerating the reference IID on Direct3D 1 games
+     * (AvP / Motoracer2) breaks them". So do not enumerate this iid in V1
+     *
+     * There's a registry key HKLM\Software\Microsoft\Direct3D\Drivers,
+     * EnumReference which enables / disables enumerating the reference
+     * rasterizer. It's a DWORD, 0 means disabled, 2 means enabled. The
+     * enablerefrast.reg and disablerefrast.reg files in the DirectX 7.0 sdk
+     * demo directory suggest this.
+     *
+     * Some games(GTA 2) seem to use the second enumerated device, so I have
+     * to enumerate at least 2 devices. So enumerate the reference device to
+     * have 2 devices.
+     *
+     * Other games (Rollcage) tell emulation and hal device apart by certain
+     * flags. Rollcage expects D3DPTEXTURECAPS_POW2 to be set (yeah, it is a
+     * limitation flag), and it refuses all devices that have the perspective
+     * flag set. This way it refuses the emulation device, and HAL devices
+     * never have POW2 unset in d3d7 on windows. */
+    if (ddraw->d3dversion != 1)
+    {
+        static CHAR reference_description[] = "RGB Direct3D emulation";
+
+        TRACE("Enumerating WineD3D D3DDevice interface.\n");
+        hal_desc = device_desc1;
+        hel_desc = device_desc1;
+        /* The rgb device has the pow2 flag set in the hel caps, but not in the hal caps. */
+        hal_desc.dpcLineCaps.dwTextureCaps &= ~(D3DPTEXTURECAPS_POW2
+                | D3DPTEXTURECAPS_NONPOW2CONDITIONAL | D3DPTEXTURECAPS_PERSPECTIVE);
+        hal_desc.dpcTriCaps.dwTextureCaps &= ~(D3DPTEXTURECAPS_POW2
+                | D3DPTEXTURECAPS_NONPOW2CONDITIONAL | D3DPTEXTURECAPS_PERSPECTIVE);
+        hr = callback((GUID *)&IID_IDirect3DRGBDevice, reference_description,
+                device_name, &hal_desc, &hel_desc, context);
+        if (hr != D3DENUMRET_OK)
+        {
+            TRACE("Application cancelled the enumeration.\n");
+            LeaveCriticalSection(&ddraw_cs);
+            return D3D_OK;
+        }
+    }
+
+    strcpy(device_name,"Direct3D HAL");
+
+    TRACE("Enumerating HAL Direct3D device.\n");
+    hal_desc = device_desc1;
+    hel_desc = device_desc1;
+    /* The hal device does not have the pow2 flag set in hel, but in hal. */
+    hel_desc.dpcLineCaps.dwTextureCaps &= ~(D3DPTEXTURECAPS_POW2
+            | D3DPTEXTURECAPS_NONPOW2CONDITIONAL | D3DPTEXTURECAPS_PERSPECTIVE);
+    hel_desc.dpcTriCaps.dwTextureCaps &= ~(D3DPTEXTURECAPS_POW2
+            | D3DPTEXTURECAPS_NONPOW2CONDITIONAL | D3DPTEXTURECAPS_PERSPECTIVE);
+    hr = callback((GUID *)&IID_IDirect3DHALDevice, wined3d_description,
+            device_name, &hal_desc, &hel_desc, context);
+    if (hr != D3DENUMRET_OK)
+    {
+        TRACE("Application cancelled the enumeration.\n");
+        LeaveCriticalSection(&ddraw_cs);
+        return D3D_OK;
+    }
+
+    TRACE("End of enumeration.\n");
+
+    LeaveCriticalSection(&ddraw_cs);
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d2_EnumDevices(IDirect3D2 *iface, LPD3DENUMDEVICESCALLBACK callback, void *context)
+{
+    TRACE("iface %p, callback %p, context %p.\n", iface, callback, context);
+
+    return d3d3_EnumDevices((IDirect3D3 *)&ddraw_from_d3d2(iface)->IDirect3D3_vtbl, callback, context);
+}
+
+static HRESULT WINAPI d3d1_EnumDevices(IDirect3D *iface, LPD3DENUMDEVICESCALLBACK callback, void *context)
+{
+    TRACE("iface %p, callback %p, context %p.\n", iface, callback, context);
+
+    return d3d3_EnumDevices((IDirect3D3 *)&ddraw_from_d3d1(iface)->IDirect3D3_vtbl, callback, context);
+}
+
+/*****************************************************************************
+ * IDirect3D3::CreateLight
+ *
+ * Creates an IDirect3DLight interface. This interface is used in
+ * Direct3D3 or earlier for lighting. In Direct3D7 it has been replaced
+ * by the DIRECT3DLIGHT7 structure. Wine's Direct3DLight implementation
+ * uses the IDirect3DDevice7 interface with D3D7 lights.
+ *
+ * Version 1, 2 and 3
+ *
+ * Params:
+ *  light: Address to store the new interface pointer
+ *  outer_unknown: Basically for aggregation, but ddraw doesn't support it.
+ *                 Must be NULL
+ *
+ * Returns:
+ *  D3D_OK on success
+ *  DDERR_OUTOFMEMORY if memory allocation failed
+ *  CLASS_E_NOAGGREGATION if outer_unknown != NULL
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d3_CreateLight(IDirect3D3 *iface, IDirect3DLight **light, IUnknown *outer_unknown)
+{
+    IDirect3DLightImpl *object;
+
+    TRACE("iface %p, light %p, outer_unknown %p.\n", iface, light, outer_unknown);
+
+    if (outer_unknown) return CLASS_E_NOAGGREGATION;
+
+    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
+    if (!object)
+    {
+        ERR("Failed to allocate light memory.\n");
+        return DDERR_OUTOFMEMORY;
+    }
+
+    d3d_light_init(object, ddraw_from_d3d3(iface));
+
+    TRACE("Created light %p.\n", object);
+    *light = (IDirect3DLight *)object;
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d2_CreateLight(IDirect3D2 *iface, IDirect3DLight **light, IUnknown *outer_unknown)
+{
+    TRACE("iface %p, light %p, outer_unknown %p.\n", iface, light, outer_unknown);
+
+    return d3d3_CreateLight((IDirect3D3 *)&ddraw_from_d3d2(iface)->IDirect3D3_vtbl, light, outer_unknown);
+}
+
+static HRESULT WINAPI d3d1_CreateLight(IDirect3D *iface, IDirect3DLight **light, IUnknown *outer_unknown)
+{
+    TRACE("iface %p, light %p, outer_unknown %p.\n", iface, light, outer_unknown);
+
+    return d3d3_CreateLight((IDirect3D3 *)&ddraw_from_d3d1(iface)->IDirect3D3_vtbl, light, outer_unknown);
+}
+
+/*****************************************************************************
+ * IDirect3D3::CreateMaterial
+ *
+ * Creates an IDirect3DMaterial interface. This interface is used by Direct3D3
+ * and older versions. The IDirect3DMaterial implementation wraps its
+ * functionality to IDirect3DDevice7::SetMaterial and friends.
+ *
+ * Version 1, 2 and 3
+ *
+ * Params:
+ *  material: Address to store the new interface's pointer to
+ *  outer_unknown: Basically for aggregation, but ddraw doesn't support it.
+ *                 Must be NULL
+ *
+ * Returns:
+ *  D3D_OK on success
+ *  DDERR_OUTOFMEMORY if memory allocation failed
+ *  CLASS_E_NOAGGREGATION if outer_unknown != NULL
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d3_CreateMaterial(IDirect3D3 *iface, IDirect3DMaterial3 **material, IUnknown *outer_unknown)
+{
+    IDirect3DMaterialImpl *object;
+
+    TRACE("iface %p, material %p, outer_unknown %p.\n", iface, material, outer_unknown);
+
+    if (outer_unknown) return CLASS_E_NOAGGREGATION;
+
+    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
+    if (!object)
+    {
+        ERR("Failed to allocate material memory.\n");
+        return DDERR_OUTOFMEMORY;
+    }
+
+    d3d_material_init(object, ddraw_from_d3d3(iface));
+
+    TRACE("Created material %p.\n", object);
+    *material = (IDirect3DMaterial3 *)object;
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d2_CreateMaterial(IDirect3D2 *iface, IDirect3DMaterial2 **material, IUnknown *outer_unknown)
+{
+    IDirect3DMaterial3 *material3;
+    HRESULT hr;
+
+    TRACE("iface %p, material %p, outer_unknown %p.\n", iface, material, outer_unknown);
+
+    hr = d3d3_CreateMaterial((IDirect3D3 *)&ddraw_from_d3d2(iface)->IDirect3D3_vtbl, &material3, outer_unknown);
+    *material = material3 ? (IDirect3DMaterial2 *)&((IDirect3DMaterialImpl *)material3)->IDirect3DMaterial2_vtbl : NULL;
+
+    TRACE("Returning material %p.\n", *material);
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d1_CreateMaterial(IDirect3D *iface, IDirect3DMaterial **material, IUnknown *outer_unknown)
+{
+    IDirect3DMaterial3 *material3;
+    HRESULT hr;
+
+    TRACE("iface %p, material %p, outer_unknown %p.\n", iface, material, outer_unknown);
+
+    hr = d3d3_CreateMaterial((IDirect3D3 *)&ddraw_from_d3d1(iface)->IDirect3D3_vtbl, &material3, outer_unknown);
+    *material = material3 ? (IDirect3DMaterial *)&((IDirect3DMaterialImpl *)material3)->IDirect3DMaterial_vtbl : NULL;
+
+    TRACE("Returning material %p.\n", *material);
+
+    return hr;
+}
+
+/*****************************************************************************
+ * IDirect3D3::CreateViewport
+ *
+ * Creates an IDirect3DViewport interface. This interface is used
+ * by Direct3D and earlier versions for Viewport management. In Direct3D7
+ * it has been replaced by a viewport structure and
+ * IDirect3DDevice7::*Viewport. Wine's IDirect3DViewport implementation
+ * uses the IDirect3DDevice7 methods for its functionality
+ *
+ * Params:
+ *  Viewport: Address to store the new interface pointer
+ *  outer_unknown: Basically for aggregation, but ddraw doesn't support it.
+ *                 Must be NULL
+ *
+ * Returns:
+ *  D3D_OK on success
+ *  DDERR_OUTOFMEMORY if memory allocation failed
+ *  CLASS_E_NOAGGREGATION if outer_unknown != NULL
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d3_CreateViewport(IDirect3D3 *iface, IDirect3DViewport3 **viewport, IUnknown *outer_unknown)
+{
+    IDirect3DViewportImpl *object;
+
+    TRACE("iface %p, viewport %p, outer_unknown %p.\n", iface, viewport, outer_unknown);
+
+    if (outer_unknown) return CLASS_E_NOAGGREGATION;
+
+    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
+    if (!object)
+    {
+        ERR("Failed to allocate viewport memory.\n");
+        return DDERR_OUTOFMEMORY;
+    }
+
+    d3d_viewport_init(object, ddraw_from_d3d3(iface));
+
+    TRACE("Created viewport %p.\n", object);
+    *viewport = (IDirect3DViewport3 *)object;
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d2_CreateViewport(IDirect3D2 *iface, IDirect3DViewport2 **viewport, IUnknown *outer_unknown)
+{
+    TRACE("iface %p, viewport %p, outer_unknown %p.\n", iface, viewport, outer_unknown);
+
+    return d3d3_CreateViewport((IDirect3D3 *)&ddraw_from_d3d2(iface)->IDirect3D3_vtbl,
+            (IDirect3DViewport3 **)viewport, outer_unknown);
+}
+
+static HRESULT WINAPI d3d1_CreateViewport(IDirect3D *iface, IDirect3DViewport **viewport, IUnknown *outer_unknown)
+{
+    TRACE("iface %p, viewport %p, outer_unknown %p.\n", iface, viewport, outer_unknown);
+
+    return d3d3_CreateViewport((IDirect3D3 *)&ddraw_from_d3d1(iface)->IDirect3D3_vtbl,
+            (IDirect3DViewport3 **)viewport, outer_unknown);
+}
+
+/*****************************************************************************
+ * IDirect3D3::FindDevice
+ *
+ * This method finds a device with the requested properties and returns a
+ * device description
+ *
+ * Verion 1, 2 and 3
+ * Params:
+ *  fds: Describes the requested device characteristics
+ *  fdr: Returns the device description
+ *
+ * Returns:
+ *  D3D_OK on success
+ *  DDERR_INVALIDPARAMS if no device was found
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d3_FindDevice(IDirect3D3 *iface, D3DFINDDEVICESEARCH *fds, D3DFINDDEVICERESULT *fdr)
+{
+    IDirectDrawImpl *ddraw = ddraw_from_d3d3(iface);
+    D3DDEVICEDESC7 desc7;
+    D3DDEVICEDESC desc1;
+    HRESULT hr;
+
+    TRACE("iface %p, fds %p, fdr %p.\n", iface, fds, fdr);
+
+    if (!fds || !fdr) return DDERR_INVALIDPARAMS;
+
+    if (fds->dwSize != sizeof(D3DFINDDEVICESEARCH)
+            || fdr->dwSize != sizeof(D3DFINDDEVICERESULT))
+        return DDERR_INVALIDPARAMS;
+
+    if ((fds->dwFlags & D3DFDS_COLORMODEL)
+            && fds->dcmColorModel != D3DCOLOR_RGB)
+    {
+        WARN("Trying to request a non-RGB D3D color model. Not supported.\n");
+        return DDERR_INVALIDPARAMS; /* No real idea what to return here :-) */
+    }
+
+    if (fds->dwFlags & D3DFDS_GUID)
+    {
+        TRACE("Trying to match guid %s.\n", debugstr_guid(&(fds->guid)));
+        if (!IsEqualGUID(&IID_D3DDEVICE_WineD3D, &fds->guid)
+                && !IsEqualGUID(&IID_IDirect3DHALDevice, &fds->guid)
+                && !IsEqualGUID(&IID_IDirect3DRGBDevice, &fds->guid))
+        {
+            WARN("No match for this GUID.\n");
+            return DDERR_NOTFOUND;
+        }
+    }
+
+    /* Get the caps */
+    hr = IDirect3DImpl_GetCaps(ddraw->wineD3D, &desc1, &desc7);
+    if (hr != D3D_OK) return hr;
+
+    /* Now return our own GUID */
+    fdr->guid = IID_D3DDEVICE_WineD3D;
+    fdr->ddHwDesc = desc1;
+    fdr->ddSwDesc = desc1;
+
+    TRACE("Returning Wine's wined3d device with (undumped) capabilities.\n");
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d2_FindDevice(IDirect3D2 *iface, D3DFINDDEVICESEARCH *fds, D3DFINDDEVICERESULT *fdr)
+{
+    TRACE("iface %p, fds %p, fdr %p.\n", iface, fds, fdr);
+
+    return d3d3_FindDevice((IDirect3D3 *)&ddraw_from_d3d2(iface)->IDirect3D3_vtbl, fds, fdr);
+}
+
+static HRESULT WINAPI d3d1_FindDevice(IDirect3D *iface, D3DFINDDEVICESEARCH *fds, D3DFINDDEVICERESULT *fdr)
+{
+    TRACE("iface %p, fds %p, fdr %p.\n", iface, fds, fdr);
+
+    return d3d3_FindDevice((IDirect3D3 *)&ddraw_from_d3d1(iface)->IDirect3D3_vtbl, fds, fdr);
+}
+
+/*****************************************************************************
+ * IDirect3D7::CreateDevice
+ *
+ * Creates an IDirect3DDevice7 interface.
+ *
+ * Version 2, 3 and 7. IDirect3DDevice 1 interfaces are interfaces to
+ * DirectDraw surfaces and are created with
+ * IDirectDrawSurface::QueryInterface. This method uses CreateDevice to
+ * create the device object and QueryInterfaces for IDirect3DDevice
+ *
+ * Params:
+ *  refiid: IID of the device to create
+ *  Surface: Initial rendertarget
+ *  Device: Address to return the interface pointer
+ *
+ * Returns:
+ *  D3D_OK on success
+ *  DDERR_OUTOFMEMORY if memory allocation failed
+ *  DDERR_INVALIDPARAMS if a device exists already
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d7_CreateDevice(IDirect3D7 *iface, REFCLSID riid,
+        IDirectDrawSurface7 *surface, IDirect3DDevice7 **device)
+{
+    IDirectDrawSurfaceImpl *target = (IDirectDrawSurfaceImpl *)surface;
+    IDirectDrawImpl *ddraw = ddraw_from_d3d7(iface);
+    IDirect3DDeviceImpl *object;
+    HRESULT hr;
+
+    TRACE("iface %p, riid %s, surface %p, device %p.\n", iface, debugstr_guid(riid), surface, device);
+
+    EnterCriticalSection(&ddraw_cs);
+    *device = NULL;
+
+    /* Fail device creation if non-opengl surfaces are used. */
+    if (ddraw->ImplType != SURFACE_OPENGL)
+    {
+        ERR("The application wants to create a Direct3D device, but non-opengl surfaces are set in the registry.\n");
+        ERR("Please set the surface implementation to opengl or autodetection to allow 3D rendering.\n");
+
+        /* We only hit this path if a default surface is set in the registry. Incorrect autodetection
+         * is caught in CreateSurface or QueryInterface. */
+        LeaveCriticalSection(&ddraw_cs);
+        return DDERR_NO3D;
+    }
+
+    if (ddraw->d3ddevice)
+    {
+        FIXME("Only one Direct3D device per DirectDraw object supported.\n");
+        LeaveCriticalSection(&ddraw_cs);
+        return DDERR_INVALIDPARAMS;
+    }
+
+    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
+    if (!object)
+    {
+        ERR("Failed to allocate device memory.\n");
+        LeaveCriticalSection(&ddraw_cs);
+        return DDERR_OUTOFMEMORY;
+    }
+
+    hr = d3d_device_init(object, ddraw, target);
+    if (FAILED(hr))
+    {
+        WARN("Failed to initialize device, hr %#x.\n", hr);
+        HeapFree(GetProcessHeap(), 0, object);
+        LeaveCriticalSection(&ddraw_cs);
+        return hr;
+    }
+
+    TRACE("Created device %p.\n", object);
+    *device = (IDirect3DDevice7 *)object;
+
+    LeaveCriticalSection(&ddraw_cs);
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d3_CreateDevice(IDirect3D3 *iface, REFCLSID riid,
+        IDirectDrawSurface4 *surface, IDirect3DDevice3 **device, IUnknown *outer_unknown)
+{
+    HRESULT hr;
+
+    TRACE("iface %p, riid %s, surface %p, device %p, outer_unknown %p.\n",
+            iface, debugstr_guid(riid), surface, device, outer_unknown);
+
+    if (outer_unknown) return CLASS_E_NOAGGREGATION;
+
+    hr = d3d7_CreateDevice((IDirect3D7 *)&ddraw_from_d3d3(iface)->IDirect3D7_vtbl, riid,
+            (IDirectDrawSurface7 *)surface, (IDirect3DDevice7 **)device);
+    if (*device) *device = (IDirect3DDevice3 *)&((IDirect3DDeviceImpl *)*device)->IDirect3DDevice3_vtbl;
+
+    return hr;
 }
 
-static HRESULT IDirectDrawImpl_CreateGDISwapChain(IDirectDrawImpl *This,
-                                                         IDirectDrawSurfaceImpl *primary) {
+static HRESULT WINAPI d3d2_CreateDevice(IDirect3D2 *iface, REFCLSID riid,
+        IDirectDrawSurface *surface, IDirect3DDevice2 **device)
+{
     HRESULT hr;
-    WINED3DPRESENT_PARAMETERS presentation_parameters;
-    HWND window;
-
-    window = This->dest_window;
 
-    memset(&presentation_parameters, 0, sizeof(presentation_parameters));
+    TRACE("iface %p, riid %s, surface %p, device %p.\n",
+            iface, debugstr_guid(riid), surface, device);
 
-    /* Use the surface description for the device parameters, not the
-     * Device settings. The app might render to an offscreen surface
-     */
-    presentation_parameters.BackBufferWidth                 = primary->surface_desc.dwWidth;
-    presentation_parameters.BackBufferHeight                = primary->surface_desc.dwHeight;
-    presentation_parameters.BackBufferFormat                = PixelFormat_DD2WineD3D(&primary->surface_desc.u4.ddpfPixelFormat);
-    presentation_parameters.BackBufferCount                 = (primary->surface_desc.dwFlags & DDSD_BACKBUFFERCOUNT) ? primary->surface_desc.u5.dwBackBufferCount : 0;
-    presentation_parameters.MultiSampleType                 = WINED3DMULTISAMPLE_NONE;
-    presentation_parameters.MultiSampleQuality              = 0;
-    presentation_parameters.SwapEffect                      = WINED3DSWAPEFFECT_FLIP;
-    presentation_parameters.hDeviceWindow                   = window;
-    presentation_parameters.Windowed                        = !(This->cooperative_level & DDSCL_FULLSCREEN);
-    presentation_parameters.EnableAutoDepthStencil          = FALSE; /* Not on GDI swapchains */
-    presentation_parameters.AutoDepthStencilFormat          = 0;
-    presentation_parameters.Flags                           = 0;
-    presentation_parameters.FullScreen_RefreshRateInHz      = WINED3DPRESENT_RATE_DEFAULT; /* Default rate: It's already set */
-    presentation_parameters.PresentationInterval            = WINED3DPRESENT_INTERVAL_DEFAULT;
-
-    This->d3d_target = primary;
-    hr = IWineD3DDevice_InitGDI(This->wineD3DDevice, &presentation_parameters);
-    This->d3d_target = NULL;
+    hr = d3d7_CreateDevice((IDirect3D7 *)&ddraw_from_d3d2(iface)->IDirect3D7_vtbl, riid,
+            surface ? (IDirectDrawSurface7 *)surface_from_surface3((IDirectDrawSurface3 *)surface) : NULL,
+            (IDirect3DDevice7 **)device);
+    if (*device) *device = (IDirect3DDevice2 *)&((IDirect3DDeviceImpl *)*device)->IDirect3DDevice2_vtbl;
 
-    if (hr != D3D_OK)
-    {
-        FIXME("(%p) call to IWineD3DDevice_InitGDI failed\n", This);
-        primary->wineD3DSwapChain = NULL;
-    }
     return hr;
 }
 
 /*****************************************************************************
- * IDirectDrawImpl_AttachD3DDevice
+ * IDirect3D7::CreateVertexBuffer
  *
- * Initializes the D3D capabilities of WineD3D
+ * Creates a new vertex buffer object and returns a IDirect3DVertexBuffer7
+ * interface.
+ *
+ * Version 3 and 7
  *
  * Params:
- *  primary: The primary surface for D3D
+ *  desc: Requested Vertex buffer properties
+ *  vertex_buffer: Address to return the interface pointer at
+ *  flags: Some flags, should be 0
  *
  * Returns
- *  DD_OK on success,
- *  DDERR_* otherwise
+ *  D3D_OK on success
+ *  DDERR_OUTOFMEMORY if memory allocation failed
+ *  The return value of IWineD3DDevice::CreateVertexBuffer if this call fails
+ *  DDERR_INVALIDPARAMS if desc or vertex_buffer are NULL
  *
  *****************************************************************************/
-static HRESULT
-IDirectDrawImpl_AttachD3DDevice(IDirectDrawImpl *This,
-                                IDirectDrawSurfaceImpl *primary)
+static HRESULT WINAPI d3d7_CreateVertexBuffer(IDirect3D7 *iface, D3DVERTEXBUFFERDESC *desc,
+        IDirect3DVertexBuffer7 **vertex_buffer, DWORD flags)
 {
+    IDirect3DVertexBufferImpl *object;
     HRESULT hr;
-    HWND                  window = This->dest_window;
 
-    WINED3DPRESENT_PARAMETERS localParameters;
+    TRACE("iface %p, desc %p, vertex_buffer %p, flags %#x.\n",
+            iface, desc, vertex_buffer, flags);
 
-    TRACE("(%p)->(%p)\n", This, primary);
+    if (!vertex_buffer || !desc) return DDERR_INVALIDPARAMS;
 
-    /* If there's no window, create a hidden window. WineD3D needs it */
-    if(window == 0 || window == GetDesktopWindow())
-    {
-        window = CreateWindowExA(0, This->classname, "Hidden D3D Window",
-                                 WS_DISABLED, 0, 0,
-                                 GetSystemMetrics(SM_CXSCREEN),
-                                 GetSystemMetrics(SM_CYSCREEN),
-                                 NULL, NULL, GetModuleHandleA(0), NULL);
+    TRACE("Vertex buffer description:\n");
+    TRACE("    dwSize %u\n", desc->dwSize);
+    TRACE("    dwCaps %#x\n", desc->dwCaps);
+    TRACE("    FVF %#x\n", desc->dwFVF);
+    TRACE("    dwNumVertices %u\n", desc->dwNumVertices);
 
-        ShowWindow(window, SW_HIDE);   /* Just to be sure */
-        WARN("(%p) No window for the Direct3DDevice, created a hidden window. HWND=%p\n", This, window);
+    /* Now create the vertex buffer */
+    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
+    if (!object)
+    {
+        ERR("Failed to allocate vertex buffer memory.\n");
+        return DDERR_OUTOFMEMORY;
     }
-    else
+
+    hr = d3d_vertex_buffer_init(object, ddraw_from_d3d7(iface), desc);
+    if (FAILED(hr))
     {
-        TRACE("(%p) Using existing window %p for Direct3D rendering\n", This, window);
+        WARN("Failed to initialize vertex buffer, hr %#x.\n", hr);
+        HeapFree(GetProcessHeap(), 0, object);
+        return hr;
     }
-    This->d3d_window = window;
 
-    /* Store the future Render Target surface */
-    This->d3d_target = primary;
+    TRACE("Created vertex buffer %p.\n", object);
+    *vertex_buffer = (IDirect3DVertexBuffer7 *)object;
 
-    /* Use the surface description for the device parameters, not the
-     * Device settings. The app might render to an offscreen surface
-     */
-    localParameters.BackBufferWidth                 = primary->surface_desc.dwWidth;
-    localParameters.BackBufferHeight                = primary->surface_desc.dwHeight;
-    localParameters.BackBufferFormat                = PixelFormat_DD2WineD3D(&primary->surface_desc.u4.ddpfPixelFormat);
-    localParameters.BackBufferCount                 = (primary->surface_desc.dwFlags & DDSD_BACKBUFFERCOUNT) ? primary->surface_desc.u5.dwBackBufferCount : 0;
-    localParameters.MultiSampleType                 = WINED3DMULTISAMPLE_NONE;
-    localParameters.MultiSampleQuality              = 0;
-    localParameters.SwapEffect                      = WINED3DSWAPEFFECT_COPY;
-    localParameters.hDeviceWindow                   = window;
-    localParameters.Windowed                        = !(This->cooperative_level & DDSCL_FULLSCREEN);
-    localParameters.EnableAutoDepthStencil          = TRUE;
-    localParameters.AutoDepthStencilFormat          = WINED3DFMT_D16_UNORM;
-    localParameters.Flags                           = 0;
-    localParameters.FullScreen_RefreshRateInHz      = WINED3DPRESENT_RATE_DEFAULT; /* Default rate: It's already set */
-    localParameters.PresentationInterval            = WINED3DPRESENT_INTERVAL_DEFAULT;
-
-    TRACE("Passing mode %d\n", localParameters.BackBufferFormat);
+    return D3D_OK;
+}
 
-    /* Set this NOW, otherwise creating the depth stencil surface will cause a
-     * recursive loop until ram or emulated video memory is full
-     */
-    This->d3d_initialized = TRUE;
+static HRESULT WINAPI d3d3_CreateVertexBuffer(IDirect3D3 *iface, D3DVERTEXBUFFERDESC *desc,
+        IDirect3DVertexBuffer **vertex_buffer, DWORD flags, IUnknown *outer_unknown)
+{
+    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
+    HRESULT hr;
 
-    hr = IWineD3DDevice_Init3D(This->wineD3DDevice, &localParameters);
-    if(FAILED(hr))
-    {
-        This->d3d_target = NULL;
-        This->d3d_initialized = FALSE;
-        return hr;
-    }
+    TRACE("iface %p, desc %p, vertex_buffer %p, flags %#x, outer_unknown %p.\n",
+            iface, desc, vertex_buffer, flags, outer_unknown);
 
-    This->declArraySize = 2;
-    This->decls = HeapAlloc(GetProcessHeap(),
-                            HEAP_ZERO_MEMORY,
-                            sizeof(*This->decls) * This->declArraySize);
-    if(!This->decls)
-    {
-        ERR("Error allocating an array for the converted vertex decls\n");
-        This->declArraySize = 0;
-        hr = IWineD3DDevice_Uninit3D(This->wineD3DDevice, D3D7CB_DestroySwapChain);
-        return E_OUTOFMEMORY;
-    }
+    if (outer_unknown) return CLASS_E_NOAGGREGATION;
 
-    /* Create an Index Buffer parent */
-    TRACE("(%p) Successfully initialized 3D\n", This);
-    return DD_OK;
+    hr = d3d7_CreateVertexBuffer((IDirect3D7 *)&This->IDirect3D7_vtbl,
+            desc, (IDirect3DVertexBuffer7 **)vertex_buffer, flags);
+    if (*vertex_buffer)
+        *vertex_buffer = (IDirect3DVertexBuffer *)&((IDirect3DVertexBufferImpl *)*vertex_buffer)->IDirect3DVertexBuffer_vtbl;
+
+    return hr;
 }
 
 /*****************************************************************************
- * DirectDrawCreateClipper (DDRAW.@)
+ * IDirect3D7::EnumZBufferFormats
  *
- * Creates a new IDirectDrawClipper object.
+ * Enumerates all supported Z buffer pixel formats
+ *
+ * Version 3 and 7
  *
  * Params:
- *  Clipper: Address to write the interface pointer to
- *  UnkOuter: For aggregation support, which ddraw doesn't have. Has to be
- *            NULL
+ *  device_iid:
+ *  callback: callback to call for each pixel format
+ *  context: Pointer to pass back to the callback
  *
  * Returns:
- *  CLASS_E_NOAGGREGATION if UnkOuter != NULL
- *  E_OUTOFMEMORY if allocating the object failed
+ *  D3D_OK on success
+ *  DDERR_INVALIDPARAMS if callback is NULL
+ *  For details, see IWineD3DDevice::EnumZBufferFormats
  *
  *****************************************************************************/
-HRESULT WINAPI
-DirectDrawCreateClipper(DWORD Flags,
-                        LPDIRECTDRAWCLIPPER *Clipper,
-                        IUnknown *UnkOuter)
+static HRESULT WINAPI d3d7_EnumZBufferFormats(IDirect3D7 *iface, REFCLSID device_iid,
+        LPD3DENUMPIXELFORMATSCALLBACK callback, void *context)
 {
-    IDirectDrawClipperImpl* object;
-    TRACE("(%08x,%p,%p)\n", Flags, Clipper, UnkOuter);
+    IDirectDrawImpl *ddraw = ddraw_from_d3d7(iface);
+    WINED3DDISPLAYMODE d3ddm;
+    WINED3DDEVTYPE type;
+    unsigned int i;
+    HRESULT hr;
 
-    EnterCriticalSection(&ddraw_cs);
-    if (UnkOuter != NULL)
+    /* Order matters. Specifically, BattleZone II (full version) expects the
+     * 16-bit depth formats to be listed before the 24 and 32 ones. */
+    static const enum wined3d_format_id formats[] =
     {
-        LeaveCriticalSection(&ddraw_cs);
-        return CLASS_E_NOAGGREGATION;
-    }
+        WINED3DFMT_S1_UINT_D15_UNORM,
+        WINED3DFMT_D16_UNORM,
+        WINED3DFMT_X8D24_UNORM,
+        WINED3DFMT_S4X4_UINT_D24_UNORM,
+        WINED3DFMT_D24_UNORM_S8_UINT,
+        WINED3DFMT_D32_UNORM,
+    };
 
-    if (!LoadWineD3D())
+    TRACE("iface %p, device_iid %s, callback %p, context %p.\n",
+            iface, debugstr_guid(device_iid), callback, context);
+
+    if (!callback) return DDERR_INVALIDPARAMS;
+
+    if (IsEqualGUID(device_iid, &IID_IDirect3DHALDevice)
+            || IsEqualGUID(device_iid, &IID_IDirect3DTnLHalDevice)
+            || IsEqualGUID(device_iid, &IID_D3DDEVICE_WineD3D))
     {
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_NODIRECTDRAWSUPPORT;
+        TRACE("Asked for HAL device.\n");
+        type = WINED3DDEVTYPE_HAL;
     }
-
-    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
-                     sizeof(IDirectDrawClipperImpl));
-    if (object == NULL)
+    else if (IsEqualGUID(device_iid, &IID_IDirect3DRGBDevice)
+            || IsEqualGUID(device_iid, &IID_IDirect3DMMXDevice))
     {
-        LeaveCriticalSection(&ddraw_cs);
-        return E_OUTOFMEMORY;
+        TRACE("Asked for SW device.\n");
+        type = WINED3DDEVTYPE_SW;
+    }
+    else if (IsEqualGUID(device_iid, &IID_IDirect3DRefDevice))
+    {
+        TRACE("Asked for REF device.\n");
+        type = WINED3DDEVTYPE_REF;
+    }
+    else if (IsEqualGUID(device_iid, &IID_IDirect3DNullDevice))
+    {
+        TRACE("Asked for NULLREF device.\n");
+        type = WINED3DDEVTYPE_NULLREF;
+    }
+    else
+    {
+        FIXME("Unexpected device GUID %s.\n", debugstr_guid(device_iid));
+        type = WINED3DDEVTYPE_HAL;
     }
 
-    object->lpVtbl = &IDirectDrawClipper_Vtbl;
-    object->ref = 1;
-    object->wineD3DClipper = pWineDirect3DCreateClipper((IUnknown *) object);
-    if(!object->wineD3DClipper)
+    EnterCriticalSection(&ddraw_cs);
+    /* We need an adapter format from somewhere to please wined3d and WGL.
+     * Use the current display mode. So far all cards offer the same depth
+     * stencil format for all modes, but if some do not and applications do
+     * not like that we'll have to find some workaround, like iterating over
+     * all imaginable formats and collecting all the depth stencil formats we
+     * can get. */
+    hr = IWineD3DDevice_GetDisplayMode(ddraw->wineD3DDevice, 0, &d3ddm);
+
+    for (i = 0; i < (sizeof(formats) / sizeof(*formats)); ++i)
     {
-        HeapFree(GetProcessHeap(), 0, object);
-        LeaveCriticalSection(&ddraw_cs);
-        return E_OUTOFMEMORY;
+        hr = IWineD3D_CheckDeviceFormat(ddraw->wineD3D, WINED3DADAPTER_DEFAULT, type, d3ddm.Format,
+                WINED3DUSAGE_DEPTHSTENCIL, WINED3DRTYPE_SURFACE, formats[i], SURFACE_OPENGL);
+        if (SUCCEEDED(hr))
+        {
+            DDPIXELFORMAT pformat;
+
+            memset(&pformat, 0, sizeof(pformat));
+            pformat.dwSize = sizeof(pformat);
+            PixelFormat_WineD3DtoDD(&pformat, formats[i]);
+
+            TRACE("Enumerating wined3d format %#x.\n", formats[i]);
+            hr = callback(&pformat, context);
+            if (hr != DDENUMRET_OK)
+            {
+                TRACE("Format enumeration cancelled by application.\n");
+                LeaveCriticalSection(&ddraw_cs);
+                return D3D_OK;
+            }
+        }
     }
+    TRACE("End of enumeration.\n");
 
-    *Clipper = (IDirectDrawClipper *) object;
     LeaveCriticalSection(&ddraw_cs);
-    return DD_OK;
+    return D3D_OK;
 }
 
-/*****************************************************************************
- * IDirectDraw7::CreateClipper
- *
- * Creates a DDraw clipper. See DirectDrawCreateClipper for details
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_CreateClipper(IDirectDraw7 *iface,
-                              DWORD Flags,
-                              IDirectDrawClipper **Clipper,
-                              IUnknown *UnkOuter)
+static HRESULT WINAPI d3d3_EnumZBufferFormats(IDirect3D3 *iface, REFCLSID device_iid,
+        LPD3DENUMPIXELFORMATSCALLBACK callback, void *context)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    TRACE("(%p)->(%x,%p,%p)\n", This, Flags, Clipper, UnkOuter);
-    return DirectDrawCreateClipper(Flags, Clipper, UnkOuter);
+    TRACE("iface %p, device_iid %s, callback %p, context %p.\n",
+            iface, debugstr_guid(device_iid), callback, context);
+
+    return d3d7_EnumZBufferFormats((IDirect3D7 *)&ddraw_from_d3d3(iface)->IDirect3D7_vtbl,
+            device_iid, callback, context);
 }
 
 /*****************************************************************************
- * IDirectDraw7::CreatePalette
+ * IDirect3D7::EvictManagedTextures
  *
- * Creates a new IDirectDrawPalette object
+ * Removes all managed textures (=surfaces with DDSCAPS2_TEXTUREMANAGE or
+ * DDSCAPS2_D3DTEXTUREMANAGE caps) to be removed from video memory.
  *
- * Params:
- *  Flags: The flags for the new clipper
- *  ColorTable: Color table to assign to the new clipper
- *  Palette: Address to write the interface pointer to
- *  UnkOuter: For aggregation support, which ddraw doesn't have. Has to be
- *            NULL
+ * Version 3 and 7
  *
  * Returns:
- *  CLASS_E_NOAGGREGATION if UnkOuter != NULL
- *  E_OUTOFMEMORY if allocating the object failed
+ *  D3D_OK, because it's a stub
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_CreatePalette(IDirectDraw7 *iface,
-                              DWORD Flags,
-                              PALETTEENTRY *ColorTable,
-                              IDirectDrawPalette **Palette,
-                              IUnknown *pUnkOuter)
+static HRESULT WINAPI d3d7_EvictManagedTextures(IDirect3D7 *iface)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    IDirectDrawPaletteImpl *object;
-    HRESULT hr = DDERR_GENERIC;
-    TRACE("(%p)->(%x,%p,%p,%p)\n", This, Flags, ColorTable, Palette, pUnkOuter);
-
-    EnterCriticalSection(&ddraw_cs);
-    if(pUnkOuter != NULL)
-    {
-        WARN("pUnkOuter is %p, returning CLASS_E_NOAGGREGATION\n", pUnkOuter);
-        LeaveCriticalSection(&ddraw_cs);
-        return CLASS_E_NOAGGREGATION;
-    }
+    FIXME("iface %p stub!\n", iface);
 
-    /* The refcount test shows that a cooplevel is required for this */
-    if(!This->cooperative_level)
-    {
-        WARN("No cooperative level set, returning DDERR_NOCOOPERATIVELEVELSET\n");
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_NOCOOPERATIVELEVELSET;
-    }
-
-    object = HeapAlloc(GetProcessHeap(), 0, sizeof(IDirectDrawPaletteImpl));
-    if(!object)
-    {
-        ERR("Out of memory when allocating memory for a palette implementation\n");
-        LeaveCriticalSection(&ddraw_cs);
-        return E_OUTOFMEMORY;
-    }
+    /* TODO: Just enumerate resources using IWineD3DDevice_EnumResources(),
+     * then unload surfaces / textures. */
 
-    object->lpVtbl = &IDirectDrawPalette_Vtbl;
-    object->ref = 1;
-    object->ddraw_owner = This;
+    return D3D_OK;
+}
 
-    hr = IWineD3DDevice_CreatePalette(This->wineD3DDevice, Flags,
-            ColorTable, &object->wineD3DPalette, (IUnknown *)object);
-    if(hr != DD_OK)
-    {
-        HeapFree(GetProcessHeap(), 0, object);
-        LeaveCriticalSection(&ddraw_cs);
-        return hr;
-    }
+static HRESULT WINAPI d3d3_EvictManagedTextures(IDirect3D3 *iface)
+{
+    TRACE("iface %p.\n", iface);
 
-    IDirectDraw7_AddRef(iface);
-    object->ifaceToRelease = (IUnknown *) iface;
-    *Palette = (IDirectDrawPalette *)object;
-    LeaveCriticalSection(&ddraw_cs);
-    return DD_OK;
+    return d3d7_EvictManagedTextures((IDirect3D7 *)&ddraw_from_d3d3(iface)->IDirect3D7_vtbl);
 }
 
 /*****************************************************************************
- * IDirectDraw7::DuplicateSurface
+ * IDirect3DImpl_GetCaps
  *
- * Duplicates a surface. The surface memory points to the same memory as
- * the original surface, and it's released when the last surface referencing
- * it is released. I guess that's beyond Wine's surface management right now
- * (Idea: create a new DDraw surface with the same WineD3DSurface. I need a
- * test application to implement this)
+ * This function retrieves the device caps from wined3d
+ * and converts it into a D3D7 and D3D - D3D3 structure
+ * This is a helper function called from various places in ddraw
  *
  * Params:
- *  Src: Address of the source surface
- *  Dest: Address to write the new surface pointer to
+ *  wined3d: The interface to get the caps from
+ *  desc1: Old D3D <3 structure to fill (needed)
+ *  desc7: D3D7 device desc structure to fill (needed)
  *
- * Returns:
- *  See IDirectDraw7::CreateSurface
+ * Returns
+ *  D3D_OK on success, or the return value of IWineD3D::GetCaps
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawImpl_DuplicateSurface(IDirectDraw7 *iface,
-                                 IDirectDrawSurface7 *Src,
-                                 IDirectDrawSurface7 **Dest)
+HRESULT IDirect3DImpl_GetCaps(IWineD3D *wined3d, D3DDEVICEDESC *desc1, D3DDEVICEDESC7 *desc7)
 {
-    IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
-    IDirectDrawSurfaceImpl *Surf = (IDirectDrawSurfaceImpl *)Src;
+    WINED3DCAPS wined3d_caps;
+    HRESULT hr;
 
-    FIXME("(%p)->(%p,%p)\n", This, Surf, Dest);
+    TRACE("wined3d %p, desc1 %p, desc7 %p.\n", wined3d, desc1, desc7);
 
-    /* For now, simply create a new, independent surface */
-    return IDirectDraw7_CreateSurface(iface,
-                                      &Surf->surface_desc,
-                                      Dest,
-                                      NULL);
+    memset(&wined3d_caps, 0, sizeof(wined3d_caps));
+
+    EnterCriticalSection(&ddraw_cs);
+    hr = IWineD3D_GetDeviceCaps(wined3d, 0, WINED3DDEVTYPE_HAL, &wined3d_caps);
+    LeaveCriticalSection(&ddraw_cs);
+    if (FAILED(hr))
+    {
+        WARN("Failed to get device caps, hr %#x.\n", hr);
+        return hr;
+    }
+
+    /* Copy the results into the d3d7 and d3d3 structures */
+    desc7->dwDevCaps = wined3d_caps.DevCaps;
+    desc7->dpcLineCaps.dwMiscCaps = wined3d_caps.PrimitiveMiscCaps;
+    desc7->dpcLineCaps.dwRasterCaps = wined3d_caps.RasterCaps;
+    desc7->dpcLineCaps.dwZCmpCaps = wined3d_caps.ZCmpCaps;
+    desc7->dpcLineCaps.dwSrcBlendCaps = wined3d_caps.SrcBlendCaps;
+    desc7->dpcLineCaps.dwDestBlendCaps = wined3d_caps.DestBlendCaps;
+    desc7->dpcLineCaps.dwAlphaCmpCaps = wined3d_caps.AlphaCmpCaps;
+    desc7->dpcLineCaps.dwShadeCaps = wined3d_caps.ShadeCaps;
+    desc7->dpcLineCaps.dwTextureCaps = wined3d_caps.TextureCaps;
+    desc7->dpcLineCaps.dwTextureFilterCaps = wined3d_caps.TextureFilterCaps;
+    desc7->dpcLineCaps.dwTextureAddressCaps = wined3d_caps.TextureAddressCaps;
+
+    desc7->dwMaxTextureWidth = wined3d_caps.MaxTextureWidth;
+    desc7->dwMaxTextureHeight = wined3d_caps.MaxTextureHeight;
+
+    desc7->dwMaxTextureRepeat = wined3d_caps.MaxTextureRepeat;
+    desc7->dwMaxTextureAspectRatio = wined3d_caps.MaxTextureAspectRatio;
+    desc7->dwMaxAnisotropy = wined3d_caps.MaxAnisotropy;
+    desc7->dvMaxVertexW = wined3d_caps.MaxVertexW;
+
+    desc7->dvGuardBandLeft = wined3d_caps.GuardBandLeft;
+    desc7->dvGuardBandTop = wined3d_caps.GuardBandTop;
+    desc7->dvGuardBandRight = wined3d_caps.GuardBandRight;
+    desc7->dvGuardBandBottom = wined3d_caps.GuardBandBottom;
+
+    desc7->dvExtentsAdjust = wined3d_caps.ExtentsAdjust;
+    desc7->dwStencilCaps = wined3d_caps.StencilCaps;
+
+    desc7->dwFVFCaps = wined3d_caps.FVFCaps;
+    desc7->dwTextureOpCaps = wined3d_caps.TextureOpCaps;
+
+    desc7->dwVertexProcessingCaps = wined3d_caps.VertexProcessingCaps;
+    desc7->dwMaxActiveLights = wined3d_caps.MaxActiveLights;
+
+    /* Remove all non-d3d7 caps */
+    desc7->dwDevCaps &= (
+        D3DDEVCAPS_FLOATTLVERTEX         | D3DDEVCAPS_SORTINCREASINGZ          | D3DDEVCAPS_SORTDECREASINGZ          |
+        D3DDEVCAPS_SORTEXACT             | D3DDEVCAPS_EXECUTESYSTEMMEMORY      | D3DDEVCAPS_EXECUTEVIDEOMEMORY       |
+        D3DDEVCAPS_TLVERTEXSYSTEMMEMORY  | D3DDEVCAPS_TLVERTEXVIDEOMEMORY      | D3DDEVCAPS_TEXTURESYSTEMMEMORY      |
+        D3DDEVCAPS_TEXTUREVIDEOMEMORY    | D3DDEVCAPS_DRAWPRIMTLVERTEX         | D3DDEVCAPS_CANRENDERAFTERFLIP       |
+        D3DDEVCAPS_TEXTURENONLOCALVIDMEM | D3DDEVCAPS_DRAWPRIMITIVES2          | D3DDEVCAPS_SEPARATETEXTUREMEMORIES  |
+        D3DDEVCAPS_DRAWPRIMITIVES2EX     | D3DDEVCAPS_HWTRANSFORMANDLIGHT      | D3DDEVCAPS_CANBLTSYSTONONLOCAL      |
+        D3DDEVCAPS_HWRASTERIZATION);
+
+    desc7->dwStencilCaps &= (
+        D3DSTENCILCAPS_KEEP              | D3DSTENCILCAPS_ZERO                 | D3DSTENCILCAPS_REPLACE              |
+        D3DSTENCILCAPS_INCRSAT           | D3DSTENCILCAPS_DECRSAT              | D3DSTENCILCAPS_INVERT               |
+        D3DSTENCILCAPS_INCR              | D3DSTENCILCAPS_DECR);
+
+    /* FVF caps ?*/
+
+    desc7->dwTextureOpCaps &= (
+        D3DTEXOPCAPS_DISABLE             | D3DTEXOPCAPS_SELECTARG1             | D3DTEXOPCAPS_SELECTARG2             |
+        D3DTEXOPCAPS_MODULATE            | D3DTEXOPCAPS_MODULATE2X             | D3DTEXOPCAPS_MODULATE4X             |
+        D3DTEXOPCAPS_ADD                 | D3DTEXOPCAPS_ADDSIGNED              | D3DTEXOPCAPS_ADDSIGNED2X            |
+        D3DTEXOPCAPS_SUBTRACT            | D3DTEXOPCAPS_ADDSMOOTH              | D3DTEXOPCAPS_BLENDTEXTUREALPHA      |
+        D3DTEXOPCAPS_BLENDFACTORALPHA    | D3DTEXOPCAPS_BLENDTEXTUREALPHAPM    | D3DTEXOPCAPS_BLENDCURRENTALPHA      |
+        D3DTEXOPCAPS_PREMODULATE         | D3DTEXOPCAPS_MODULATEALPHA_ADDCOLOR | D3DTEXOPCAPS_MODULATECOLOR_ADDALPHA |
+        D3DTEXOPCAPS_MODULATEINVALPHA_ADDCOLOR | D3DTEXOPCAPS_MODULATEINVCOLOR_ADDALPHA | D3DTEXOPCAPS_BUMPENVMAP    |
+        D3DTEXOPCAPS_BUMPENVMAPLUMINANCE | D3DTEXOPCAPS_DOTPRODUCT3);
+
+    desc7->dwVertexProcessingCaps &= (
+        D3DVTXPCAPS_TEXGEN               | D3DVTXPCAPS_MATERIALSOURCE7         | D3DVTXPCAPS_VERTEXFOG               |
+        D3DVTXPCAPS_DIRECTIONALLIGHTS    | D3DVTXPCAPS_POSITIONALLIGHTS        | D3DVTXPCAPS_LOCALVIEWER);
+
+    desc7->dpcLineCaps.dwMiscCaps &= (
+        D3DPMISCCAPS_MASKPLANES          | D3DPMISCCAPS_MASKZ                  | D3DPMISCCAPS_LINEPATTERNREP         |
+        D3DPMISCCAPS_CONFORMANT          | D3DPMISCCAPS_CULLNONE               | D3DPMISCCAPS_CULLCW                 |
+        D3DPMISCCAPS_CULLCCW);
+
+    desc7->dpcLineCaps.dwRasterCaps &= (
+        D3DPRASTERCAPS_DITHER            | D3DPRASTERCAPS_ROP2                 | D3DPRASTERCAPS_XOR                  |
+        D3DPRASTERCAPS_PAT               | D3DPRASTERCAPS_ZTEST                | D3DPRASTERCAPS_SUBPIXEL             |
+        D3DPRASTERCAPS_SUBPIXELX         | D3DPRASTERCAPS_FOGVERTEX            | D3DPRASTERCAPS_FOGTABLE             |
+        D3DPRASTERCAPS_STIPPLE           | D3DPRASTERCAPS_ANTIALIASSORTDEPENDENT | D3DPRASTERCAPS_ANTIALIASSORTINDEPENDENT |
+        D3DPRASTERCAPS_ANTIALIASEDGES    | D3DPRASTERCAPS_MIPMAPLODBIAS        | D3DPRASTERCAPS_ZBIAS                |
+        D3DPRASTERCAPS_ZBUFFERLESSHSR    | D3DPRASTERCAPS_FOGRANGE             | D3DPRASTERCAPS_ANISOTROPY           |
+        D3DPRASTERCAPS_WBUFFER           | D3DPRASTERCAPS_TRANSLUCENTSORTINDEPENDENT | D3DPRASTERCAPS_WFOG           |
+        D3DPRASTERCAPS_ZFOG);
+
+    desc7->dpcLineCaps.dwZCmpCaps &= (
+        D3DPCMPCAPS_NEVER                | D3DPCMPCAPS_LESS                    | D3DPCMPCAPS_EQUAL                   |
+        D3DPCMPCAPS_LESSEQUAL            | D3DPCMPCAPS_GREATER                 | D3DPCMPCAPS_NOTEQUAL                |
+        D3DPCMPCAPS_GREATEREQUAL         | D3DPCMPCAPS_ALWAYS);
+
+    desc7->dpcLineCaps.dwSrcBlendCaps &= (
+        D3DPBLENDCAPS_ZERO               | D3DPBLENDCAPS_ONE                   | D3DPBLENDCAPS_SRCCOLOR              |
+        D3DPBLENDCAPS_INVSRCCOLOR        | D3DPBLENDCAPS_SRCALPHA              | D3DPBLENDCAPS_INVSRCALPHA           |
+        D3DPBLENDCAPS_DESTALPHA          | D3DPBLENDCAPS_INVDESTALPHA          | D3DPBLENDCAPS_DESTCOLOR             |
+        D3DPBLENDCAPS_INVDESTCOLOR       | D3DPBLENDCAPS_SRCALPHASAT           | D3DPBLENDCAPS_BOTHSRCALPHA          |
+        D3DPBLENDCAPS_BOTHINVSRCALPHA);
+
+    desc7->dpcLineCaps.dwDestBlendCaps &= (
+        D3DPBLENDCAPS_ZERO               | D3DPBLENDCAPS_ONE                   | D3DPBLENDCAPS_SRCCOLOR              |
+        D3DPBLENDCAPS_INVSRCCOLOR        | D3DPBLENDCAPS_SRCALPHA              | D3DPBLENDCAPS_INVSRCALPHA           |
+        D3DPBLENDCAPS_DESTALPHA          | D3DPBLENDCAPS_INVDESTALPHA          | D3DPBLENDCAPS_DESTCOLOR             |
+        D3DPBLENDCAPS_INVDESTCOLOR       | D3DPBLENDCAPS_SRCALPHASAT           | D3DPBLENDCAPS_BOTHSRCALPHA          |
+        D3DPBLENDCAPS_BOTHINVSRCALPHA);
+
+    desc7->dpcLineCaps.dwAlphaCmpCaps &= (
+        D3DPCMPCAPS_NEVER                | D3DPCMPCAPS_LESS                    | D3DPCMPCAPS_EQUAL                   |
+        D3DPCMPCAPS_LESSEQUAL            | D3DPCMPCAPS_GREATER                 | D3DPCMPCAPS_NOTEQUAL                |
+        D3DPCMPCAPS_GREATEREQUAL         | D3DPCMPCAPS_ALWAYS);
+
+    desc7->dpcLineCaps.dwShadeCaps &= (
+        D3DPSHADECAPS_COLORFLATMONO      | D3DPSHADECAPS_COLORFLATRGB          | D3DPSHADECAPS_COLORGOURAUDMONO      |
+        D3DPSHADECAPS_COLORGOURAUDRGB    | D3DPSHADECAPS_COLORPHONGMONO        | D3DPSHADECAPS_COLORPHONGRGB         |
+        D3DPSHADECAPS_SPECULARFLATMONO   | D3DPSHADECAPS_SPECULARFLATRGB       | D3DPSHADECAPS_SPECULARGOURAUDMONO   |
+        D3DPSHADECAPS_SPECULARGOURAUDRGB | D3DPSHADECAPS_SPECULARPHONGMONO     | D3DPSHADECAPS_SPECULARPHONGRGB      |
+        D3DPSHADECAPS_ALPHAFLATBLEND     | D3DPSHADECAPS_ALPHAFLATSTIPPLED     | D3DPSHADECAPS_ALPHAGOURAUDBLEND     |
+        D3DPSHADECAPS_ALPHAGOURAUDSTIPPLED | D3DPSHADECAPS_ALPHAPHONGBLEND     | D3DPSHADECAPS_ALPHAPHONGSTIPPLED    |
+        D3DPSHADECAPS_FOGFLAT            | D3DPSHADECAPS_FOGGOURAUD            | D3DPSHADECAPS_FOGPHONG);
+
+    desc7->dpcLineCaps.dwTextureCaps &= (
+        D3DPTEXTURECAPS_PERSPECTIVE      | D3DPTEXTURECAPS_POW2                | D3DPTEXTURECAPS_ALPHA               |
+        D3DPTEXTURECAPS_TRANSPARENCY     | D3DPTEXTURECAPS_BORDER              | D3DPTEXTURECAPS_SQUAREONLY          |
+        D3DPTEXTURECAPS_TEXREPEATNOTSCALEDBYSIZE | D3DPTEXTURECAPS_ALPHAPALETTE| D3DPTEXTURECAPS_NONPOW2CONDITIONAL  |
+        D3DPTEXTURECAPS_PROJECTED        | D3DPTEXTURECAPS_CUBEMAP             | D3DPTEXTURECAPS_COLORKEYBLEND);
+
+    desc7->dpcLineCaps.dwTextureFilterCaps &= (
+        D3DPTFILTERCAPS_NEAREST          | D3DPTFILTERCAPS_LINEAR              | D3DPTFILTERCAPS_MIPNEAREST          |
+        D3DPTFILTERCAPS_MIPLINEAR        | D3DPTFILTERCAPS_LINEARMIPNEAREST    | D3DPTFILTERCAPS_LINEARMIPLINEAR     |
+        D3DPTFILTERCAPS_MINFPOINT        | D3DPTFILTERCAPS_MINFLINEAR          | D3DPTFILTERCAPS_MINFANISOTROPIC     |
+        D3DPTFILTERCAPS_MIPFPOINT        | D3DPTFILTERCAPS_MIPFLINEAR          | D3DPTFILTERCAPS_MAGFPOINT           |
+        D3DPTFILTERCAPS_MAGFLINEAR       | D3DPTFILTERCAPS_MAGFANISOTROPIC     | D3DPTFILTERCAPS_MAGFAFLATCUBIC      |
+        D3DPTFILTERCAPS_MAGFGAUSSIANCUBIC);
+
+    desc7->dpcLineCaps.dwTextureBlendCaps &= (
+        D3DPTBLENDCAPS_DECAL             | D3DPTBLENDCAPS_MODULATE             | D3DPTBLENDCAPS_DECALALPHA           |
+        D3DPTBLENDCAPS_MODULATEALPHA     | D3DPTBLENDCAPS_DECALMASK            | D3DPTBLENDCAPS_MODULATEMASK         |
+        D3DPTBLENDCAPS_COPY              | D3DPTBLENDCAPS_ADD);
+
+    desc7->dpcLineCaps.dwTextureAddressCaps &= (
+        D3DPTADDRESSCAPS_WRAP            | D3DPTADDRESSCAPS_MIRROR             | D3DPTADDRESSCAPS_CLAMP              |
+        D3DPTADDRESSCAPS_BORDER          | D3DPTADDRESSCAPS_INDEPENDENTUV);
+
+    if (!(desc7->dpcLineCaps.dwTextureCaps & D3DPTEXTURECAPS_POW2))
+    {
+        /* DirectX7 always has the np2 flag set, no matter what the card
+         * supports. Some old games (Rollcage) check the caps incorrectly.
+         * If wined3d supports nonpow2 textures it also has np2 conditional
+         * support. */
+        desc7->dpcLineCaps.dwTextureCaps |= D3DPTEXTURECAPS_POW2 | D3DPTEXTURECAPS_NONPOW2CONDITIONAL;
+    }
+
+    /* Fill the missing members, and do some fixup */
+    desc7->dpcLineCaps.dwSize = sizeof(desc7->dpcLineCaps);
+    desc7->dpcLineCaps.dwTextureBlendCaps = D3DPTBLENDCAPS_ADD | D3DPTBLENDCAPS_MODULATEMASK |
+                                            D3DPTBLENDCAPS_COPY | D3DPTBLENDCAPS_DECAL |
+                                            D3DPTBLENDCAPS_DECALALPHA | D3DPTBLENDCAPS_DECALMASK |
+                                            D3DPTBLENDCAPS_MODULATE | D3DPTBLENDCAPS_MODULATEALPHA;
+    desc7->dpcLineCaps.dwStippleWidth = 32;
+    desc7->dpcLineCaps.dwStippleHeight = 32;
+    /* Use the same for the TriCaps */
+    desc7->dpcTriCaps = desc7->dpcLineCaps;
+
+    desc7->dwDeviceRenderBitDepth = DDBD_16 | DDBD_24 | DDBD_32;
+    desc7->dwDeviceZBufferBitDepth = DDBD_16 | DDBD_24;
+    desc7->dwMinTextureWidth = 1;
+    desc7->dwMinTextureHeight = 1;
+
+    /* Convert DWORDs safely to WORDs */
+    if (wined3d_caps.MaxTextureBlendStages > 0xffff) desc7->wMaxTextureBlendStages = 0xffff;
+    else desc7->wMaxTextureBlendStages = (WORD)wined3d_caps.MaxTextureBlendStages;
+    if (wined3d_caps.MaxSimultaneousTextures > 0xffff) desc7->wMaxSimultaneousTextures = 0xffff;
+    else desc7->wMaxSimultaneousTextures = (WORD)wined3d_caps.MaxSimultaneousTextures;
+
+    if (wined3d_caps.MaxUserClipPlanes > 0xffff) desc7->wMaxUserClipPlanes = 0xffff;
+    else desc7->wMaxUserClipPlanes = (WORD)wined3d_caps.MaxUserClipPlanes;
+    if (wined3d_caps.MaxVertexBlendMatrices > 0xffff) desc7->wMaxVertexBlendMatrices = 0xffff;
+    else desc7->wMaxVertexBlendMatrices = (WORD)wined3d_caps.MaxVertexBlendMatrices;
+
+    desc7->deviceGUID = IID_IDirect3DTnLHalDevice;
+
+    desc7->dwReserved1 = 0;
+    desc7->dwReserved2 = 0;
+    desc7->dwReserved3 = 0;
+    desc7->dwReserved4 = 0;
+
+    /* Fill the old structure */
+    memset(desc1, 0, sizeof(*desc1));
+    desc1->dwSize = sizeof(D3DDEVICEDESC);
+    desc1->dwFlags = D3DDD_COLORMODEL
+            | D3DDD_DEVCAPS
+            | D3DDD_TRANSFORMCAPS
+            | D3DDD_BCLIPPING
+            | D3DDD_LIGHTINGCAPS
+            | D3DDD_LINECAPS
+            | D3DDD_TRICAPS
+            | D3DDD_DEVICERENDERBITDEPTH
+            | D3DDD_DEVICEZBUFFERBITDEPTH
+            | D3DDD_MAXBUFFERSIZE
+            | D3DDD_MAXVERTEXCOUNT;
+
+    desc1->dcmColorModel = D3DCOLOR_RGB;
+    desc1->dwDevCaps = desc7->dwDevCaps;
+    desc1->dtcTransformCaps.dwSize = sizeof(D3DTRANSFORMCAPS);
+    desc1->dtcTransformCaps.dwCaps = D3DTRANSFORMCAPS_CLIP;
+    desc1->bClipping = TRUE;
+    desc1->dlcLightingCaps.dwSize = sizeof(D3DLIGHTINGCAPS);
+    desc1->dlcLightingCaps.dwCaps = D3DLIGHTCAPS_DIRECTIONAL
+            | D3DLIGHTCAPS_PARALLELPOINT
+            | D3DLIGHTCAPS_POINT
+            | D3DLIGHTCAPS_SPOT;
+
+    desc1->dlcLightingCaps.dwLightingModel = D3DLIGHTINGMODEL_RGB;
+    desc1->dlcLightingCaps.dwNumLights = desc7->dwMaxActiveLights;
+
+    desc1->dpcLineCaps.dwSize = sizeof(D3DPRIMCAPS);
+    desc1->dpcLineCaps.dwMiscCaps = desc7->dpcLineCaps.dwMiscCaps;
+    desc1->dpcLineCaps.dwRasterCaps = desc7->dpcLineCaps.dwRasterCaps;
+    desc1->dpcLineCaps.dwZCmpCaps = desc7->dpcLineCaps.dwZCmpCaps;
+    desc1->dpcLineCaps.dwSrcBlendCaps = desc7->dpcLineCaps.dwSrcBlendCaps;
+    desc1->dpcLineCaps.dwDestBlendCaps = desc7->dpcLineCaps.dwDestBlendCaps;
+    desc1->dpcLineCaps.dwShadeCaps = desc7->dpcLineCaps.dwShadeCaps;
+    desc1->dpcLineCaps.dwTextureCaps = desc7->dpcLineCaps.dwTextureCaps;
+    desc1->dpcLineCaps.dwTextureFilterCaps = desc7->dpcLineCaps.dwTextureFilterCaps;
+    desc1->dpcLineCaps.dwTextureBlendCaps = desc7->dpcLineCaps.dwTextureBlendCaps;
+    desc1->dpcLineCaps.dwTextureAddressCaps = desc7->dpcLineCaps.dwTextureAddressCaps;
+    desc1->dpcLineCaps.dwStippleWidth = desc7->dpcLineCaps.dwStippleWidth;
+    desc1->dpcLineCaps.dwAlphaCmpCaps = desc7->dpcLineCaps.dwAlphaCmpCaps;
+
+    desc1->dpcTriCaps.dwSize = sizeof(D3DPRIMCAPS);
+    desc1->dpcTriCaps.dwMiscCaps = desc7->dpcTriCaps.dwMiscCaps;
+    desc1->dpcTriCaps.dwRasterCaps = desc7->dpcTriCaps.dwRasterCaps;
+    desc1->dpcTriCaps.dwZCmpCaps = desc7->dpcTriCaps.dwZCmpCaps;
+    desc1->dpcTriCaps.dwSrcBlendCaps = desc7->dpcTriCaps.dwSrcBlendCaps;
+    desc1->dpcTriCaps.dwDestBlendCaps = desc7->dpcTriCaps.dwDestBlendCaps;
+    desc1->dpcTriCaps.dwShadeCaps = desc7->dpcTriCaps.dwShadeCaps;
+    desc1->dpcTriCaps.dwTextureCaps = desc7->dpcTriCaps.dwTextureCaps;
+    desc1->dpcTriCaps.dwTextureFilterCaps = desc7->dpcTriCaps.dwTextureFilterCaps;
+    desc1->dpcTriCaps.dwTextureBlendCaps = desc7->dpcTriCaps.dwTextureBlendCaps;
+    desc1->dpcTriCaps.dwTextureAddressCaps = desc7->dpcTriCaps.dwTextureAddressCaps;
+    desc1->dpcTriCaps.dwStippleWidth = desc7->dpcTriCaps.dwStippleWidth;
+    desc1->dpcTriCaps.dwAlphaCmpCaps = desc7->dpcTriCaps.dwAlphaCmpCaps;
+
+    desc1->dwDeviceRenderBitDepth = desc7->dwDeviceRenderBitDepth;
+    desc1->dwDeviceZBufferBitDepth = desc7->dwDeviceZBufferBitDepth;
+    desc1->dwMaxBufferSize = 0;
+    desc1->dwMaxVertexCount = 65536;
+    desc1->dwMinTextureWidth  = desc7->dwMinTextureWidth;
+    desc1->dwMinTextureHeight = desc7->dwMinTextureHeight;
+    desc1->dwMaxTextureWidth  = desc7->dwMaxTextureWidth;
+    desc1->dwMaxTextureHeight = desc7->dwMaxTextureHeight;
+    desc1->dwMinStippleWidth  = 1;
+    desc1->dwMinStippleHeight = 1;
+    desc1->dwMaxStippleWidth  = 32;
+    desc1->dwMaxStippleHeight = 32;
+    desc1->dwMaxTextureRepeat = desc7->dwMaxTextureRepeat;
+    desc1->dwMaxTextureAspectRatio = desc7->dwMaxTextureAspectRatio;
+    desc1->dwMaxAnisotropy = desc7->dwMaxAnisotropy;
+    desc1->dvGuardBandLeft = desc7->dvGuardBandLeft;
+    desc1->dvGuardBandRight = desc7->dvGuardBandRight;
+    desc1->dvGuardBandTop = desc7->dvGuardBandTop;
+    desc1->dvGuardBandBottom = desc7->dvGuardBandBottom;
+    desc1->dvExtentsAdjust = desc7->dvExtentsAdjust;
+    desc1->dwStencilCaps = desc7->dwStencilCaps;
+    desc1->dwFVFCaps = desc7->dwFVFCaps;
+    desc1->dwTextureOpCaps = desc7->dwTextureOpCaps;
+    desc1->wMaxTextureBlendStages = desc7->wMaxTextureBlendStages;
+    desc1->wMaxSimultaneousTextures = desc7->wMaxSimultaneousTextures;
+
+    return DD_OK;
 }
 
 /*****************************************************************************
  * IDirectDraw7 VTable
  *****************************************************************************/
-const IDirectDraw7Vtbl IDirectDraw7_Vtbl =
-{
-    /*** IUnknown ***/
-    IDirectDrawImpl_QueryInterface,
-    IDirectDrawImpl_AddRef,
-    IDirectDrawImpl_Release,
-    /*** IDirectDraw ***/
-    IDirectDrawImpl_Compact,
-    IDirectDrawImpl_CreateClipper,
-    IDirectDrawImpl_CreatePalette,
-    IDirectDrawImpl_CreateSurface,
-    IDirectDrawImpl_DuplicateSurface,
-    IDirectDrawImpl_EnumDisplayModes,
-    IDirectDrawImpl_EnumSurfaces,
-    IDirectDrawImpl_FlipToGDISurface,
-    IDirectDrawImpl_GetCaps,
-    IDirectDrawImpl_GetDisplayMode,
-    IDirectDrawImpl_GetFourCCCodes,
-    IDirectDrawImpl_GetGDISurface,
-    IDirectDrawImpl_GetMonitorFrequency,
-    IDirectDrawImpl_GetScanLine,
-    IDirectDrawImpl_GetVerticalBlankStatus,
-    IDirectDrawImpl_Initialize,
-    IDirectDrawImpl_RestoreDisplayMode,
-    IDirectDrawImpl_SetCooperativeLevel,
-    IDirectDrawImpl_SetDisplayMode,
-    IDirectDrawImpl_WaitForVerticalBlank,
-    /*** IDirectDraw2 ***/
-    IDirectDrawImpl_GetAvailableVidMem,
-    /*** IDirectDraw3 ***/
-    IDirectDrawImpl_GetSurfaceFromDC,
-    /*** IDirectDraw4 ***/
-    IDirectDrawImpl_RestoreAllSurfaces,
-    IDirectDrawImpl_TestCooperativeLevel,
-    IDirectDrawImpl_GetDeviceIdentifier,
-    /*** IDirectDraw7 ***/
-    IDirectDrawImpl_StartModeTest,
-    IDirectDrawImpl_EvaluateMode
+static const struct IDirectDraw7Vtbl ddraw7_vtbl =
+{
+    /* IUnknown */
+    ddraw7_QueryInterface,
+    ddraw7_AddRef,
+    ddraw7_Release,
+    /* IDirectDraw */
+    ddraw7_Compact,
+    ddraw7_CreateClipper,
+    ddraw7_CreatePalette,
+    ddraw7_CreateSurface,
+    ddraw7_DuplicateSurface,
+    ddraw7_EnumDisplayModes,
+    ddraw7_EnumSurfaces,
+    ddraw7_FlipToGDISurface,
+    ddraw7_GetCaps,
+    ddraw7_GetDisplayMode,
+    ddraw7_GetFourCCCodes,
+    ddraw7_GetGDISurface,
+    ddraw7_GetMonitorFrequency,
+    ddraw7_GetScanLine,
+    ddraw7_GetVerticalBlankStatus,
+    ddraw7_Initialize,
+    ddraw7_RestoreDisplayMode,
+    ddraw7_SetCooperativeLevel,
+    ddraw7_SetDisplayMode,
+    ddraw7_WaitForVerticalBlank,
+    /* IDirectDraw2 */
+    ddraw7_GetAvailableVidMem,
+    /* IDirectDraw3 */
+    ddraw7_GetSurfaceFromDC,
+    /* IDirectDraw4 */
+    ddraw7_RestoreAllSurfaces,
+    ddraw7_TestCooperativeLevel,
+    ddraw7_GetDeviceIdentifier,
+    /* IDirectDraw7 */
+    ddraw7_StartModeTest,
+    ddraw7_EvaluateMode
+};
+
+static const struct IDirectDraw4Vtbl ddraw4_vtbl =
+{
+    /* IUnknown */
+    ddraw4_QueryInterface,
+    ddraw4_AddRef,
+    ddraw4_Release,
+    /* IDirectDraw */
+    ddraw4_Compact,
+    ddraw4_CreateClipper,
+    ddraw4_CreatePalette,
+    ddraw4_CreateSurface,
+    ddraw4_DuplicateSurface,
+    ddraw4_EnumDisplayModes,
+    ddraw4_EnumSurfaces,
+    ddraw4_FlipToGDISurface,
+    ddraw4_GetCaps,
+    ddraw4_GetDisplayMode,
+    ddraw4_GetFourCCCodes,
+    ddraw4_GetGDISurface,
+    ddraw4_GetMonitorFrequency,
+    ddraw4_GetScanLine,
+    ddraw4_GetVerticalBlankStatus,
+    ddraw4_Initialize,
+    ddraw4_RestoreDisplayMode,
+    ddraw4_SetCooperativeLevel,
+    ddraw4_SetDisplayMode,
+    ddraw4_WaitForVerticalBlank,
+    /* IDirectDraw2 */
+    ddraw4_GetAvailableVidMem,
+    /* IDirectDraw3 */
+    ddraw4_GetSurfaceFromDC,
+    /* IDirectDraw4 */
+    ddraw4_RestoreAllSurfaces,
+    ddraw4_TestCooperativeLevel,
+    ddraw4_GetDeviceIdentifier,
+};
+
+static const struct IDirectDraw3Vtbl ddraw3_vtbl =
+{
+    /* IUnknown */
+    ddraw3_QueryInterface,
+    ddraw3_AddRef,
+    ddraw3_Release,
+    /* IDirectDraw */
+    ddraw3_Compact,
+    ddraw3_CreateClipper,
+    ddraw3_CreatePalette,
+    ddraw3_CreateSurface,
+    ddraw3_DuplicateSurface,
+    ddraw3_EnumDisplayModes,
+    ddraw3_EnumSurfaces,
+    ddraw3_FlipToGDISurface,
+    ddraw3_GetCaps,
+    ddraw3_GetDisplayMode,
+    ddraw3_GetFourCCCodes,
+    ddraw3_GetGDISurface,
+    ddraw3_GetMonitorFrequency,
+    ddraw3_GetScanLine,
+    ddraw3_GetVerticalBlankStatus,
+    ddraw3_Initialize,
+    ddraw3_RestoreDisplayMode,
+    ddraw3_SetCooperativeLevel,
+    ddraw3_SetDisplayMode,
+    ddraw3_WaitForVerticalBlank,
+    /* IDirectDraw2 */
+    ddraw3_GetAvailableVidMem,
+    /* IDirectDraw3 */
+    ddraw3_GetSurfaceFromDC,
+};
+
+static const struct IDirectDraw2Vtbl ddraw2_vtbl =
+{
+    /* IUnknown */
+    ddraw2_QueryInterface,
+    ddraw2_AddRef,
+    ddraw2_Release,
+    /* IDirectDraw */
+    ddraw2_Compact,
+    ddraw2_CreateClipper,
+    ddraw2_CreatePalette,
+    ddraw2_CreateSurface,
+    ddraw2_DuplicateSurface,
+    ddraw2_EnumDisplayModes,
+    ddraw2_EnumSurfaces,
+    ddraw2_FlipToGDISurface,
+    ddraw2_GetCaps,
+    ddraw2_GetDisplayMode,
+    ddraw2_GetFourCCCodes,
+    ddraw2_GetGDISurface,
+    ddraw2_GetMonitorFrequency,
+    ddraw2_GetScanLine,
+    ddraw2_GetVerticalBlankStatus,
+    ddraw2_Initialize,
+    ddraw2_RestoreDisplayMode,
+    ddraw2_SetCooperativeLevel,
+    ddraw2_SetDisplayMode,
+    ddraw2_WaitForVerticalBlank,
+    /* IDirectDraw2 */
+    ddraw2_GetAvailableVidMem,
+};
+
+static const struct IDirectDrawVtbl ddraw1_vtbl =
+{
+    /* IUnknown */
+    ddraw1_QueryInterface,
+    ddraw1_AddRef,
+    ddraw1_Release,
+    /* IDirectDraw */
+    ddraw1_Compact,
+    ddraw1_CreateClipper,
+    ddraw1_CreatePalette,
+    ddraw1_CreateSurface,
+    ddraw1_DuplicateSurface,
+    ddraw1_EnumDisplayModes,
+    ddraw1_EnumSurfaces,
+    ddraw1_FlipToGDISurface,
+    ddraw1_GetCaps,
+    ddraw1_GetDisplayMode,
+    ddraw1_GetFourCCCodes,
+    ddraw1_GetGDISurface,
+    ddraw1_GetMonitorFrequency,
+    ddraw1_GetScanLine,
+    ddraw1_GetVerticalBlankStatus,
+    ddraw1_Initialize,
+    ddraw1_RestoreDisplayMode,
+    ddraw1_SetCooperativeLevel,
+    ddraw1_SetDisplayMode,
+    ddraw1_WaitForVerticalBlank,
+};
+
+static const struct IDirect3D7Vtbl d3d7_vtbl =
+{
+    /* IUnknown methods */
+    d3d7_QueryInterface,
+    d3d7_AddRef,
+    d3d7_Release,
+    /* IDirect3D7 methods */
+    d3d7_EnumDevices,
+    d3d7_CreateDevice,
+    d3d7_CreateVertexBuffer,
+    d3d7_EnumZBufferFormats,
+    d3d7_EvictManagedTextures
+};
+
+static const struct IDirect3D3Vtbl d3d3_vtbl =
+{
+    /* IUnknown methods */
+    d3d3_QueryInterface,
+    d3d3_AddRef,
+    d3d3_Release,
+    /* IDirect3D3 methods */
+    d3d3_EnumDevices,
+    d3d3_CreateLight,
+    d3d3_CreateMaterial,
+    d3d3_CreateViewport,
+    d3d3_FindDevice,
+    d3d3_CreateDevice,
+    d3d3_CreateVertexBuffer,
+    d3d3_EnumZBufferFormats,
+    d3d3_EvictManagedTextures
+};
+
+static const struct IDirect3D2Vtbl d3d2_vtbl =
+{
+    /* IUnknown methods */
+    d3d2_QueryInterface,
+    d3d2_AddRef,
+    d3d2_Release,
+    /* IDirect3D2 methods */
+    d3d2_EnumDevices,
+    d3d2_CreateLight,
+    d3d2_CreateMaterial,
+    d3d2_CreateViewport,
+    d3d2_FindDevice,
+    d3d2_CreateDevice
+};
+
+static const struct IDirect3DVtbl d3d1_vtbl =
+{
+    /* IUnknown methods */
+    d3d1_QueryInterface,
+    d3d1_AddRef,
+    d3d1_Release,
+    /* IDirect3D methods */
+    d3d1_Initialize,
+    d3d1_EnumDevices,
+    d3d1_CreateLight,
+    d3d1_CreateMaterial,
+    d3d1_CreateViewport,
+    d3d1_FindDevice
 };
 
 /*****************************************************************************
- * IDirectDrawImpl_FindDecl
+ * ddraw_find_decl
  *
  * Finds the WineD3D vertex declaration for a specific fvf, and creates one
  * if none was found.
@@ -3189,9 +5432,7 @@ const IDirectDraw7Vtbl IDirectDraw7_Vtbl =
  *  fvf otherwise.
  *
  *****************************************************************************/
-IWineD3DVertexDeclaration *
-IDirectDrawImpl_FindDecl(IDirectDrawImpl *This,
-                         DWORD fvf)
+IWineD3DVertexDeclaration *ddraw_find_decl(IDirectDrawImpl *This, DWORD fvf)
 {
     HRESULT hr;
     IWineD3DVertexDeclaration* pDecl = NULL;
@@ -3216,8 +5457,8 @@ IDirectDrawImpl_FindDecl(IDirectDrawImpl *This,
     }
     TRACE("not found. Creating and inserting at position %d.\n", low);
 
-    hr = IWineD3DDevice_CreateVertexDeclarationFromFVF(This->wineD3DDevice, &pDecl,
-            (IUnknown *)This, &ddraw_null_wined3d_parent_ops, fvf);
+    hr = IWineD3DDevice_CreateVertexDeclarationFromFVF(This->wineD3DDevice,
+            fvf, This, &ddraw_null_wined3d_parent_ops, &pDecl);
     if (hr != S_OK) return NULL;
 
     if(This->declArraySize == This->numConvertedDecls) {
@@ -3252,19 +5493,19 @@ static inline struct IDirectDrawImpl *ddraw_from_device_parent(IWineD3DDevicePar
 static HRESULT STDMETHODCALLTYPE device_parent_QueryInterface(IWineD3DDeviceParent *iface, REFIID riid, void **object)
 {
     struct IDirectDrawImpl *This = ddraw_from_device_parent(iface);
-    return IDirectDrawImpl_QueryInterface((IDirectDraw7 *)This, riid, object);
+    return ddraw7_QueryInterface((IDirectDraw7 *)This, riid, object);
 }
 
 static ULONG STDMETHODCALLTYPE device_parent_AddRef(IWineD3DDeviceParent *iface)
 {
     struct IDirectDrawImpl *This = ddraw_from_device_parent(iface);
-    return IDirectDrawImpl_AddRef((IDirectDraw7 *)This);
+    return ddraw7_AddRef((IDirectDraw7 *)This);
 }
 
 static ULONG STDMETHODCALLTYPE device_parent_Release(IWineD3DDeviceParent *iface)
 {
     struct IDirectDrawImpl *This = ddraw_from_device_parent(iface);
-    return IDirectDrawImpl_Release((IDirectDraw7 *)This);
+    return ddraw7_Release((IDirectDraw7 *)This);
 }
 
 /* IWineD3DDeviceParent methods */
@@ -3275,7 +5516,7 @@ static void STDMETHODCALLTYPE device_parent_WineD3DDeviceCreated(IWineD3DDeviceP
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateSurface(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, WINED3DFORMAT format, DWORD usage,
+        IUnknown *superior, UINT width, UINT height, enum wined3d_format_id format, DWORD usage,
         WINED3DPOOL pool, UINT level, WINED3DCUBEMAP_FACES face, IWineD3DSurface **surface)
 {
     struct IDirectDrawImpl *This = ddraw_from_device_parent(iface);
@@ -3344,9 +5585,31 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateSurface(IWineD3DDeviceParen
     return D3D_OK;
 }
 
+static HRESULT WINAPI findRenderTarget(IDirectDrawSurface7 *surface, DDSURFACEDESC2 *surface_desc, void *ctx)
+{
+    IDirectDrawSurfaceImpl *s = (IDirectDrawSurfaceImpl *)surface;
+    IDirectDrawSurfaceImpl **target = ctx;
+
+    if (!s->isRenderTarget)
+    {
+        *target = s;
+        IDirectDrawSurface7_Release(surface);
+        return DDENUMRET_CANCEL;
+    }
+
+    /* Recurse into the surface tree */
+    IDirectDrawSurface7_EnumAttachedSurfaces(surface, ctx, findRenderTarget);
+
+    IDirectDrawSurface7_Release(surface);
+    if (*target) return DDENUMRET_CANCEL;
+
+    return DDENUMRET_OK;
+}
+
 static HRESULT STDMETHODCALLTYPE device_parent_CreateRenderTarget(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, WINED3DFORMAT format, WINED3DMULTISAMPLE_TYPE multisample_type,
-        DWORD multisample_quality, BOOL lockable, IWineD3DSurface **surface)
+        IUnknown *superior, UINT width, UINT height, enum wined3d_format_id format,
+        WINED3DMULTISAMPLE_TYPE multisample_type, DWORD multisample_quality, BOOL lockable,
+        IWineD3DSurface **surface)
 {
     struct IDirectDrawImpl *This = ddraw_from_device_parent(iface);
     IDirectDrawSurfaceImpl *d3d_surface = This->d3d_target;
@@ -3383,7 +5646,7 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateRenderTarget(IWineD3DDevice
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateDepthStencilSurface(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, WINED3DFORMAT format, WINED3DMULTISAMPLE_TYPE multisample_type,
+        UINT width, UINT height, enum wined3d_format_id format, WINED3DMULTISAMPLE_TYPE multisample_type,
         DWORD multisample_quality, BOOL discard, IWineD3DSurface **surface)
 {
     struct IDirectDrawImpl *This = ddraw_from_device_parent(iface);
@@ -3391,9 +5654,9 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateDepthStencilSurface(IWineD3
     DDSURFACEDESC2 ddsd;
     HRESULT hr;
 
-    TRACE("iface %p, superior %p, width %u, height %u, format %#x, multisample_type %#x,\n"
+    TRACE("iface %p, width %u, height %u, format %#x, multisample_type %#x,\n"
             "\tmultisample_quality %u, discard %u, surface %p\n",
-            iface, superior, width, height, format, multisample_type, multisample_quality, discard, surface);
+            iface, width, height, format, multisample_type, multisample_quality, discard, surface);
 
     *surface = NULL;
 
@@ -3431,7 +5694,7 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateDepthStencilSurface(IWineD3
 }
 
 static HRESULT STDMETHODCALLTYPE device_parent_CreateVolume(IWineD3DDeviceParent *iface,
-        IUnknown *superior, UINT width, UINT height, UINT depth, WINED3DFORMAT format,
+        IUnknown *superior, UINT width, UINT height, UINT depth, enum wined3d_format_id format,
         WINED3DPOOL pool, DWORD usage, IWineD3DVolume **volume)
 {
     TRACE("iface %p, superior %p, width %u, height %u, depth %u, format %#x, pool %#x, usage %#x, volume %p\n",
@@ -3460,11 +5723,10 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateSwapChain(IWineD3DDevicePar
         return DDERR_OUTOFVIDEOMEMORY;
     }
 
-    object->lpVtbl = &IParent_Vtbl;
-    object->ref = 1;
+    ddraw_parent_init(object);
 
     hr = IWineD3DDevice_CreateSwapChain(This->wineD3DDevice, present_parameters,
-            swapchain, (IUnknown *)object, This->ImplType);
+            This->ImplType, object, swapchain);
     if (FAILED(hr))
     {
         FIXME("(%p) CreateSwapChain failed, returning %#x\n", iface, hr);
@@ -3485,7 +5747,7 @@ static HRESULT STDMETHODCALLTYPE device_parent_CreateSwapChain(IWineD3DDevicePar
     return hr;
 }
 
-const IWineD3DDeviceParentVtbl ddraw_wined3d_device_parent_vtbl =
+static const IWineD3DDeviceParentVtbl ddraw_wined3d_device_parent_vtbl =
 {
     /* IUnknown methods */
     device_parent_QueryInterface,
@@ -3499,3 +5761,62 @@ const IWineD3DDeviceParentVtbl ddraw_wined3d_device_parent_vtbl =
     device_parent_CreateVolume,
     device_parent_CreateSwapChain,
 };
+
+HRESULT ddraw_init(IDirectDrawImpl *ddraw, WINED3DDEVTYPE device_type)
+{
+    HRESULT hr;
+    HDC hDC;
+
+    ddraw->lpVtbl = &ddraw7_vtbl;
+    ddraw->IDirectDraw_vtbl = &ddraw1_vtbl;
+    ddraw->IDirectDraw2_vtbl = &ddraw2_vtbl;
+    ddraw->IDirectDraw3_vtbl = &ddraw3_vtbl;
+    ddraw->IDirectDraw4_vtbl = &ddraw4_vtbl;
+    ddraw->IDirect3D_vtbl = &d3d1_vtbl;
+    ddraw->IDirect3D2_vtbl = &d3d2_vtbl;
+    ddraw->IDirect3D3_vtbl = &d3d3_vtbl;
+    ddraw->IDirect3D7_vtbl = &d3d7_vtbl;
+    ddraw->device_parent_vtbl = &ddraw_wined3d_device_parent_vtbl;
+    ddraw->numIfaces = 1;
+    ddraw->ref7 = 1;
+
+    /* See comments in IDirectDrawImpl_CreateNewSurface for a description of
+     * this field. */
+    ddraw->ImplType = DefaultSurfaceType;
+
+    /* Get the current screen settings. */
+    hDC = GetDC(0);
+    ddraw->orig_bpp = GetDeviceCaps(hDC, BITSPIXEL) * GetDeviceCaps(hDC, PLANES);
+    ReleaseDC(0, hDC);
+    ddraw->orig_width = GetSystemMetrics(SM_CXSCREEN);
+    ddraw->orig_height = GetSystemMetrics(SM_CYSCREEN);
+
+    if (!LoadWineD3D())
+    {
+        ERR("Failed to load wined3d - broken OpenGL setup?\n");
+        return DDERR_NODIRECTDRAWSUPPORT;
+    }
+
+    ddraw->wineD3D = pWineDirect3DCreate(7, (IUnknown *)ddraw);
+    if (!ddraw->wineD3D)
+    {
+        WARN("Failed to create a wined3d object.\n");
+        return E_OUTOFMEMORY;
+    }
+
+    hr = IWineD3D_CreateDevice(ddraw->wineD3D, WINED3DADAPTER_DEFAULT, device_type, NULL, 0,
+            (IWineD3DDeviceParent *)&ddraw->device_parent_vtbl, &ddraw->wineD3DDevice);
+    if (FAILED(hr))
+    {
+        WARN("Failed to create a wined3d device, hr %#x.\n", hr);
+        IWineD3D_Release(ddraw->wineD3D);
+        return hr;
+    }
+
+    /* Get the amount of video memory */
+    ddraw->total_vidmem = IWineD3DDevice_GetAvailableTextureMem(ddraw->wineD3DDevice);
+
+    list_init(&ddraw->surface_list);
+
+    return DD_OK;
+}
index 962cd7a..d221726 100644 (file)
 
        <file>clipper.c</file>
        <file>ddraw.c</file>
-       <file>ddraw_thunks.c</file>
        <file>device.c</file>
-       <file>direct3d.c</file>
        <file>executebuffer.c</file>
-       <file>gamma.c</file>
        <file>light.c</file>
        <file>main.c</file>
        <file>material.c</file>
@@ -34,8 +31,6 @@
        <file>regsvr.c</file>
        <file>stubs.c</file>
        <file>surface.c</file>
-       <file>surface_thunks.c</file>
-       <file>texture.c</file>
        <file>utils.c</file>
        <file>version.rc</file>
        <file>vertexbuffer.c</file>
index bea5ad2..91662fe 100644 (file)
 #ifndef __WINE_DLLS_DDRAW_DDRAW_PRIVATE_H
 #define __WINE_DLLS_DDRAW_DDRAW_PRIVATE_H
 
-/* MAY NOT CONTAIN X11 or DGA specific includes/defines/structs! */
+#include <assert.h>
+#define COBJMACROS
+#define NONAMELESSSTRUCT
+#define NONAMELESSUNION
+#include "wine/debug.h"
 
-#include <stdarg.h>
-#include <stdio.h>
-
-#include "windef.h"
 #include "winbase.h"
-#include "wtypes.h"
 #include "wingdi.h"
 #include "winuser.h"
-#include "ddraw.h"
-#include "ddrawi.h"
-#include "d3d.h"
 
-#include "wine/list.h"
+#include "d3d.h"
+#include "ddraw.h"
 #ifdef DDRAW_INIT_GUID
 #include "initguid.h"
 #endif
+#include "wine/list.h"
 #include "wine/wined3d.h"
+#include "legacy.h"
 
 extern const struct wined3d_parent_ops ddraw_null_wined3d_parent_ops DECLSPEC_HIDDEN;
 
@@ -100,6 +99,7 @@ struct IDirectDrawImpl
     /* IUnknown fields */
     const IDirectDraw7Vtbl *lpVtbl;
     const IDirectDraw4Vtbl *IDirectDraw4_vtbl;
+    const IDirectDraw3Vtbl *IDirectDraw3_vtbl;
     const IDirectDraw2Vtbl *IDirectDraw2_vtbl;
     const IDirectDrawVtbl *IDirectDraw_vtbl;
     const IDirect3D7Vtbl *IDirect3D7_vtbl;
@@ -142,11 +142,6 @@ struct IDirectDrawImpl
     /* The surface type to request */
     WINED3DSURFTYPE         ImplType;
 
-
-    /* Our private window class */
-    char classname[32];
-    WNDCLASSA wnd_class;
-
     /* Helpers for surface creation */
     IDirectDrawSurfaceImpl *tex_root;
     BOOL                    depthstencil;
@@ -164,12 +159,9 @@ struct IDirectDrawImpl
     UINT                    numConvertedDecls, declArraySize;
 };
 
-/* Declare the VTables. They can be found ddraw.c */
-extern const IDirectDraw7Vtbl IDirectDraw7_Vtbl DECLSPEC_HIDDEN;
-extern const IDirectDraw4Vtbl IDirectDraw4_Vtbl DECLSPEC_HIDDEN;
-extern const IDirectDraw2Vtbl IDirectDraw2_Vtbl DECLSPEC_HIDDEN;
-extern const IDirectDrawVtbl IDirectDraw1_Vtbl DECLSPEC_HIDDEN;
-extern const IWineD3DDeviceParentVtbl ddraw_wined3d_device_parent_vtbl DECLSPEC_HIDDEN;
+#define DDRAW_WINDOW_CLASS_NAME "ddraw_wc"
+
+HRESULT ddraw_init(IDirectDrawImpl *ddraw, WINED3DDEVTYPE device_type) DECLSPEC_HIDDEN;
 
 /* Helper structures */
 typedef struct EnumDisplayModesCBS
@@ -189,10 +181,9 @@ typedef struct EnumSurfacesCBS
 /* Utility functions */
 void DDRAW_Convert_DDSCAPS_1_To_2(const DDSCAPS *pIn, DDSCAPS2 *pOut) DECLSPEC_HIDDEN;
 void DDRAW_Convert_DDDEVICEIDENTIFIER_2_To_1(const DDDEVICEIDENTIFIER2 *pIn, DDDEVICEIDENTIFIER *pOut) DECLSPEC_HIDDEN;
-void IDirectDrawImpl_Destroy(IDirectDrawImpl *This) DECLSPEC_HIDDEN;
-HRESULT WINAPI IDirectDrawImpl_RecreateSurfacesCallback(IDirectDrawSurface7 *surf,
+HRESULT WINAPI ddraw_recreate_surfaces_cb(IDirectDrawSurface7 *surf,
         DDSURFACEDESC2 *desc, void *Context) DECLSPEC_HIDDEN;
-IWineD3DVertexDeclaration *IDirectDrawImpl_FindDecl(IDirectDrawImpl *This, DWORD fvf) DECLSPEC_HIDDEN;
+IWineD3DVertexDeclaration *ddraw_find_decl(IDirectDrawImpl *This, DWORD fvf) DECLSPEC_HIDDEN;
 
 static inline IDirectDrawImpl *ddraw_from_d3d1(IDirect3D *iface)
 {
@@ -214,24 +205,13 @@ static inline IDirectDrawImpl *ddraw_from_d3d7(IDirect3D7 *iface)
     return (IDirectDrawImpl *)((char*)iface - FIELD_OFFSET(IDirectDrawImpl, IDirect3D7_vtbl));
 }
 
-static inline IDirectDrawImpl *ddraw_from_ddraw1(IDirectDraw *iface)
-{
-    return (IDirectDrawImpl *)((char*)iface - FIELD_OFFSET(IDirectDrawImpl, IDirectDraw_vtbl));
-}
-
-static inline IDirectDrawImpl *ddraw_from_ddraw2(IDirectDraw2 *iface)
-{
-    return (IDirectDrawImpl *)((char*)iface - FIELD_OFFSET(IDirectDrawImpl, IDirectDraw2_vtbl));
-}
-
-static inline IDirectDrawImpl *ddraw_from_ddraw4(IDirectDraw4 *iface)
-{
-    return (IDirectDrawImpl *)((char*)iface - FIELD_OFFSET(IDirectDrawImpl, IDirectDraw4_vtbl));
-}
-
 /* The default surface type */
 extern WINED3DSURFTYPE DefaultSurfaceType DECLSPEC_HIDDEN;
 
+extern typeof(WineDirect3DCreateClipper) *pWineDirect3DCreateClipper DECLSPEC_HIDDEN;
+extern typeof(WineDirect3DCreate) *pWineDirect3DCreate DECLSPEC_HIDDEN;
+
+
 /*****************************************************************************
  * IDirectDrawSurface implementation structure
  *****************************************************************************/
@@ -292,16 +272,9 @@ struct IDirectDrawSurfaceImpl
     DWORD                   Handle;
 };
 
-/* VTable declaration. It's located in surface.c / surface_thunks.c */
-extern const IDirectDrawSurface7Vtbl IDirectDrawSurface7_Vtbl DECLSPEC_HIDDEN;
-extern const IDirectDrawSurface3Vtbl IDirectDrawSurface3_Vtbl DECLSPEC_HIDDEN;
-extern const IDirectDrawGammaControlVtbl IDirectDrawGammaControl_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3DTexture2Vtbl IDirect3DTexture2_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3DTextureVtbl IDirect3DTexture1_Vtbl DECLSPEC_HIDDEN;
-
-HRESULT WINAPI IDirectDrawSurfaceImpl_AddAttachedSurface(IDirectDrawSurfaceImpl *This,
-        IDirectDrawSurfaceImpl *Surf) DECLSPEC_HIDDEN;
-void IDirectDrawSurfaceImpl_Destroy(IDirectDrawSurfaceImpl *This) DECLSPEC_HIDDEN;
+void ddraw_surface_destroy(IDirectDrawSurfaceImpl *surface) DECLSPEC_HIDDEN;
+HRESULT ddraw_surface_init(IDirectDrawSurfaceImpl *surface, IDirectDrawImpl *ddraw,
+        DDSURFACEDESC2 *desc, UINT mip_level, WINED3DSURFTYPE surface_type) DECLSPEC_HIDDEN;
 
 static inline IDirectDrawSurfaceImpl *surface_from_texture1(IDirect3DTexture *iface)
 {
@@ -336,26 +309,43 @@ struct IParentImpl
 
 };
 
-extern const IParentVtbl IParent_Vtbl DECLSPEC_HIDDEN;
+void ddraw_parent_init(IParentImpl *parent) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * IDirect3DDevice implementation
  *****************************************************************************/
-typedef enum
+
+#define DDRAW_INVALID_HANDLE ~0U
+
+enum ddraw_handle_type
 {
-    DDrawHandle_Unknown       = 0,
-    DDrawHandle_Texture       = 1,
-    DDrawHandle_Material      = 2,
-    DDrawHandle_Matrix        = 3,
-    DDrawHandle_StateBlock    = 4
-} DDrawHandleTypes;
+    DDRAW_HANDLE_FREE,
+    DDRAW_HANDLE_MATERIAL,
+    DDRAW_HANDLE_MATRIX,
+    DDRAW_HANDLE_STATEBLOCK,
+    DDRAW_HANDLE_SURFACE,
+};
 
-struct HandleEntry
+struct ddraw_handle_entry
 {
-    void    *ptr;
-    DDrawHandleTypes      type;
+    void *object;
+    enum ddraw_handle_type type;
 };
 
+struct ddraw_handle_table
+{
+    struct ddraw_handle_entry *entries;
+    struct ddraw_handle_entry *free_entries;
+    UINT table_size;
+    UINT entry_count;
+};
+
+BOOL ddraw_handle_table_init(struct ddraw_handle_table *t, UINT initial_size) DECLSPEC_HIDDEN;
+void ddraw_handle_table_destroy(struct ddraw_handle_table *t) DECLSPEC_HIDDEN;
+DWORD ddraw_allocate_handle(struct ddraw_handle_table *t, void *object, enum ddraw_handle_type type) DECLSPEC_HIDDEN;
+void *ddraw_free_handle(struct ddraw_handle_table *t, DWORD handle, enum ddraw_handle_type type) DECLSPEC_HIDDEN;
+void *ddraw_get_object(struct ddraw_handle_table *t, DWORD handle, enum ddraw_handle_type type) DECLSPEC_HIDDEN;
+
 struct IDirect3DDeviceImpl
 {
     /* IUnknown */
@@ -370,7 +360,6 @@ struct IDirect3DDeviceImpl
     IDirectDrawImpl         *ddraw;
     IWineD3DBuffer          *indexbuffer;
     IDirectDrawSurfaceImpl  *target;
-    BOOL                    OffScreenTarget;
 
     /* Viewport management */
     IDirect3DViewportImpl *viewport_list;
@@ -393,24 +382,18 @@ struct IDirect3DDeviceImpl
     DWORD buffer_size;
 
     /* Handle management */
-    struct HandleEntry      *Handles;
-    DWORD                    numHandles;
+    struct ddraw_handle_table handle_table;
     D3DMATRIXHANDLE          world, proj, view;
 };
 
-/* Vtables in various versions */
-extern const IDirect3DDevice7Vtbl IDirect3DDevice7_FPUSetup_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3DDevice7Vtbl IDirect3DDevice7_FPUPreserve_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3DDevice3Vtbl IDirect3DDevice3_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3DDevice2Vtbl IDirect3DDevice2_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3DDeviceVtbl  IDirect3DDevice1_Vtbl DECLSPEC_HIDDEN;
+HRESULT d3d_device_init(IDirect3DDeviceImpl *device, IDirectDrawImpl *ddraw,
+        IDirectDrawSurfaceImpl *target) DECLSPEC_HIDDEN;
 
 /* The IID */
 extern const GUID IID_D3DDEVICE_WineD3D DECLSPEC_HIDDEN;
 
 /* Helper functions */
 HRESULT IDirect3DImpl_GetCaps(IWineD3D *WineD3D, D3DDEVICEDESC *Desc123, D3DDEVICEDESC7 *Desc7) DECLSPEC_HIDDEN;
-DWORD IDirect3DDeviceImpl_CreateHandle(IDirect3DDeviceImpl *This) DECLSPEC_HIDDEN;
 WINED3DZBUFFERTYPE IDirect3DDeviceImpl_UpdateDepthStencil(IDirect3DDeviceImpl *This) DECLSPEC_HIDDEN;
 
 static inline IDirect3DDeviceImpl *device_from_device1(IDirect3DDevice *iface)
@@ -436,18 +419,6 @@ struct EnumTextureFormatsCBS
     void *Context;
 };
 
-/*****************************************************************************
- * IDirect3D implementation
- *****************************************************************************/
-
-/* No implementation structure as this is only another interface to DirectDraw */
-
-/* the Vtables */
-extern const IDirect3DVtbl IDirect3D1_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3D2Vtbl IDirect3D2_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3D3Vtbl IDirect3D3_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3D7Vtbl IDirect3D7_Vtbl DECLSPEC_HIDDEN;
-
 /* Structure for EnumZBufferFormats */
 struct EnumZBufferFormatsData
 {
@@ -465,12 +436,10 @@ struct IDirectDrawClipperImpl
     LONG ref;
 
     IWineD3DClipper           *wineD3DClipper;
-    IDirectDrawImpl           *ddraw_owner;
+    BOOL initialized;
 };
 
-extern const IDirectDrawClipperVtbl IDirectDrawClipper_Vtbl DECLSPEC_HIDDEN;
-
-typeof(WineDirect3DCreateClipper) *pWineDirect3DCreateClipper DECLSPEC_HIDDEN;
+HRESULT ddraw_clipper_init(IDirectDrawClipperImpl *clipper) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * IDirectDrawPalette implementation structure
@@ -485,10 +454,11 @@ struct IDirectDrawPaletteImpl
     IWineD3DPalette           *wineD3DPalette;
 
     /* IDirectDrawPalette fields */
-    IDirectDrawImpl           *ddraw_owner;
     IUnknown                  *ifaceToRelease;
 };
-extern const IDirectDrawPaletteVtbl IDirectDrawPalette_Vtbl DECLSPEC_HIDDEN;
+
+HRESULT ddraw_palette_init(IDirectDrawPaletteImpl *palette,
+        IDirectDrawImpl *ddraw, DWORD flags, PALETTEENTRY *entries) DECLSPEC_HIDDEN;
 
 /******************************************************************************
  * DirectDraw ClassFactory implementation - incomplete
@@ -530,20 +500,12 @@ struct IDirect3DLightImpl
 
     /* Chained list used for adding / removing from viewports */
     IDirect3DLightImpl        *next;
-
-    /* Activation function */
-    void                      (*activate)(IDirect3DLightImpl*);
-    void                      (*desactivate)(IDirect3DLightImpl*);
-    void                      (*update)(IDirect3DLightImpl*);
 };
 
-/* Vtable */
-extern const IDirect3DLightVtbl IDirect3DLight_Vtbl DECLSPEC_HIDDEN;
-
 /* Helper functions */
-void light_update(IDirect3DLightImpl *This) DECLSPEC_HIDDEN;
-void light_activate(IDirect3DLightImpl *This) DECLSPEC_HIDDEN;
-void light_desactivate(IDirect3DLightImpl *This) DECLSPEC_HIDDEN;
+void light_activate(IDirect3DLightImpl *light) DECLSPEC_HIDDEN;
+void light_deactivate(IDirect3DLightImpl *light) DECLSPEC_HIDDEN;
+void d3d_light_init(IDirect3DLightImpl *light, IDirectDrawImpl *ddraw) DECLSPEC_HIDDEN;
 
 /******************************************************************************
  * IDirect3DMaterial implementation structure - Wraps to D3D7
@@ -561,17 +523,11 @@ struct IDirect3DMaterialImpl
 
     D3DMATERIAL mat;
     DWORD Handle;
-
-    void (*activate)(IDirect3DMaterialImpl* this);
 };
 
-/* VTables in various versions */
-extern const IDirect3DMaterialVtbl IDirect3DMaterial_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3DMaterial2Vtbl IDirect3DMaterial2_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3DMaterial3Vtbl IDirect3DMaterial3_Vtbl DECLSPEC_HIDDEN;
-
 /* Helper functions */
 void material_activate(IDirect3DMaterialImpl* This) DECLSPEC_HIDDEN;
+void d3d_material_init(IDirect3DMaterialImpl *material, IDirectDrawImpl *ddraw) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * IDirect3DViewport - Wraps to D3D7
@@ -598,9 +554,6 @@ struct IDirect3DViewportImpl
         D3DVIEWPORT2 vp2;
     } viewports;
 
-    /* Activation function */
-    void                      (*activate)(IDirect3DViewportImpl*, BOOL);
-
     /* Field used to chain viewports together */
     IDirect3DViewportImpl     *next;
 
@@ -611,11 +564,9 @@ struct IDirect3DViewportImpl
     IDirect3DMaterialImpl     *background;
 };
 
-/* Vtable */
-extern const IDirect3DViewport3Vtbl IDirect3DViewport3_Vtbl DECLSPEC_HIDDEN;
-
 /* Helper functions */
 void viewport_activate(IDirect3DViewportImpl* This, BOOL ignore_lights) DECLSPEC_HIDDEN;
+void d3d_viewport_init(IDirect3DViewportImpl *viewport, IDirectDrawImpl *ddraw) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * IDirect3DExecuteBuffer - Wraps to D3D7
@@ -644,8 +595,8 @@ struct IDirect3DExecuteBufferImpl
     BOOL                 need_free;
 };
 
-/* The VTable */
-extern const IDirect3DExecuteBufferVtbl IDirect3DExecuteBuffer_Vtbl DECLSPEC_HIDDEN;
+HRESULT d3d_execute_buffer_init(IDirect3DExecuteBufferImpl *execute_buffer,
+        IDirect3DDeviceImpl *device, D3DEXECUTEBUFFERDESC *desc) DECLSPEC_HIDDEN;
 
 /* The execute function */
 void IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
@@ -671,9 +622,8 @@ struct IDirect3DVertexBufferImpl
     DWORD                fvf;
 };
 
-/* The Vtables */
-extern const IDirect3DVertexBuffer7Vtbl IDirect3DVertexBuffer7_Vtbl DECLSPEC_HIDDEN;
-extern const IDirect3DVertexBufferVtbl IDirect3DVertexBuffer1_Vtbl DECLSPEC_HIDDEN;
+HRESULT d3d_vertex_buffer_init(IDirect3DVertexBufferImpl *buffer,
+        IDirectDrawImpl *ddraw, D3DVERTEXBUFFERDESC *desc) DECLSPEC_HIDDEN;
 
 static inline IDirect3DVertexBufferImpl *vb_from_vb1(IDirect3DVertexBuffer *iface)
 {
@@ -691,8 +641,8 @@ static inline IDirect3DVertexBufferImpl *vb_from_vb1(IDirect3DVertexBuffer *ifac
 #define GET_TEXCOORD_SIZE_FROM_FVF(d3dvtVertexType, tex_num) \
     (((((d3dvtVertexType) >> (16 + (2 * (tex_num)))) + 1) & 0x03) + 1)
 
-void PixelFormat_WineD3DtoDD(DDPIXELFORMAT *DDPixelFormat, WINED3DFORMAT WineD3DFormat) DECLSPEC_HIDDEN;
-WINED3DFORMAT PixelFormat_DD2WineD3D(const DDPIXELFORMAT *DDPixelFormat) DECLSPEC_HIDDEN;
+void PixelFormat_WineD3DtoDD(DDPIXELFORMAT *DDPixelFormat, enum wined3d_format_id WineD3DFormat) DECLSPEC_HIDDEN;
+enum wined3d_format_id PixelFormat_DD2WineD3D(const DDPIXELFORMAT *DDPixelFormat) DECLSPEC_HIDDEN;
 void DDRAW_dump_surface_desc(const DDSURFACEDESC2 *lpddsd) DECLSPEC_HIDDEN;
 void dump_D3DMATRIX(const D3DMATRIX *mat) DECLSPEC_HIDDEN;
 void DDRAW_dump_DDCAPS(const DDCAPS *lpcaps) DECLSPEC_HIDDEN;
diff --git a/reactos/dll/directx/wine/ddraw/ddraw_thunks.c b/reactos/dll/directx/wine/ddraw/ddraw_thunks.c
deleted file mode 100644 (file)
index 9d60624..0000000
+++ /dev/null
@@ -1,912 +0,0 @@
-/* Direct Draw Thunks and old vtables
- * Copyright 2000 TransGaming Technologies Inc.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "wine/port.h"
-
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-#define NONAMELESSUNION
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
-#include "ddraw_private.h"
-#include "wine/debug.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(ddraw_thunk);
-WINE_DECLARE_DEBUG_CHANNEL(ddraw);
-
-static HRESULT WINAPI
-IDirectDrawImpl_QueryInterface(LPDIRECTDRAW This, REFIID iid, LPVOID *ppObj)
-{
-    return IDirectDraw7_QueryInterface((IDirectDraw7 *)ddraw_from_ddraw1(This), iid, ppObj);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_QueryInterface(LPDIRECTDRAW2 This, REFIID iid, LPVOID *ppObj)
-{
-    return IDirectDraw7_QueryInterface((IDirectDraw7 *)ddraw_from_ddraw2(This), iid, ppObj);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_QueryInterface(LPDIRECTDRAW4 This, REFIID iid, LPVOID *ppObj)
-{
-    return IDirectDraw7_QueryInterface((IDirectDraw7 *)ddraw_from_ddraw4(This), iid, ppObj);
-}
-
-static ULONG WINAPI
-IDirectDrawImpl_AddRef(LPDIRECTDRAW iface)
-{
-    IDirectDrawImpl *This = ddraw_from_ddraw1(iface);
-    ULONG ref = InterlockedIncrement(&This->ref1);
-
-    TRACE("(%p) : incrementing IDirectDraw refcount from %u.\n", This, ref -1);
-
-    if(ref == 1) InterlockedIncrement(&This->numIfaces);
-
-    return ref;
-}
-
-static ULONG WINAPI
-IDirectDraw2Impl_AddRef(LPDIRECTDRAW2 iface)
-{
-    IDirectDrawImpl *This = ddraw_from_ddraw2(iface);
-    ULONG ref = InterlockedIncrement(&This->ref2);
-
-    TRACE("(%p) : incrementing IDirectDraw2 refcount from %u.\n", This, ref -1);
-
-    if(ref == 1) InterlockedIncrement(&This->numIfaces);
-
-    return ref;
-}
-
-static ULONG WINAPI
-IDirectDraw4Impl_AddRef(LPDIRECTDRAW4 iface)
-{
-    IDirectDrawImpl *This = ddraw_from_ddraw4(iface);
-    ULONG ref = InterlockedIncrement(&This->ref4);
-
-    TRACE("(%p) : incrementing IDirectDraw4 refcount from %u.\n", This, ref -1);
-
-    if(ref == 1) InterlockedIncrement(&This->numIfaces);
-
-    return ref;
-}
-
-static ULONG WINAPI
-IDirectDrawImpl_Release(LPDIRECTDRAW iface)
-{
-    IDirectDrawImpl *This = ddraw_from_ddraw1(iface);
-    ULONG ref = InterlockedDecrement(&This->ref1);
-
-    TRACE_(ddraw)("(%p)->() decrementing IDirectDraw refcount from %u.\n", This, ref +1);
-
-    if(ref == 0)
-    {
-        ULONG ifacecount = InterlockedDecrement(&This->numIfaces);
-        if(ifacecount == 0) IDirectDrawImpl_Destroy(This);
-    }
-
-    return ref;
-}
-
-static ULONG WINAPI
-IDirectDraw2Impl_Release(LPDIRECTDRAW2 iface)
-{
-    IDirectDrawImpl *This = ddraw_from_ddraw2(iface);
-    ULONG ref = InterlockedDecrement(&This->ref2);
-
-    TRACE_(ddraw)("(%p)->() decrementing IDirectDraw2 refcount from %u.\n", This, ref +1);
-
-    if(ref == 0)
-    {
-        ULONG ifacecount = InterlockedDecrement(&This->numIfaces);
-        if(ifacecount == 0) IDirectDrawImpl_Destroy(This);
-    }
-
-    return ref;
-}
-
-static ULONG WINAPI
-IDirectDraw4Impl_Release(LPDIRECTDRAW4 iface)
-{
-    IDirectDrawImpl *This = ddraw_from_ddraw4(iface);
-    ULONG ref = InterlockedDecrement(&This->ref4);
-
-    TRACE_(ddraw)("(%p)->() decrementing IDirectDraw4 refcount from %u.\n", This, ref +1);
-
-    if(ref == 0)
-    {
-        ULONG ifacecount = InterlockedDecrement(&This->numIfaces);
-        if(ifacecount == 0) IDirectDrawImpl_Destroy(This);
-    }
-
-    return ref;
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_Compact(LPDIRECTDRAW This)
-{
-    return IDirectDraw7_Compact((IDirectDraw7 *)ddraw_from_ddraw1(This));
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_Compact(LPDIRECTDRAW2 This)
-{
-    return IDirectDraw7_Compact((IDirectDraw7 *)ddraw_from_ddraw2(This));
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_Compact(LPDIRECTDRAW4 This)
-{
-    return IDirectDraw7_Compact((IDirectDraw7 *)ddraw_from_ddraw4(This));
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_CreateClipper(LPDIRECTDRAW This, DWORD dwFlags,
-                             LPDIRECTDRAWCLIPPER *ppClipper,
-                             IUnknown *pUnkOuter)
-{
-    return IDirectDraw7_CreateClipper((IDirectDraw7 *)ddraw_from_ddraw1(This), dwFlags, ppClipper, pUnkOuter);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_CreateClipper(LPDIRECTDRAW2 This, DWORD dwFlags,
-                              LPDIRECTDRAWCLIPPER *ppClipper,
-                              IUnknown *pUnkOuter)
-{
-    return IDirectDraw7_CreateClipper((IDirectDraw7 *)ddraw_from_ddraw2(This), dwFlags, ppClipper, pUnkOuter);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_CreateClipper(LPDIRECTDRAW4 This, DWORD dwFlags,
-                              LPDIRECTDRAWCLIPPER *ppClipper,
-                              IUnknown *pUnkOuter)
-{
-    return IDirectDraw7_CreateClipper((IDirectDraw7 *)ddraw_from_ddraw4(This), dwFlags, ppClipper, pUnkOuter);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_CreatePalette(LPDIRECTDRAW This, DWORD dwFlags,
-                             LPPALETTEENTRY pEntries,
-                             LPDIRECTDRAWPALETTE *ppPalette,
-                             IUnknown *pUnkOuter)
-{
-    HRESULT hr;
-    hr = IDirectDraw7_CreatePalette((IDirectDraw7 *)ddraw_from_ddraw1(This), dwFlags, pEntries, ppPalette, pUnkOuter);
-    if(SUCCEEDED(hr) && *ppPalette)
-    {
-        IDirectDrawPaletteImpl *impl = (IDirectDrawPaletteImpl *)*ppPalette;
-        IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw1(This));
-        impl->ifaceToRelease = NULL;
-
-    }
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_CreatePalette(LPDIRECTDRAW2 This, DWORD dwFlags,
-                              LPPALETTEENTRY pEntries,
-                              LPDIRECTDRAWPALETTE *ppPalette,
-                              IUnknown *pUnkOuter)
-{
-    HRESULT hr;
-    hr = IDirectDraw7_CreatePalette((IDirectDraw7 *)ddraw_from_ddraw2(This), dwFlags, pEntries, ppPalette, pUnkOuter);
-    if(SUCCEEDED(hr) && *ppPalette)
-    {
-        IDirectDrawPaletteImpl *impl = (IDirectDrawPaletteImpl *)*ppPalette;
-        IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw2(This));
-        impl->ifaceToRelease = NULL;
-    }
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_CreatePalette(LPDIRECTDRAW4 This, DWORD dwFlags,
-                              LPPALETTEENTRY pEntries,
-                              LPDIRECTDRAWPALETTE *ppPalette,
-                              IUnknown *pUnkOuter)
-{
-    HRESULT hr;
-    hr = IDirectDraw7_CreatePalette((IDirectDraw7 *)ddraw_from_ddraw4(This), dwFlags, pEntries, ppPalette, pUnkOuter);
-    if(SUCCEEDED(hr) && *ppPalette)
-    {
-        IDirectDrawPaletteImpl *impl = (IDirectDrawPaletteImpl *)*ppPalette;
-        IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw4(This));
-        IDirectDraw4_AddRef(This);
-        impl->ifaceToRelease = (IUnknown *) This;
-    }
-    return hr;
-}
-
-/* Must set all attached surfaces (e.g. mipmaps) versions as well */
-static void set_surf_version(IDirectDrawSurfaceImpl *surf, int version)
-{
-    int i;
-    TRACE("%p->version(%d) = %d\n", surf, surf->version, version);
-    surf->version = version;
-    for(i = 0; i < MAX_COMPLEX_ATTACHED; i++)
-    {
-        if(!surf->complex_array[i]) break;
-        set_surf_version(surf->complex_array[i], version);
-    }
-    while( (surf = surf->next_attached) )
-    {
-        set_surf_version(surf, version);
-    }
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_CreateSurface(LPDIRECTDRAW This, LPDDSURFACEDESC pSDesc,
-                             LPDIRECTDRAWSURFACE *ppSurface,
-                             IUnknown *pUnkOuter)
-{
-    LPDIRECTDRAWSURFACE7 pSurface7;
-    IDirectDrawSurfaceImpl *impl;
-    HRESULT hr;
-
-    /* Remove front buffer flag, this causes failure in v7, and its added to normal
-     * primaries anyway
-     */
-    pSDesc->ddsCaps.dwCaps &= ~DDSCAPS_FRONTBUFFER;
-    /* the LPDDSURFACEDESC -> LPDDSURFACEDESC2 conversion should be ok,
-     * since the data layout is the same */
-    hr = IDirectDraw7_CreateSurface((IDirectDraw7 *)ddraw_from_ddraw1(This),
-            (LPDDSURFACEDESC2)pSDesc, &pSurface7, pUnkOuter);
-    if (FAILED(hr))
-    {
-        *ppSurface = NULL;
-        return hr;
-    }
-
-    impl = (IDirectDrawSurfaceImpl *)pSurface7;
-    *ppSurface = (IDirectDrawSurface *)&impl->IDirectDrawSurface3_vtbl;
-    set_surf_version(impl, 1);
-    IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw1(This));
-    impl->ifaceToRelease = NULL;
-
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_CreateSurface(LPDIRECTDRAW2 This, LPDDSURFACEDESC pSDesc,
-                              LPDIRECTDRAWSURFACE *ppSurface,
-                              IUnknown *pUnkOuter)
-{
-    LPDIRECTDRAWSURFACE7 pSurface7;
-    IDirectDrawSurfaceImpl *impl;
-    HRESULT hr;
-
-    hr = IDirectDraw7_CreateSurface((IDirectDraw7 *)ddraw_from_ddraw2(This),
-            (LPDDSURFACEDESC2)pSDesc, &pSurface7, pUnkOuter);
-    if (FAILED(hr))
-    {
-        *ppSurface = NULL;
-        return hr;
-    }
-
-    impl = (IDirectDrawSurfaceImpl *)pSurface7;
-    *ppSurface = (IDirectDrawSurface *)&impl->IDirectDrawSurface3_vtbl;
-    set_surf_version(impl, 2);
-    IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw2(This));
-    impl->ifaceToRelease = NULL;
-
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_CreateSurface(LPDIRECTDRAW4 This, LPDDSURFACEDESC2 pSDesc,
-                              LPDIRECTDRAWSURFACE4 *ppSurface,
-                              IUnknown *pUnkOuter)
-{
-    HRESULT hr;
-    IDirectDrawSurfaceImpl *impl;
-
-    hr = IDirectDraw7_CreateSurface((IDirectDraw7 *)ddraw_from_ddraw4(This),
-            pSDesc, (LPDIRECTDRAWSURFACE7 *)ppSurface, pUnkOuter);
-    impl = (IDirectDrawSurfaceImpl *)*ppSurface;
-    if(SUCCEEDED(hr) && impl)
-    {
-        set_surf_version(impl, 4);
-        IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw4(This));
-        IDirectDraw4_AddRef(This);
-        impl->ifaceToRelease = (IUnknown *) This;
-    }
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_DuplicateSurface(LPDIRECTDRAW This, LPDIRECTDRAWSURFACE pSrc,
-                                LPDIRECTDRAWSURFACE *ppDst)
-{
-    LPDIRECTDRAWSURFACE7 pDst7;
-    HRESULT hr;
-
-    hr = IDirectDraw7_DuplicateSurface((IDirectDraw7 *)ddraw_from_ddraw1(This),
-            pSrc ? (IDirectDrawSurface7 *)surface_from_surface3((IDirectDrawSurface3 *)pSrc) : NULL, &pDst7);
-
-    /* This coercion is safe, since the IDirectDrawSurface3 vtable has the
-     * IDirectDrawSurface vtable layout at the beginning  */
-    *ppDst = pDst7 ? (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)pDst7)->IDirectDrawSurface3_vtbl : NULL;
-
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_DuplicateSurface(LPDIRECTDRAW2 This, LPDIRECTDRAWSURFACE pSrc,
-                                 LPDIRECTDRAWSURFACE *ppDst)
-{
-    LPDIRECTDRAWSURFACE7 pDst7;
-    HRESULT hr;
-
-    hr = IDirectDraw7_DuplicateSurface((IDirectDraw7 *)ddraw_from_ddraw2(This),
-            pSrc ? (IDirectDrawSurface7 *)surface_from_surface3((IDirectDrawSurface3 *)pSrc) : NULL, &pDst7);
-
-    /* This coercion is safe, since the IDirectDrawSurface3 vtable has the
-     * IDirectDrawSurface vtable layout at the beginning  */
-    *ppDst = pDst7 ? (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)pDst7)->IDirectDrawSurface3_vtbl : NULL;
-
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_DuplicateSurface(LPDIRECTDRAW4 This,
-                                 LPDIRECTDRAWSURFACE4 pSrc,
-                                 LPDIRECTDRAWSURFACE4 *ppDst)
-{
-    return IDirectDraw7_DuplicateSurface((IDirectDraw7 *)ddraw_from_ddraw4(This),
-            (LPDIRECTDRAWSURFACE7)pSrc, (LPDIRECTDRAWSURFACE7 *)ppDst);
-}
-
-struct displaymodescallback_context
-{
-    LPDDENUMMODESCALLBACK func;
-    LPVOID context;
-};
-
-static HRESULT CALLBACK
-EnumDisplayModesCallbackThunk(LPDDSURFACEDESC2 pDDSD2, LPVOID context)
-{
-    DDSURFACEDESC DDSD;
-    struct displaymodescallback_context *cbcontext = context;
-
-    memcpy(&DDSD,pDDSD2,sizeof(DDSD));
-    DDSD.dwSize = sizeof(DDSD);
-
-    return cbcontext->func(&DDSD, cbcontext->context);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_EnumDisplayModes(LPDIRECTDRAW This, DWORD dwFlags,
-                                LPDDSURFACEDESC pDDSD, LPVOID context,
-                                LPDDENUMMODESCALLBACK cb)
-{
-    struct displaymodescallback_context cbcontext;
-
-    cbcontext.func    = cb;
-    cbcontext.context = context;
-
-    return IDirectDraw7_EnumDisplayModes((IDirectDraw7 *)ddraw_from_ddraw1(This),
-            dwFlags, (LPDDSURFACEDESC2)pDDSD, &cbcontext, EnumDisplayModesCallbackThunk);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_EnumDisplayModes(LPDIRECTDRAW2 This, DWORD dwFlags,
-                                 LPDDSURFACEDESC pDDSD, LPVOID context,
-                                 LPDDENUMMODESCALLBACK cb)
-{
-    struct displaymodescallback_context cbcontext;
-
-    cbcontext.func    = cb;
-    cbcontext.context = context;
-
-    return IDirectDraw7_EnumDisplayModes((IDirectDraw7 *)ddraw_from_ddraw2(This),
-            dwFlags, (LPDDSURFACEDESC2)pDDSD, &cbcontext, EnumDisplayModesCallbackThunk);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_EnumDisplayModes(LPDIRECTDRAW4 This, DWORD dwFlags,
-                                 LPDDSURFACEDESC2 pDDSD, LPVOID context,
-                                 LPDDENUMMODESCALLBACK2 cb)
-{
-    return IDirectDraw7_EnumDisplayModes((IDirectDraw7 *)ddraw_from_ddraw4(This), dwFlags, pDDSD, context, cb);
-}
-
-struct surfacescallback_context
-{
-    LPDDENUMSURFACESCALLBACK func;
-    LPVOID context;
-};
-
-static HRESULT CALLBACK
-EnumSurfacesCallbackThunk(LPDIRECTDRAWSURFACE7 pSurf, LPDDSURFACEDESC2 pDDSD,
-                         LPVOID context)
-{
-    struct surfacescallback_context *cbcontext = context;
-
-    /* This coercion is safe, since the IDirectDrawSurface3 vtable has the
-     * IDirectDrawSurface vtable layout at the beginning  */
-    return cbcontext->func(
-            pSurf ? (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)pSurf)->IDirectDrawSurface3_vtbl : NULL,
-            (LPDDSURFACEDESC)pDDSD, cbcontext->context);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_EnumSurfaces(LPDIRECTDRAW This, DWORD dwFlags,
-                            LPDDSURFACEDESC pDDSD, LPVOID context,
-                            LPDDENUMSURFACESCALLBACK cb)
-{
-    struct surfacescallback_context cbcontext;
-
-    cbcontext.func    = cb;
-    cbcontext.context = context;
-
-    return IDirectDraw7_EnumSurfaces((IDirectDraw7 *)ddraw_from_ddraw1(This),
-            dwFlags, (LPDDSURFACEDESC2)pDDSD, &cbcontext, EnumSurfacesCallbackThunk);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_EnumSurfaces(LPDIRECTDRAW2 This, DWORD dwFlags,
-                             LPDDSURFACEDESC pDDSD, LPVOID context,
-                             LPDDENUMSURFACESCALLBACK cb)
-{
-    struct surfacescallback_context cbcontext;
-
-    cbcontext.func    = cb;
-    cbcontext.context = context;
-
-    return IDirectDraw7_EnumSurfaces((IDirectDraw7 *)ddraw_from_ddraw2(This),
-            dwFlags, (LPDDSURFACEDESC2)pDDSD, &cbcontext, EnumSurfacesCallbackThunk);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_EnumSurfaces(LPDIRECTDRAW4 This, DWORD dwFlags,
-                             LPDDSURFACEDESC2 pDDSD, LPVOID context,
-                             LPDDENUMSURFACESCALLBACK2 cb)
-{
-    return IDirectDraw7_EnumSurfaces((IDirectDraw7 *)ddraw_from_ddraw4(This),
-            dwFlags, pDDSD, context, (LPDDENUMSURFACESCALLBACK7)cb);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_FlipToGDISurface(LPDIRECTDRAW This)
-{
-    return IDirectDraw7_FlipToGDISurface((IDirectDraw7 *)ddraw_from_ddraw1(This));
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_FlipToGDISurface(LPDIRECTDRAW2 This)
-{
-    return IDirectDraw7_FlipToGDISurface((IDirectDraw7 *)ddraw_from_ddraw2(This));
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_FlipToGDISurface(LPDIRECTDRAW4 This)
-{
-    return IDirectDraw7_FlipToGDISurface((IDirectDraw7 *)ddraw_from_ddraw4(This));
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_GetCaps(LPDIRECTDRAW This, LPDDCAPS pDDC1, LPDDCAPS pDDC2)
-{
-    return IDirectDraw7_GetCaps((IDirectDraw7 *)ddraw_from_ddraw1(This), pDDC1, pDDC2);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_GetCaps(LPDIRECTDRAW2 This, LPDDCAPS pDDC1, LPDDCAPS pDDC2)
-{
-    return IDirectDraw7_GetCaps((IDirectDraw7 *)ddraw_from_ddraw2(This), pDDC1, pDDC2);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetCaps(LPDIRECTDRAW4 This, LPDDCAPS pDDC1, LPDDCAPS pDDC2)
-{
-    return IDirectDraw7_GetCaps((IDirectDraw7 *)ddraw_from_ddraw4(This), pDDC1, pDDC2);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_GetDisplayMode(LPDIRECTDRAW This, LPDDSURFACEDESC pDDSD)
-{
-    return IDirectDraw7_GetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw1(This), (LPDDSURFACEDESC2)pDDSD);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_GetDisplayMode(LPDIRECTDRAW2 This, LPDDSURFACEDESC pDDSD)
-{
-    return IDirectDraw7_GetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw2(This), (LPDDSURFACEDESC2)pDDSD);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetDisplayMode(LPDIRECTDRAW4 This, LPDDSURFACEDESC2 pDDSD)
-{
-    return IDirectDraw7_GetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw4(This), (LPDDSURFACEDESC2)pDDSD);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_GetFourCCCodes(LPDIRECTDRAW This, LPDWORD lpNumCodes,
-                              LPDWORD lpCodes)
-{
-    return IDirectDraw7_GetFourCCCodes((IDirectDraw7 *)ddraw_from_ddraw1(This), lpNumCodes, lpCodes);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_GetFourCCCodes(LPDIRECTDRAW2 This, LPDWORD lpNumCodes,
-                               LPDWORD lpCodes)
-{
-    return IDirectDraw7_GetFourCCCodes((IDirectDraw7 *)ddraw_from_ddraw2(This), lpNumCodes, lpCodes);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetFourCCCodes(LPDIRECTDRAW4 This, LPDWORD lpNumCodes,
-                               LPDWORD lpCodes)
-{
-    return IDirectDraw7_GetFourCCCodes((IDirectDraw7 *)ddraw_from_ddraw4(This), lpNumCodes, lpCodes);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_GetGDISurface(LPDIRECTDRAW This, LPDIRECTDRAWSURFACE *ppSurf)
-{
-    LPDIRECTDRAWSURFACE7 pSurf7;
-    HRESULT hr;
-
-    hr = IDirectDraw7_GetGDISurface((IDirectDraw7 *)ddraw_from_ddraw1(This), &pSurf7);
-
-    /* This coercion is safe, since the IDirectDrawSurface3 vtable has the
-     * IDirectDrawSurface vtable layout at the beginning  */
-    *ppSurf = pSurf7 ? (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)pSurf7)->IDirectDrawSurface3_vtbl : NULL;
-
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_GetGDISurface(LPDIRECTDRAW2 This, LPDIRECTDRAWSURFACE *ppSurf)
-{
-    LPDIRECTDRAWSURFACE7 pSurf7;
-    HRESULT hr;
-
-    hr = IDirectDraw7_GetGDISurface((IDirectDraw7 *)ddraw_from_ddraw2(This), &pSurf7);
-
-    /* This coercion is safe, since the IDirectDrawSurface3 vtable has the
-     * IDirectDrawSurface vtable layout at the beginning  */
-    *ppSurf = pSurf7 ? (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)pSurf7)->IDirectDrawSurface3_vtbl : NULL;
-
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetGDISurface(LPDIRECTDRAW4 This,
-                              LPDIRECTDRAWSURFACE4 *ppSurf)
-{
-    return IDirectDraw7_GetGDISurface((IDirectDraw7 *)ddraw_from_ddraw4(This), (LPDIRECTDRAWSURFACE7 *)ppSurf);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_GetMonitorFrequency(LPDIRECTDRAW This, LPDWORD pdwFreq)
-{
-    return IDirectDraw7_GetMonitorFrequency((IDirectDraw7 *)ddraw_from_ddraw1(This), pdwFreq);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_GetMonitorFrequency(LPDIRECTDRAW2 This, LPDWORD pdwFreq)
-{
-    return IDirectDraw7_GetMonitorFrequency((IDirectDraw7 *)ddraw_from_ddraw2(This), pdwFreq);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetMonitorFrequency(LPDIRECTDRAW4 This, LPDWORD pdwFreq)
-{
-    return IDirectDraw7_GetMonitorFrequency((IDirectDraw7 *)ddraw_from_ddraw4(This), pdwFreq);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_GetScanLine(LPDIRECTDRAW This, LPDWORD pdwLine)
-{
-    return IDirectDraw7_GetScanLine((IDirectDraw7 *)ddraw_from_ddraw1(This), pdwLine);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_GetScanLine(LPDIRECTDRAW2 This, LPDWORD pdwLine)
-{
-    return IDirectDraw7_GetScanLine((IDirectDraw7 *)ddraw_from_ddraw2(This), pdwLine);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetScanLine(LPDIRECTDRAW4 This, LPDWORD pdwLine)
-{
-    return IDirectDraw7_GetScanLine((IDirectDraw7 *)ddraw_from_ddraw4(This), pdwLine);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_GetVerticalBlankStatus(LPDIRECTDRAW This, LPBOOL lpbIsInVB)
-{
-    return IDirectDraw7_GetVerticalBlankStatus((IDirectDraw7 *)ddraw_from_ddraw1(This), lpbIsInVB);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_GetVerticalBlankStatus(LPDIRECTDRAW2 This, LPBOOL lpbIsInVB)
-{
-    return IDirectDraw7_GetVerticalBlankStatus((IDirectDraw7 *)ddraw_from_ddraw2(This), lpbIsInVB);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetVerticalBlankStatus(LPDIRECTDRAW4 This, LPBOOL lpbIsInVB)
-{
-    return IDirectDraw7_GetVerticalBlankStatus((IDirectDraw7 *)ddraw_from_ddraw4(This), lpbIsInVB);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_Initialize(LPDIRECTDRAW iface, LPGUID pGUID)
-{
-    IDirectDrawImpl *This = ddraw_from_ddraw1(iface);
-    HRESULT ret_value;
-
-    ret_value = IDirectDraw7_Initialize((IDirectDraw7 *)This, pGUID);
-
-    return ret_value;
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_Initialize(LPDIRECTDRAW2 iface, LPGUID pGUID)
-{
-    IDirectDrawImpl *This = ddraw_from_ddraw2(iface);
-    HRESULT ret_value;
-
-    ret_value = IDirectDraw7_Initialize((IDirectDraw7 *)This, pGUID);
-
-    return ret_value;
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_Initialize(LPDIRECTDRAW4 iface, LPGUID pGUID)
-{
-    IDirectDrawImpl *This = ddraw_from_ddraw4(iface);
-    HRESULT ret_value;
-
-    ret_value = IDirectDraw7_Initialize((IDirectDraw7 *)This, pGUID);
-
-    return ret_value;
-}
-
-
-static HRESULT WINAPI
-IDirectDrawImpl_RestoreDisplayMode(LPDIRECTDRAW This)
-{
-    return IDirectDraw7_RestoreDisplayMode((IDirectDraw7 *)ddraw_from_ddraw1(This));
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_RestoreDisplayMode(LPDIRECTDRAW2 This)
-{
-    return IDirectDraw7_RestoreDisplayMode((IDirectDraw7 *)ddraw_from_ddraw2(This));
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_RestoreDisplayMode(LPDIRECTDRAW4 This)
-{
-    return IDirectDraw7_RestoreDisplayMode((IDirectDraw7 *)ddraw_from_ddraw4(This));
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_SetCooperativeLevel(LPDIRECTDRAW This, HWND hWnd,
-                                   DWORD dwFlags)
-{
-    return IDirectDraw7_SetCooperativeLevel((IDirectDraw7 *)ddraw_from_ddraw1(This), hWnd, dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_SetCooperativeLevel(LPDIRECTDRAW2 This, HWND hWnd,
-                                    DWORD dwFlags)
-{
-    return IDirectDraw7_SetCooperativeLevel((IDirectDraw7 *)ddraw_from_ddraw2(This), hWnd, dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_SetCooperativeLevel(LPDIRECTDRAW4 This, HWND hWnd,
-                                    DWORD dwFlags)
-{
-    return IDirectDraw7_SetCooperativeLevel((IDirectDraw7 *)ddraw_from_ddraw4(This), hWnd, dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_SetDisplayMode(LPDIRECTDRAW This, DWORD a, DWORD b, DWORD c)
-{
-    return IDirectDraw7_SetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw1(This), a, b, c, 0, 0);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_SetDisplayMode(LPDIRECTDRAW2 This, DWORD a, DWORD b, DWORD c,
-                               DWORD d, DWORD e)
-{
-    return IDirectDraw7_SetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw2(This), a, b, c, d, e);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_SetDisplayMode(LPDIRECTDRAW4 This, DWORD a, DWORD b, DWORD c,
-                               DWORD d, DWORD e)
-{
-    return IDirectDraw7_SetDisplayMode((IDirectDraw7 *)ddraw_from_ddraw4(This), a, b, c, d, e);
-}
-
-static HRESULT WINAPI
-IDirectDrawImpl_WaitForVerticalBlank(LPDIRECTDRAW This, DWORD dwFlags,
-                                    HANDLE hEvent)
-{
-    return IDirectDraw7_WaitForVerticalBlank((IDirectDraw7 *)ddraw_from_ddraw1(This), dwFlags, hEvent);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_WaitForVerticalBlank(LPDIRECTDRAW2 This, DWORD dwFlags,
-                                     HANDLE hEvent)
-{
-    return IDirectDraw7_WaitForVerticalBlank((IDirectDraw7 *)ddraw_from_ddraw2(This), dwFlags, hEvent);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_WaitForVerticalBlank(LPDIRECTDRAW4 This, DWORD dwFlags,
-                                     HANDLE hEvent)
-{
-    return IDirectDraw7_WaitForVerticalBlank((IDirectDraw7 *)ddraw_from_ddraw4(This), dwFlags, hEvent);
-}
-
-static HRESULT WINAPI
-IDirectDraw2Impl_GetAvailableVidMem(LPDIRECTDRAW2 This, LPDDSCAPS pCaps,
-                                   LPDWORD pdwTotal, LPDWORD pdwFree)
-{
-    DDSCAPS2 Caps2;
-    DDRAW_Convert_DDSCAPS_1_To_2(pCaps, &Caps2);
-
-    return IDirectDraw7_GetAvailableVidMem((IDirectDraw7 *)ddraw_from_ddraw2(This), &Caps2, pdwTotal, pdwFree);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetAvailableVidMem(LPDIRECTDRAW4 This, LPDDSCAPS2 pCaps,
-                                   LPDWORD pdwTotal, LPDWORD pdwFree)
-{
-    return IDirectDraw7_GetAvailableVidMem((IDirectDraw7 *)ddraw_from_ddraw4(This), pCaps, pdwTotal, pdwFree);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetSurfaceFromDC(LPDIRECTDRAW4 This, HDC hDC,
-                                 LPDIRECTDRAWSURFACE4 *pSurf)
-{
-    return IDirectDraw7_GetSurfaceFromDC((IDirectDraw7 *)ddraw_from_ddraw4(This), hDC, (LPDIRECTDRAWSURFACE7 *)pSurf);
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_RestoreAllSurfaces(LPDIRECTDRAW4 This)
-{
-    return IDirectDraw7_RestoreAllSurfaces((IDirectDraw7 *)ddraw_from_ddraw4(This));
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_TestCooperativeLevel(LPDIRECTDRAW4 This)
-{
-    return IDirectDraw7_TestCooperativeLevel((IDirectDraw7 *)ddraw_from_ddraw4(This));
-}
-
-static HRESULT WINAPI
-IDirectDraw4Impl_GetDeviceIdentifier(LPDIRECTDRAW4 This,
-                                    LPDDDEVICEIDENTIFIER pDDDI, DWORD dwFlags)
-{
-    DDDEVICEIDENTIFIER2 DDDI2;
-    HRESULT hr;
-
-    hr = IDirectDraw7_GetDeviceIdentifier((IDirectDraw7 *)ddraw_from_ddraw4(This), &DDDI2, dwFlags);
-
-    DDRAW_Convert_DDDEVICEIDENTIFIER_2_To_1(&DDDI2, pDDDI);
-
-    return hr;
-}
-
-const IDirectDrawVtbl IDirectDraw1_Vtbl =
-{
-    IDirectDrawImpl_QueryInterface,
-    IDirectDrawImpl_AddRef,
-    IDirectDrawImpl_Release,
-    IDirectDrawImpl_Compact,
-    IDirectDrawImpl_CreateClipper,
-    IDirectDrawImpl_CreatePalette,
-    IDirectDrawImpl_CreateSurface,
-    IDirectDrawImpl_DuplicateSurface,
-    IDirectDrawImpl_EnumDisplayModes,
-    IDirectDrawImpl_EnumSurfaces,
-    IDirectDrawImpl_FlipToGDISurface,
-    IDirectDrawImpl_GetCaps,
-    IDirectDrawImpl_GetDisplayMode,
-    IDirectDrawImpl_GetFourCCCodes,
-    IDirectDrawImpl_GetGDISurface,
-    IDirectDrawImpl_GetMonitorFrequency,
-    IDirectDrawImpl_GetScanLine,
-    IDirectDrawImpl_GetVerticalBlankStatus,
-    IDirectDrawImpl_Initialize,
-    IDirectDrawImpl_RestoreDisplayMode,
-    IDirectDrawImpl_SetCooperativeLevel,
-    IDirectDrawImpl_SetDisplayMode,
-    IDirectDrawImpl_WaitForVerticalBlank,
-};
-
-const IDirectDraw2Vtbl IDirectDraw2_Vtbl =
-{
-    IDirectDraw2Impl_QueryInterface,
-    IDirectDraw2Impl_AddRef,
-    IDirectDraw2Impl_Release,
-    IDirectDraw2Impl_Compact,
-    IDirectDraw2Impl_CreateClipper,
-    IDirectDraw2Impl_CreatePalette,
-    IDirectDraw2Impl_CreateSurface,
-    IDirectDraw2Impl_DuplicateSurface,
-    IDirectDraw2Impl_EnumDisplayModes,
-    IDirectDraw2Impl_EnumSurfaces,
-    IDirectDraw2Impl_FlipToGDISurface,
-    IDirectDraw2Impl_GetCaps,
-    IDirectDraw2Impl_GetDisplayMode,
-    IDirectDraw2Impl_GetFourCCCodes,
-    IDirectDraw2Impl_GetGDISurface,
-    IDirectDraw2Impl_GetMonitorFrequency,
-    IDirectDraw2Impl_GetScanLine,
-    IDirectDraw2Impl_GetVerticalBlankStatus,
-    IDirectDraw2Impl_Initialize,
-    IDirectDraw2Impl_RestoreDisplayMode,
-    IDirectDraw2Impl_SetCooperativeLevel,
-    IDirectDraw2Impl_SetDisplayMode,
-    IDirectDraw2Impl_WaitForVerticalBlank,
-    IDirectDraw2Impl_GetAvailableVidMem
-};
-
-const IDirectDraw4Vtbl IDirectDraw4_Vtbl =
-{
-    IDirectDraw4Impl_QueryInterface,
-    IDirectDraw4Impl_AddRef,
-    IDirectDraw4Impl_Release,
-    IDirectDraw4Impl_Compact,
-    IDirectDraw4Impl_CreateClipper,
-    IDirectDraw4Impl_CreatePalette,
-    IDirectDraw4Impl_CreateSurface,
-    IDirectDraw4Impl_DuplicateSurface,
-    IDirectDraw4Impl_EnumDisplayModes,
-    IDirectDraw4Impl_EnumSurfaces,
-    IDirectDraw4Impl_FlipToGDISurface,
-    IDirectDraw4Impl_GetCaps,
-    IDirectDraw4Impl_GetDisplayMode,
-    IDirectDraw4Impl_GetFourCCCodes,
-    IDirectDraw4Impl_GetGDISurface,
-    IDirectDraw4Impl_GetMonitorFrequency,
-    IDirectDraw4Impl_GetScanLine,
-    IDirectDraw4Impl_GetVerticalBlankStatus,
-    IDirectDraw4Impl_Initialize,
-    IDirectDraw4Impl_RestoreDisplayMode,
-    IDirectDraw4Impl_SetCooperativeLevel,
-    IDirectDraw4Impl_SetDisplayMode,
-    IDirectDraw4Impl_WaitForVerticalBlank,
-    IDirectDraw4Impl_GetAvailableVidMem,
-    IDirectDraw4Impl_GetSurfaceFromDC,
-    IDirectDraw4Impl_RestoreAllSurfaces,
-    IDirectDraw4Impl_TestCooperativeLevel,
-    IDirectDraw4Impl_GetDeviceIdentifier
-};
index 9a4e5c7..9f0f631 100644 (file)
 #include "config.h"
 #include "wine/port.h"
 
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-#define NONAMELESSUNION
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
 #include "ddraw_private.h"
-#include "wine/debug.h"
 
-WINE_DEFAULT_DEBUG_CHANNEL(d3d7);
-WINE_DECLARE_DEBUG_CHANNEL(ddraw_thunk);
+WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
 /* The device ID */
 const GUID IID_D3DDEVICE_WineD3D = {
@@ -121,7 +102,8 @@ IDirect3DDeviceImpl_7_QueryInterface(IDirect3DDevice7 *iface,
                                      void **obj)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
-    TRACE("(%p)->(%s,%p)\n", This, debugstr_guid(refiid), obj);
+
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(refiid), obj);
 
     /* According to COM docs, if the QueryInterface fails, obj should be set to NULL */
     *obj = NULL;
@@ -214,9 +196,9 @@ Thunk_IDirect3DDeviceImpl_3_QueryInterface(IDirect3DDevice3 *iface,
                                            REFIID riid,
                                            void **obj)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%s,%p) thunking to IDirect3DDevice7 interface.\n", This, debugstr_guid(riid), obj);
-    return IDirect3DDevice7_QueryInterface((IDirect3DDevice7 *)This, riid, obj);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obj);
+
+    return IDirect3DDevice7_QueryInterface((IDirect3DDevice7 *)device_from_device3(iface), riid, obj);
 }
 
 static HRESULT WINAPI
@@ -224,9 +206,9 @@ Thunk_IDirect3DDeviceImpl_2_QueryInterface(IDirect3DDevice2 *iface,
                                            REFIID riid,
                                            void **obj)
 {
-    IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%s,%p) thunking to IDirect3DDevice7 interface.\n", This, debugstr_guid(riid), obj);
-    return IDirect3DDevice7_QueryInterface((IDirect3DDevice7 *)This, riid, obj);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obj);
+
+    return IDirect3DDevice7_QueryInterface((IDirect3DDevice7 *)device_from_device2(iface), riid, obj);
 }
 
 static HRESULT WINAPI
@@ -234,9 +216,9 @@ Thunk_IDirect3DDeviceImpl_1_QueryInterface(IDirect3DDevice *iface,
                                            REFIID riid,
                                            void **obp)
 {
-    IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%s,%p) thunking to IDirect3DDevice7 interface.\n", This, debugstr_guid(riid), obp);
-    return IDirect3DDevice7_QueryInterface((IDirect3DDevice7 *)This, riid, obp);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obp);
+
+    return IDirect3DDevice7_QueryInterface((IDirect3DDevice7 *)device_from_device1(iface), riid, obp);
 }
 
 /*****************************************************************************
@@ -257,7 +239,7 @@ IDirect3DDeviceImpl_7_AddRef(IDirect3DDevice7 *iface)
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    TRACE("(%p) : incrementing from %u.\n", This, ref -1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -265,23 +247,24 @@ IDirect3DDeviceImpl_7_AddRef(IDirect3DDevice7 *iface)
 static ULONG WINAPI
 Thunk_IDirect3DDeviceImpl_3_AddRef(IDirect3DDevice3 *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_AddRef((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_AddRef((IDirect3DDevice7 *)device_from_device3(iface));
 }
 
 static ULONG WINAPI
 Thunk_IDirect3DDeviceImpl_2_AddRef(IDirect3DDevice2 *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_AddRef((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_AddRef((IDirect3DDevice7 *)device_from_device2(iface));
 }
 
 static ULONG WINAPI
 Thunk_IDirect3DDeviceImpl_1_AddRef(IDirect3DDevice *iface)
 {
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", iface);
+    TRACE("iface %p.\n", iface);
+
     return IDirect3DDevice7_AddRef((IDirect3DDevice7 *)device_from_device1(iface));
 }
 
@@ -303,7 +286,7 @@ IDirect3DDeviceImpl_7_Release(IDirect3DDevice7 *iface)
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
 
-    TRACE("(%p)->() decrementing from %u.\n", This, ref +1);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     /* This method doesn't destroy the WineD3DDevice, because it's still in use for
      * 2D rendering. IDirectDrawSurface7::Release will destroy the WineD3DDevice
@@ -317,10 +300,8 @@ IDirect3DDeviceImpl_7_Release(IDirect3DDevice7 *iface)
         EnterCriticalSection(&ddraw_cs);
         /* Free the index buffer. */
         IWineD3DDevice_SetIndexBuffer(This->wineD3DDevice, NULL, WINED3DFMT_UNKNOWN);
-        IWineD3DBuffer_GetParent(This->indexbuffer,
-                                 (IUnknown **) &IndexBufferParent);
-        IParent_Release(IndexBufferParent); /* Once for the getParent */
-        if( IParent_Release(IndexBufferParent) != 0)  /* And now to destroy it */
+        IndexBufferParent = IWineD3DBuffer_GetParent(This->indexbuffer);
+        if (IParent_Release(IndexBufferParent))
         {
             ERR(" (%p) Something is still holding the index buffer parent %p\n", This, IndexBufferParent);
         }
@@ -330,34 +311,10 @@ IDirect3DDeviceImpl_7_Release(IDirect3DDevice7 *iface)
          * IDirect3DVertexBuffer::Release will unset it.
          */
 
-        /* Restore the render targets */
-        if(This->OffScreenTarget)
-        {
-            WINED3DVIEWPORT vp;
-
-            vp.X = 0;
-            vp.Y = 0;
-            vp.Width = This->ddraw->d3d_target->surface_desc.dwWidth;
-            vp.Height = This->ddraw->d3d_target->surface_desc.dwHeight;
-            vp.MinZ = 0.0;
-            vp.MaxZ = 1.0;
-            IWineD3DDevice_SetViewport(This->wineD3DDevice,
-                                       &vp);
-
-            /* Set the device up to render to the front buffer since the back buffer will
-             * vanish soon.
-             */
-            IWineD3DDevice_SetRenderTarget(This->wineD3DDevice, 0,
-                                           This->ddraw->d3d_target->WineD3DSurface,
-                                           FALSE);
-            /* This->target is the offscreen target.
-             * This->ddraw->d3d_target is the target used by DDraw
-             */
-            TRACE("(%p) Release: Using %p as front buffer, %p as back buffer\n", This, This->ddraw->d3d_target, NULL);
-            IWineD3DDevice_SetFrontBackBuffers(This->wineD3DDevice,
-                                               This->ddraw->d3d_target->WineD3DSurface,
-                                               NULL);
-        }
+        /* Set the device up to render to the front buffer since the back
+         * buffer will vanish soon. */
+        IWineD3DDevice_SetRenderTarget(This->wineD3DDevice, 0,
+                This->ddraw->d3d_target->WineD3DSurface, TRUE);
 
         /* Release the WineD3DDevice. This won't destroy it */
         if(IWineD3DDevice_Release(This->wineD3DDevice) <= 0)
@@ -366,53 +323,55 @@ IDirect3DDeviceImpl_7_Release(IDirect3DDevice7 *iface)
         }
 
         /* The texture handles should be unset by now, but there might be some bits
-         * missing in our reference counting(needs test). Do a sanity check
-         */
-        for(i = 0; i < This->numHandles; i++)
+         * missing in our reference counting(needs test). Do a sanity check. */
+        for (i = 0; i < This->handle_table.entry_count; ++i)
         {
-            if(This->Handles[i].ptr)
+            struct ddraw_handle_entry *entry = &This->handle_table.entries[i];
+
+            switch (entry->type)
             {
-                switch(This->Handles[i].type)
-                {
-                    case DDrawHandle_Texture:
-                    {
-                        IDirectDrawSurfaceImpl *surf = This->Handles[i].ptr;
-                        FIXME("Texture Handle %d not unset properly\n", i + 1);
-                        surf->Handle = 0;
-                    }
+                case DDRAW_HANDLE_FREE:
                     break;
 
-                    case DDrawHandle_Material:
-                    {
-                        IDirect3DMaterialImpl *mat = This->Handles[i].ptr;
-                        FIXME("Material handle %d not unset properly\n", i + 1);
-                        mat->Handle = 0;
-                    }
+                case DDRAW_HANDLE_MATERIAL:
+                {
+                    IDirect3DMaterialImpl *m = entry->object;
+                    FIXME("Material handle %#x (%p) not unset properly.\n", i + 1, m);
+                    m->Handle = 0;
                     break;
+                }
 
-                    case DDrawHandle_Matrix:
-                    {
-                        /* No fixme here because this might happen because of sloppy apps */
-                        WARN("Leftover matrix handle %d, deleting\n", i + 1);
-                        IDirect3DDevice_DeleteMatrix((IDirect3DDevice *)&This->IDirect3DDevice_vtbl, i + 1);
-                    }
+                case DDRAW_HANDLE_MATRIX:
+                {
+                    /* No FIXME here because this might happen because of sloppy applications. */
+                    WARN("Leftover matrix handle %#x (%p), deleting.\n", i + 1, entry->object);
+                    IDirect3DDevice_DeleteMatrix((IDirect3DDevice *)&This->IDirect3DDevice_vtbl, i + 1);
                     break;
+                }
 
-                    case DDrawHandle_StateBlock:
-                    {
-                        /* No fixme here because this might happen because of sloppy apps */
-                        WARN("Leftover stateblock handle %d, deleting\n", i + 1);
-                        IDirect3DDevice7_DeleteStateBlock((IDirect3DDevice7 *)This, i + 1);
-                    }
+                case DDRAW_HANDLE_STATEBLOCK:
+                {
+                    /* No FIXME here because this might happen because of sloppy applications. */
+                    WARN("Leftover stateblock handle %#x (%p), deleting.\n", i + 1, entry->object);
+                    IDirect3DDevice7_DeleteStateBlock(iface, i + 1);
                     break;
+                }
 
-                    default:
-                        FIXME("Unknown handle %d not unset properly\n", i + 1);
+                case DDRAW_HANDLE_SURFACE:
+                {
+                    IDirectDrawSurfaceImpl *surf = entry->object;
+                    FIXME("Texture handle %#x (%p) not unset properly.\n", i + 1, surf);
+                    surf->Handle = 0;
+                    break;
                 }
+
+                default:
+                    FIXME("Handle %#x (%p) has unknown type %#x.\n", i + 1, entry->object, entry->type);
+                    break;
             }
         }
 
-        HeapFree(GetProcessHeap(), 0, This->Handles);
+        ddraw_handle_table_destroy(&This->handle_table);
 
         TRACE("Releasing target %p %p\n", This->target, This->ddraw->d3d_target);
         /* Release the render target and the WineD3D render target
@@ -436,25 +395,25 @@ IDirect3DDeviceImpl_7_Release(IDirect3DDevice7 *iface)
 static ULONG WINAPI
 Thunk_IDirect3DDeviceImpl_3_Release(IDirect3DDevice3 *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_Release((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_Release((IDirect3DDevice7 *)device_from_device3(iface));
 }
 
 static ULONG WINAPI
 Thunk_IDirect3DDeviceImpl_2_Release(IDirect3DDevice2 *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_Release((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_Release((IDirect3DDevice7 *)device_from_device2(iface));
 }
 
 static ULONG WINAPI
 Thunk_IDirect3DDeviceImpl_1_Release(IDirect3DDevice *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_Release((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_Release((IDirect3DDevice7 *)device_from_device1(iface));
 }
 
 /*****************************************************************************
@@ -480,12 +439,10 @@ IDirect3DDeviceImpl_1_Initialize(IDirect3DDevice *iface,
                                  IDirect3D *Direct3D, GUID *guid,
                                  D3DDEVICEDESC *Desc)
 {
-    IDirect3DDeviceImpl *This = device_from_device1(iface);
-
     /* It shouldn't be crucial, but print a FIXME, I'm interested if
-     * any game calls it and when
-     */
-    FIXME("(%p)->(%p,%p,%p): No-op!\n", This, Direct3D, guid, Desc);
+     * any game calls it and when. */
+    FIXME("iface %p, d3d %p, guid %s, device_desc %p nop!\n",
+            iface, Direct3D, debugstr_guid(guid), Desc);
 
     return D3D_OK;
 }
@@ -512,7 +469,8 @@ IDirect3DDeviceImpl_7_GetCaps(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     D3DDEVICEDESC OldDesc;
-    TRACE("(%p)->(%p)\n", This, Desc);
+
+    TRACE("iface %p, device_desc %p.\n", iface, Desc);
 
     /* Call the same function used by IDirect3D, this saves code */
     return IDirect3DImpl_GetCaps(This->ddraw->wineD3D, &OldDesc, Desc);
@@ -563,7 +521,8 @@ IDirect3DDeviceImpl_3_GetCaps(IDirect3DDevice3 *iface,
     IDirect3DDeviceImpl *This = device_from_device3(iface);
     D3DDEVICEDESC7 newDesc;
     HRESULT hr;
-    TRACE("(%p)->(%p,%p)\n", iface, HWDesc, HelDesc);
+
+    TRACE("iface %p, hw_desc %p, hel_desc %p.\n", iface, HWDesc, HelDesc);
 
     hr = IDirect3DImpl_GetCaps(This->ddraw->wineD3D, HWDesc, &newDesc);
     if(hr != D3D_OK) return hr;
@@ -578,7 +537,7 @@ Thunk_IDirect3DDeviceImpl_2_GetCaps(IDirect3DDevice2 *iface,
                                     D3DDEVICEDESC *D3DHELDevDesc)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p) thunking to IDirect3DDevice3 interface.\n", This, D3DHWDevDesc, D3DHELDevDesc);
+    TRACE("iface %p, hw_desc %p, hel_desc %p.\n", iface, D3DHWDevDesc, D3DHELDevDesc);
     return IDirect3DDevice3_GetCaps((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, D3DHWDevDesc, D3DHELDevDesc);
 }
 
@@ -588,7 +547,7 @@ Thunk_IDirect3DDeviceImpl_1_GetCaps(IDirect3DDevice *iface,
                                     D3DDEVICEDESC *D3DHELDevDesc)
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p) thunking to IDirect3DDevice3 interface.\n", This, D3DHWDevDesc, D3DHELDevDesc);
+    TRACE("iface %p, hw_desc %p, hel_desc %p.\n", iface, D3DHWDevDesc, D3DHELDevDesc);
     return IDirect3DDevice3_GetCaps((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, D3DHWDevDesc, D3DHELDevDesc);
 }
 
@@ -610,18 +569,21 @@ IDirect3DDeviceImpl_2_SwapTextureHandles(IDirect3DDevice2 *iface,
                                          IDirect3DTexture2 *Tex2)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    DWORD swap;
     IDirectDrawSurfaceImpl *surf1 = surface_from_texture2(Tex1);
     IDirectDrawSurfaceImpl *surf2 = surface_from_texture2(Tex2);
-    TRACE("(%p)->(%p,%p)\n", This, surf1, surf2);
+    DWORD h1, h2;
+
+    TRACE("iface %p, tex1 %p, tex2 %p.\n", iface, Tex1, Tex2);
 
     EnterCriticalSection(&ddraw_cs);
-    This->Handles[surf1->Handle - 1].ptr = surf2;
-    This->Handles[surf2->Handle - 1].ptr = surf1;
 
-    swap = surf2->Handle;
-    surf2->Handle = surf1->Handle;
-    surf1->Handle = swap;
+    h1 = surf1->Handle - 1;
+    h2 = surf2->Handle - 1;
+    This->handle_table.entries[h1].object = surf2;
+    This->handle_table.entries[h2].object = surf1;
+    surf2->Handle = h1 + 1;
+    surf1->Handle = h2 + 1;
+
     LeaveCriticalSection(&ddraw_cs);
 
     return D3D_OK;
@@ -637,7 +599,9 @@ Thunk_IDirect3DDeviceImpl_1_SwapTextureHandles(IDirect3DDevice *iface,
     IDirectDrawSurfaceImpl *surf2 = surface_from_texture1(D3DTex2);
     IDirect3DTexture2 *t1 = surf1 ? (IDirect3DTexture2 *)&surf1->IDirect3DTexture2_vtbl : NULL;
     IDirect3DTexture2 *t2 = surf2 ? (IDirect3DTexture2 *)&surf2->IDirect3DTexture2_vtbl : NULL;
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p) thunking to IDirect3DDevice2 interface.\n", This, surf1, surf2);
+
+    TRACE("iface %p, tex1 %p, tex2 %p.\n", iface, D3DTex1, D3DTex2);
+
     return IDirect3DDevice2_SwapTextureHandles((IDirect3DDevice2 *)&This->IDirect3DDevice2_vtbl, t1, t2);
 }
 
@@ -663,8 +627,7 @@ static HRESULT WINAPI
 IDirect3DDeviceImpl_3_GetStats(IDirect3DDevice3 *iface,
                                D3DSTATS *Stats)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    FIXME("(%p)->(%p): Stub!\n", This, Stats);
+    FIXME("iface %p, stats %p stub!\n", iface, Stats);
 
     if(!Stats)
         return DDERR_INVALIDPARAMS;
@@ -684,7 +647,9 @@ Thunk_IDirect3DDeviceImpl_2_GetStats(IDirect3DDevice2 *iface,
                                      D3DSTATS *Stats)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice3 interface.\n", This, Stats);
+
+    TRACE("iface %p, stats %p.\n", iface, Stats);
+
     return IDirect3DDevice3_GetStats((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, Stats);
 }
 
@@ -693,7 +658,9 @@ Thunk_IDirect3DDeviceImpl_1_GetStats(IDirect3DDevice *iface,
                                      D3DSTATS *Stats)
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice3 interface.\n", This, Stats);
+
+    TRACE("iface %p, stats %p.\n", iface, Stats);
+
     return IDirect3DDevice3_GetStats((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, Stats);
 }
 
@@ -725,7 +692,10 @@ IDirect3DDeviceImpl_1_CreateExecuteBuffer(IDirect3DDevice *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
     IDirect3DExecuteBufferImpl* object;
-    TRACE("(%p)->(%p,%p,%p)!\n", This, Desc, ExecuteBuffer, UnkOuter);
+    HRESULT hr;
+
+    TRACE("iface %p, buffer_desc %p, buffer %p, outer_unknown %p.\n",
+            iface, Desc, ExecuteBuffer, UnkOuter);
 
     if(UnkOuter)
         return CLASS_E_NOAGGREGATION;
@@ -738,46 +708,14 @@ IDirect3DDeviceImpl_1_CreateExecuteBuffer(IDirect3DDevice *iface,
         return DDERR_OUTOFMEMORY;
     }
 
-    object->lpVtbl = &IDirect3DExecuteBuffer_Vtbl;
-    object->ref = 1;
-    object->d3ddev = This;
-
-    /* Initializes memory */
-    memcpy(&object->desc, Desc, Desc->dwSize);
-
-    /* No buffer given */
-    if ((object->desc.dwFlags & D3DDEB_LPDATA) == 0)
-        object->desc.lpData = NULL;
-
-    /* No buffer size given */
-    if ((object->desc.dwFlags & D3DDEB_BUFSIZE) == 0)
-        object->desc.dwBufferSize = 0;
-
-    /* Create buffer if asked */
-    if ((object->desc.lpData == NULL) && (object->desc.dwBufferSize > 0))
+    hr = d3d_execute_buffer_init(object, This, Desc);
+    if (FAILED(hr))
     {
-        object->need_free = TRUE;
-        object->desc.lpData = HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,object->desc.dwBufferSize);
-        if(!object->desc.lpData)
-        {
-            ERR("Out of memory when allocating the execute buffer data\n");
-            HeapFree(GetProcessHeap(), 0, object);
-            return DDERR_OUTOFMEMORY;
-        }
-    }
-    else
-    {
-        object->need_free = FALSE;
+        WARN("Failed to initialize execute buffer, hr %#x.\n", hr);
+        HeapFree(GetProcessHeap(), 0, object);
+        return hr;
     }
 
-    /* No vertices for the moment */
-    object->vertex_data = NULL;
-
-    object->desc.dwFlags |= D3DDEB_LPDATA;
-
-    object->indices = NULL;
-    object->nb_indices = 0;
-
     *ExecuteBuffer = (IDirect3DExecuteBuffer *)object;
 
     TRACE(" Returning IDirect3DExecuteBuffer at %p, implementation is at %p\n", *ExecuteBuffer, object);
@@ -810,7 +748,7 @@ IDirect3DDeviceImpl_1_Execute(IDirect3DDevice *iface,
     IDirect3DExecuteBufferImpl *Direct3DExecuteBufferImpl = (IDirect3DExecuteBufferImpl *)ExecuteBuffer;
     IDirect3DViewportImpl *Direct3DViewportImpl = (IDirect3DViewportImpl *)Viewport;
 
-    TRACE("(%p)->(%p,%p,%08x)\n", This, Direct3DExecuteBufferImpl, Direct3DViewportImpl, Flags);
+    TRACE("iface %p, buffer %p, viewport %p, flags %#x.\n", iface, ExecuteBuffer, Viewport, Flags);
 
     if(!Direct3DExecuteBufferImpl)
         return DDERR_INVALIDPARAMS;
@@ -847,7 +785,7 @@ IDirect3DDeviceImpl_3_AddViewport(IDirect3DDevice3 *iface,
     IDirect3DDeviceImpl *This = device_from_device3(iface);
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Viewport;
 
-    TRACE("(%p)->(%p)\n", This, vp);
+    TRACE("iface %p, viewport %p.\n", iface, Viewport);
 
     /* Sanity check */
     if(!vp)
@@ -869,7 +807,9 @@ Thunk_IDirect3DDeviceImpl_2_AddViewport(IDirect3DDevice2 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Direct3DViewport2;
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice3 interface.\n", This, vp);
+
+    TRACE("iface %p, viewport %p.\n", iface, Direct3DViewport2);
+
     return IDirect3DDevice3_AddViewport((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, (IDirect3DViewport3 *)vp);
 }
 
@@ -879,7 +819,9 @@ Thunk_IDirect3DDeviceImpl_1_AddViewport(IDirect3DDevice *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Direct3DViewport;
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice3 interface.\n", This, vp);
+
+    TRACE("iface %p, viewport %p.\n", iface, Direct3DViewport);
+
     return IDirect3DDevice3_AddViewport((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, (IDirect3DViewport3 *)vp);
 }
 
@@ -907,7 +849,7 @@ IDirect3DDeviceImpl_3_DeleteViewport(IDirect3DDevice3 *iface,
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *) Viewport;
     IDirect3DViewportImpl *cur_viewport, *prev_viewport = NULL;
 
-    TRACE("(%p)->(%p)\n", This, vp);
+    TRACE("iface %p, viewport %p.\n", iface, Viewport);
 
     EnterCriticalSection(&ddraw_cs);
     cur_viewport = This->viewport_list;
@@ -935,7 +877,9 @@ Thunk_IDirect3DDeviceImpl_2_DeleteViewport(IDirect3DDevice2 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Direct3DViewport2;
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice3 interface.\n", This, vp);
+
+    TRACE("iface %p, viewport %p.\n", iface, Direct3DViewport2);
+
     return IDirect3DDevice3_DeleteViewport((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, (IDirect3DViewport3 *)vp);
 }
 
@@ -945,7 +889,9 @@ Thunk_IDirect3DDeviceImpl_1_DeleteViewport(IDirect3DDevice *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Direct3DViewport;
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice3 interface.\n", This, vp);
+
+    TRACE("iface %p, viewport %p.\n", iface, Direct3DViewport);
+
     return IDirect3DDevice3_DeleteViewport((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, (IDirect3DViewport3 *)vp);
 }
 
@@ -977,7 +923,8 @@ IDirect3DDeviceImpl_3_NextViewport(IDirect3DDevice3 *iface,
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Viewport3;
     IDirect3DViewportImpl *res = NULL;
 
-    TRACE("(%p)->(%p,%p,%08x)\n", This, vp, lplpDirect3DViewport3, Flags);
+    TRACE("iface %p, viewport %p, next %p, flags %#x.\n",
+            iface, Viewport3, lplpDirect3DViewport3, Flags);
 
     if(!vp)
     {
@@ -1030,7 +977,10 @@ Thunk_IDirect3DDeviceImpl_2_NextViewport(IDirect3DDevice2 *iface,
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Viewport2;
     IDirect3DViewport3 *res;
     HRESULT hr;
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p,%08x) thunking to IDirect3DDevice3 interface.\n", This, vp, lplpDirect3DViewport2, Flags);
+
+    TRACE("iface %p, viewport %p, next %p, flags %#x.\n",
+            iface, Viewport2, lplpDirect3DViewport2, Flags);
+
     hr = IDirect3DDevice3_NextViewport((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl,
             (IDirect3DViewport3 *)vp, &res, Flags);
     *lplpDirect3DViewport2 = (IDirect3DViewport2 *)res;
@@ -1047,7 +997,10 @@ Thunk_IDirect3DDeviceImpl_1_NextViewport(IDirect3DDevice *iface,
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Viewport;
     IDirect3DViewport3 *res;
     HRESULT hr;
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p,%08x) thunking to IDirect3DDevice3 interface.\n", This, vp, lplpDirect3DViewport, Flags);
+
+    TRACE("iface %p, viewport %p, next %p, flags %#x.\n",
+            iface, Viewport, lplpDirect3DViewport, Flags);
+
     hr = IDirect3DDevice3_NextViewport((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl,
             (IDirect3DViewport3 *)vp, &res, Flags);
     *lplpDirect3DViewport = (IDirect3DViewport *)res;
@@ -1082,10 +1035,8 @@ IDirect3DDeviceImpl_1_Pick(IDirect3DDevice *iface,
                            DWORD Flags,
                            D3DRECT *Rect)
 {
-    IDirect3DDeviceImpl *This = device_from_device1(iface);
-    IDirect3DExecuteBufferImpl *execbuf = (IDirect3DExecuteBufferImpl *)ExecuteBuffer;
-    IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Viewport;
-    FIXME("(%p)->(%p,%p,%08x,%p): stub!\n", This, execbuf, vp, Flags, Rect);
+    FIXME("iface %p, buffer %p, viewport %p, flags %#x, rect %s stub!\n",
+            iface, ExecuteBuffer, Viewport, Flags, wine_dbgstr_rect((RECT *)Rect));
 
     return D3D_OK;
 }
@@ -1111,8 +1062,7 @@ IDirect3DDeviceImpl_1_GetPickRecords(IDirect3DDevice *iface,
                                      DWORD *Count,
                                      D3DPICKRECORD *D3DPickRec)
 {
-    IDirect3DDeviceImpl *This = device_from_device1(iface);
-    FIXME("(%p)->(%p,%p): stub!\n", This, Count, D3DPickRec);
+    FIXME("iface %p, count %p, records %p stub!\n", iface, Count, D3DPickRec);
 
     return D3D_OK;
 }
@@ -1146,7 +1096,8 @@ IDirect3DDeviceImpl_7_EnumTextureFormats(IDirect3DDevice7 *iface,
     WINED3DDISPLAYMODE mode;
     unsigned int i;
 
-    WINED3DFORMAT FormatList[] = {
+    static const enum wined3d_format_id FormatList[] =
+    {
         /* 32 bit */
         WINED3DFMT_B8G8R8A8_UNORM,
         WINED3DFMT_B8G8R8X8_UNORM,
@@ -1166,17 +1117,17 @@ IDirect3DDeviceImpl_7_EnumTextureFormats(IDirect3DDevice7 *iface,
         WINED3DFMT_DXT5,
     };
 
-    WINED3DFORMAT BumpFormatList[] = {
+    static const enum wined3d_format_id BumpFormatList[] =
+    {
         WINED3DFMT_R8G8_SNORM,
         WINED3DFMT_R5G5_SNORM_L6_UNORM,
         WINED3DFMT_R8G8_SNORM_L8X8_UNORM,
-        WINED3DFMT_R8G8B8A8_SNORM,
         WINED3DFMT_R16G16_SNORM,
         WINED3DFMT_R10G11B11_SNORM,
         WINED3DFMT_R10G10B10_SNORM_A2_UNORM
     };
 
-    TRACE("(%p)->(%p,%p): Relay\n", This, Callback, Arg);
+    TRACE("iface %p, callback %p, context %p.\n", iface, Callback, Arg);
 
     if(!Callback)
         return DDERR_INVALIDPARAMS;
@@ -1193,7 +1144,7 @@ IDirect3DDeviceImpl_7_EnumTextureFormats(IDirect3DDevice7 *iface,
         return hr;
     }
 
-    for(i = 0; i < sizeof(FormatList) / sizeof(WINED3DFORMAT); i++)
+    for (i = 0; i < sizeof(FormatList) / sizeof(*FormatList); ++i)
     {
         hr = IWineD3D_CheckDeviceFormat(This->ddraw->wineD3D,
                                         WINED3DADAPTER_DEFAULT,
@@ -1222,7 +1173,7 @@ IDirect3DDeviceImpl_7_EnumTextureFormats(IDirect3DDevice7 *iface,
         }
     }
 
-    for(i = 0; i < sizeof(BumpFormatList) / sizeof(WINED3DFORMAT); i++)
+    for (i = 0; i < sizeof(BumpFormatList) / sizeof(*BumpFormatList); ++i)
     {
         hr = IWineD3D_CheckDeviceFormat(This->ddraw->wineD3D,
                                         WINED3DADAPTER_DEFAULT,
@@ -1284,7 +1235,9 @@ Thunk_IDirect3DDeviceImpl_3_EnumTextureFormats(IDirect3DDevice3 *iface,
                                                void *Arg)
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p) thunking to IDirect3DDevice7 interface.\n", This, Callback, Arg);
+
+    TRACE("iface %p, callback %p, context %p.\n", iface, Callback, Arg);
+
     return IDirect3DDevice7_EnumTextureFormats((IDirect3DDevice7 *)This, Callback, Arg);
 }
 
@@ -1308,7 +1261,8 @@ IDirect3DDeviceImpl_2_EnumTextureFormats(IDirect3DDevice2 *iface,
     unsigned int i;
     WINED3DDISPLAYMODE mode;
 
-    WINED3DFORMAT FormatList[] = {
+    static const enum wined3d_format_id FormatList[] =
+    {
         /* 32 bit */
         WINED3DFMT_B8G8R8A8_UNORM,
         WINED3DFMT_B8G8R8X8_UNORM,
@@ -1325,7 +1279,7 @@ IDirect3DDeviceImpl_2_EnumTextureFormats(IDirect3DDevice2 *iface,
         /* FOURCC codes - Not in this version*/
     };
 
-    TRACE("(%p)->(%p,%p): Relay\n", This, Callback, Arg);
+    TRACE("iface %p, callback %p, context %p.\n", iface, Callback, Arg);
 
     if(!Callback)
         return DDERR_INVALIDPARAMS;
@@ -1342,7 +1296,7 @@ IDirect3DDeviceImpl_2_EnumTextureFormats(IDirect3DDevice2 *iface,
         return hr;
     }
 
-    for(i = 0; i < sizeof(FormatList) / sizeof(WINED3DFORMAT); i++)
+    for (i = 0; i < sizeof(FormatList) / sizeof(*FormatList); ++i)
     {
         hr = IWineD3D_CheckDeviceFormat(This->ddraw->wineD3D,
                                         0 /* Adapter */,
@@ -1384,7 +1338,9 @@ Thunk_IDirect3DDeviceImpl_1_EnumTextureFormats(IDirect3DDevice *iface,
                                                void *Arg)
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p) thunking to IDirect3DDevice2 interface.\n", This, Callback, Arg);
+
+    TRACE("iface %p, callback %p, context %p.\n", iface, Callback, Arg);
+
     return IDirect3DDevice2_EnumTextureFormats((IDirect3DDevice2 *)&This->IDirect3DDevice2_vtbl, Callback, Arg);
 }
 
@@ -1409,7 +1365,9 @@ IDirect3DDeviceImpl_1_CreateMatrix(IDirect3DDevice *iface, D3DMATRIXHANDLE *D3DM
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
     D3DMATRIX *Matrix;
-    TRACE("(%p)->(%p)\n", This, D3DMatHandle);
+    DWORD h;
+
+    TRACE("iface %p, matrix_handle %p.\n", iface, D3DMatHandle);
 
     if(!D3DMatHandle)
         return DDERR_INVALIDPARAMS;
@@ -1422,16 +1380,18 @@ IDirect3DDeviceImpl_1_CreateMatrix(IDirect3DDevice *iface, D3DMATRIXHANDLE *D3DM
     }
 
     EnterCriticalSection(&ddraw_cs);
-    *D3DMatHandle = IDirect3DDeviceImpl_CreateHandle(This);
-    if(!(*D3DMatHandle))
+
+    h = ddraw_allocate_handle(&This->handle_table, Matrix, DDRAW_HANDLE_MATRIX);
+    if (h == DDRAW_INVALID_HANDLE)
     {
-        ERR("Failed to create a matrix handle\n");
+        ERR("Failed to allocate a matrix handle.\n");
         HeapFree(GetProcessHeap(), 0, Matrix);
         LeaveCriticalSection(&ddraw_cs);
         return DDERR_OUTOFMEMORY;
     }
-    This->Handles[*D3DMatHandle - 1].ptr = Matrix;
-    This->Handles[*D3DMatHandle - 1].type = DDrawHandle_Matrix;
+
+    *D3DMatHandle = h + 1;
+
     TRACE(" returning matrix handle %d\n", *D3DMatHandle);
 
     LeaveCriticalSection(&ddraw_cs);
@@ -1462,29 +1422,26 @@ IDirect3DDeviceImpl_1_SetMatrix(IDirect3DDevice *iface,
                                 D3DMATRIX *D3DMatrix)
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE("(%p)->(%08x,%p)\n", This, D3DMatHandle, D3DMatrix);
+    D3DMATRIX *m;
 
-    if( (!D3DMatHandle) || (!D3DMatrix) )
-        return DDERR_INVALIDPARAMS;
+    TRACE("iface %p, matrix_handle %#x, matrix %p.\n", iface, D3DMatHandle, D3DMatrix);
+
+    if (!D3DMatrix) return DDERR_INVALIDPARAMS;
 
     EnterCriticalSection(&ddraw_cs);
-    if(D3DMatHandle > This->numHandles)
-    {
-        ERR("Handle %d out of range\n", D3DMatHandle);
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_INVALIDPARAMS;
-    }
-    else if(This->Handles[D3DMatHandle - 1].type != DDrawHandle_Matrix)
+
+    m = ddraw_get_object(&This->handle_table, D3DMatHandle - 1, DDRAW_HANDLE_MATRIX);
+    if (!m)
     {
-        ERR("Handle %d is not a matrix handle\n", D3DMatHandle);
+        WARN("Invalid matrix handle.\n");
         LeaveCriticalSection(&ddraw_cs);
         return DDERR_INVALIDPARAMS;
     }
 
-    if (TRACE_ON(d3d7))
+    if (TRACE_ON(ddraw))
         dump_D3DMATRIX(D3DMatrix);
 
-    *((D3DMATRIX *) This->Handles[D3DMatHandle - 1].ptr) = *D3DMatrix;
+    *m = *D3DMatrix;
 
     if(This->world == D3DMatHandle)
     {
@@ -1510,7 +1467,7 @@ IDirect3DDeviceImpl_1_SetMatrix(IDirect3DDevice *iface,
 }
 
 /*****************************************************************************
- * IDirect3DDevice::SetMatrix
+ * IDirect3DDevice::GetMatrix
  *
  * Returns the content of a D3DMATRIX handle
  *
@@ -1531,29 +1488,23 @@ IDirect3DDeviceImpl_1_GetMatrix(IDirect3DDevice *iface,
                                 D3DMATRIX *D3DMatrix)
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE("(%p)->(%08x,%p)\n", This, D3DMatHandle, D3DMatrix);
+    D3DMATRIX *m;
 
-    if(!D3DMatrix)
-        return DDERR_INVALIDPARAMS;
-    if(!D3DMatHandle)
-        return DDERR_INVALIDPARAMS;
+    TRACE("iface %p, matrix_handle %#x, matrix %p.\n", iface, D3DMatHandle, D3DMatrix);
+
+    if (!D3DMatrix) return DDERR_INVALIDPARAMS;
 
     EnterCriticalSection(&ddraw_cs);
-    if(D3DMatHandle > This->numHandles)
-    {
-        ERR("Handle %d out of range\n", D3DMatHandle);
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_INVALIDPARAMS;
-    }
-    else if(This->Handles[D3DMatHandle - 1].type != DDrawHandle_Matrix)
+
+    m = ddraw_get_object(&This->handle_table, D3DMatHandle - 1, DDRAW_HANDLE_MATRIX);
+    if (!m)
     {
-        ERR("Handle %d is not a matrix handle\n", D3DMatHandle);
+        WARN("Invalid matrix handle.\n");
         LeaveCriticalSection(&ddraw_cs);
         return DDERR_INVALIDPARAMS;
     }
 
-    /* The handle is simply a pointer to a D3DMATRIX structure */
-    *D3DMatrix = *((D3DMATRIX *) This->Handles[D3DMatHandle - 1].ptr);
+    *D3DMatrix = *m;
 
     LeaveCriticalSection(&ddraw_cs);
     return D3D_OK;
@@ -1579,30 +1530,24 @@ IDirect3DDeviceImpl_1_DeleteMatrix(IDirect3DDevice *iface,
                                    D3DMATRIXHANDLE D3DMatHandle)
 {
     IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE("(%p)->(%08x)\n", This, D3DMatHandle);
+    D3DMATRIX *m;
 
-    if(!D3DMatHandle)
-        return DDERR_INVALIDPARAMS;
+    TRACE("iface %p, matrix_handle %#x.\n", iface, D3DMatHandle);
 
     EnterCriticalSection(&ddraw_cs);
-    if(D3DMatHandle > This->numHandles)
-    {
-        ERR("Handle %d out of range\n", D3DMatHandle);
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_INVALIDPARAMS;
-    }
-    else if(This->Handles[D3DMatHandle - 1].type != DDrawHandle_Matrix)
+
+    m = ddraw_free_handle(&This->handle_table, D3DMatHandle - 1, DDRAW_HANDLE_MATRIX);
+    if (!m)
     {
-        ERR("Handle %d is not a matrix handle\n", D3DMatHandle);
+        WARN("Invalid matrix handle.\n");
         LeaveCriticalSection(&ddraw_cs);
         return DDERR_INVALIDPARAMS;
     }
 
-    HeapFree(GetProcessHeap(), 0, This->Handles[D3DMatHandle - 1].ptr);
-    This->Handles[D3DMatHandle - 1].ptr = NULL;
-    This->Handles[D3DMatHandle - 1].type = DDrawHandle_Unknown;
-
     LeaveCriticalSection(&ddraw_cs);
+
+    HeapFree(GetProcessHeap(), 0, m);
+
     return D3D_OK;
 }
 
@@ -1625,7 +1570,8 @@ IDirect3DDeviceImpl_7_BeginScene(IDirect3DDevice7 *iface)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p): Relay\n", This);
+
+    TRACE("iface %p.\n", iface);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DDevice_BeginScene(This->wineD3DDevice);
@@ -1656,25 +1602,25 @@ IDirect3DDeviceImpl_7_BeginScene_FPUPreserve(IDirect3DDevice7 *iface)
 static HRESULT WINAPI
 Thunk_IDirect3DDeviceImpl_3_BeginScene(IDirect3DDevice3 *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_BeginScene((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_BeginScene((IDirect3DDevice7 *)device_from_device3(iface));
 }
 
 static HRESULT WINAPI
 Thunk_IDirect3DDeviceImpl_2_BeginScene(IDirect3DDevice2 *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_BeginScene((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_BeginScene((IDirect3DDevice7 *)device_from_device2(iface));
 }
 
 static HRESULT WINAPI
 Thunk_IDirect3DDeviceImpl_1_BeginScene(IDirect3DDevice *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_BeginScene((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_BeginScene((IDirect3DDevice7 *)device_from_device1(iface));
 }
 
 /*****************************************************************************
@@ -1696,7 +1642,8 @@ IDirect3DDeviceImpl_7_EndScene(IDirect3DDevice7 *iface)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p): Relay\n", This);
+
+    TRACE("iface %p.\n", iface);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DDevice_EndScene(This->wineD3DDevice);
@@ -1727,25 +1674,25 @@ IDirect3DDeviceImpl_7_EndScene_FPUPreserve(IDirect3DDevice7 *iface)
 static HRESULT WINAPI DECLSPEC_HOTPATCH
 Thunk_IDirect3DDeviceImpl_3_EndScene(IDirect3DDevice3 *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_EndScene((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_EndScene((IDirect3DDevice7 *)device_from_device3(iface));
 }
 
 static HRESULT WINAPI DECLSPEC_HOTPATCH
 Thunk_IDirect3DDeviceImpl_2_EndScene(IDirect3DDevice2 *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_EndScene((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_EndScene((IDirect3DDevice7 *)device_from_device2(iface));
 }
 
 static HRESULT WINAPI DECLSPEC_HOTPATCH
 Thunk_IDirect3DDeviceImpl_1_EndScene(IDirect3DDevice *iface)
 {
-    IDirect3DDeviceImpl *This = device_from_device1(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DDevice7 interface.\n", This);
-    return IDirect3DDevice7_EndScene((IDirect3DDevice7 *)This);
+    TRACE("iface %p.\n", iface);
+
+    return IDirect3DDevice7_EndScene((IDirect3DDevice7 *)device_from_device1(iface));
 }
 
 /*****************************************************************************
@@ -1767,7 +1714,8 @@ IDirect3DDeviceImpl_7_GetDirect3D(IDirect3DDevice7 *iface,
                                   IDirect3D7 **Direct3D7)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
-    TRACE("(%p)->(%p)\n", This, Direct3D7);
+
+    TRACE("iface %p, d3d %p.\n", iface, Direct3D7);
 
     if(!Direct3D7)
         return DDERR_INVALIDPARAMS;
@@ -1787,7 +1735,8 @@ Thunk_IDirect3DDeviceImpl_3_GetDirect3D(IDirect3DDevice3 *iface,
     HRESULT ret;
     IDirect3D7 *ret_ptr;
 
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, Direct3D3);
+    TRACE("iface %p, d3d %p.\n", iface, Direct3D3);
+
     ret = IDirect3DDevice7_GetDirect3D((IDirect3DDevice7 *)This, &ret_ptr);
     if(ret != D3D_OK)
         return ret;
@@ -1804,7 +1753,8 @@ Thunk_IDirect3DDeviceImpl_2_GetDirect3D(IDirect3DDevice2 *iface,
     HRESULT ret;
     IDirect3D7 *ret_ptr;
 
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, Direct3D2);
+    TRACE("iface %p, d3d %p.\n", iface, Direct3D2);
+
     ret = IDirect3DDevice7_GetDirect3D((IDirect3DDevice7 *)This, &ret_ptr);
     if(ret != D3D_OK)
         return ret;
@@ -1821,7 +1771,8 @@ Thunk_IDirect3DDeviceImpl_1_GetDirect3D(IDirect3DDevice *iface,
     HRESULT ret;
     IDirect3D7 *ret_ptr;
 
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, Direct3D);
+    TRACE("iface %p, d3d %p.\n", iface, Direct3D);
+
     ret = IDirect3DDevice7_GetDirect3D((IDirect3DDevice7 *)This, &ret_ptr);
     if(ret != D3D_OK)
         return ret;
@@ -1852,7 +1803,8 @@ IDirect3DDeviceImpl_3_SetCurrentViewport(IDirect3DDevice3 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Direct3DViewport3;
-    TRACE("(%p)->(%p)\n", This, Direct3DViewport3);
+
+    TRACE("iface %p, viewport %p.\n", iface, Direct3DViewport3);
 
     EnterCriticalSection(&ddraw_cs);
     /* Do nothing if the specified viewport is the same as the current one */
@@ -1878,7 +1830,7 @@ IDirect3DDeviceImpl_3_SetCurrentViewport(IDirect3DDevice3 *iface,
 
     /* Activate this viewport */
     This->current_viewport->active_device = This;
-    This->current_viewport->activate(This->current_viewport, FALSE);
+    viewport_activate(This->current_viewport, FALSE);
 
     LeaveCriticalSection(&ddraw_cs);
     return D3D_OK;
@@ -1890,7 +1842,9 @@ Thunk_IDirect3DDeviceImpl_2_SetCurrentViewport(IDirect3DDevice2 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
     IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)Direct3DViewport2;
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice3 interface.\n", This, vp);
+
+    TRACE("iface %p, viewport %p.\n", iface, Direct3DViewport2);
+
     return IDirect3DDevice3_SetCurrentViewport((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl,
             (IDirect3DViewport3 *)vp);
 }
@@ -1915,7 +1869,8 @@ IDirect3DDeviceImpl_3_GetCurrentViewport(IDirect3DDevice3 *iface,
                                          IDirect3DViewport3 **Direct3DViewport3)
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE("(%p)->(%p)\n", This, Direct3DViewport3);
+
+    TRACE("iface %p, viewport %p.\n", iface, Direct3DViewport3);
 
     if(!Direct3DViewport3)
         return DDERR_INVALIDPARAMS;
@@ -1938,7 +1893,9 @@ Thunk_IDirect3DDeviceImpl_2_GetCurrentViewport(IDirect3DDevice2 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
     HRESULT hr;
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice3 interface.\n", This, Direct3DViewport2);
+
+    TRACE("iface %p, viewport %p.\n", iface, Direct3DViewport2);
+
     hr = IDirect3DDevice3_GetCurrentViewport((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl,
             (IDirect3DViewport3 **)Direct3DViewport2);
     if(hr != D3D_OK) return hr;
@@ -1971,7 +1928,8 @@ IDirect3DDeviceImpl_7_SetRenderTarget(IDirect3DDevice7 *iface,
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     IDirectDrawSurfaceImpl *Target = (IDirectDrawSurfaceImpl *)NewTarget;
     HRESULT hr;
-    TRACE("(%p)->(%p,%08x): Relay\n", This, NewTarget, Flags);
+
+    TRACE("iface %p, target %p, flags %#x.\n", iface, NewTarget, Flags);
 
     EnterCriticalSection(&ddraw_cs);
     /* Flags: Not used */
@@ -2030,7 +1988,9 @@ Thunk_IDirect3DDeviceImpl_3_SetRenderTarget(IDirect3DDevice3 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
     IDirectDrawSurfaceImpl *Target = (IDirectDrawSurfaceImpl *)NewRenderTarget;
-    TRACE_(ddraw_thunk)("(%p)->(%p,%08x) thunking to IDirect3DDevice7 interface.\n", This, Target, Flags);
+
+    TRACE("iface %p, target %p, flags %#x.\n", iface, NewRenderTarget, Flags);
+
     return IDirect3DDevice7_SetRenderTarget((IDirect3DDevice7 *)This, (IDirectDrawSurface7 *)Target, Flags);
 }
 
@@ -2041,7 +2001,9 @@ Thunk_IDirect3DDeviceImpl_2_SetRenderTarget(IDirect3DDevice2 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
     IDirectDrawSurfaceImpl *Target = (IDirectDrawSurfaceImpl *)NewRenderTarget;
-    TRACE_(ddraw_thunk)("(%p)->(%p,%08x) thunking to IDirect3DDevice7 interface.\n", This, Target, Flags);
+
+    TRACE("iface %p, target %p, flags %#x.\n", iface, NewRenderTarget, Flags);
+
     return IDirect3DDevice7_SetRenderTarget((IDirect3DDevice7 *)This, (IDirectDrawSurface7 *)Target, Flags);
 }
 
@@ -2067,7 +2029,8 @@ IDirect3DDeviceImpl_7_GetRenderTarget(IDirect3DDevice7 *iface,
                                       IDirectDrawSurface7 **RenderTarget)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
-    TRACE("(%p)->(%p): Relay\n", This, RenderTarget);
+
+    TRACE("iface %p, target %p.\n", iface, RenderTarget);
 
     if(!RenderTarget)
         return DDERR_INVALIDPARAMS;
@@ -2086,7 +2049,9 @@ Thunk_IDirect3DDeviceImpl_3_GetRenderTarget(IDirect3DDevice3 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
     HRESULT hr;
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, RenderTarget);
+
+    TRACE("iface %p, target %p.\n", iface, RenderTarget);
+
     hr = IDirect3DDevice7_GetRenderTarget((IDirect3DDevice7 *)This, (IDirectDrawSurface7 **)RenderTarget);
     if(hr != D3D_OK) return hr;
     return D3D_OK;
@@ -2098,7 +2063,9 @@ Thunk_IDirect3DDeviceImpl_2_GetRenderTarget(IDirect3DDevice2 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
     HRESULT hr;
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, RenderTarget);
+
+    TRACE("iface %p, target %p.\n", iface, RenderTarget);
+
     hr = IDirect3DDevice7_GetRenderTarget((IDirect3DDevice7 *)This, (IDirectDrawSurface7 **)RenderTarget);
     if(hr != D3D_OK) return hr;
     *RenderTarget = *RenderTarget ?
@@ -2131,7 +2098,9 @@ IDirect3DDeviceImpl_3_Begin(IDirect3DDevice3 *iface,
                             DWORD Flags)
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE("(%p)->(%d,%d,%08x)\n", This, PrimitiveType, VertexTypeDesc, Flags);
+
+    TRACE("iface %p, primitive_type %#x, FVF %#x, flags %#x.\n",
+            iface, PrimitiveType, VertexTypeDesc, Flags);
 
     EnterCriticalSection(&ddraw_cs);
     This->primitive_type = PrimitiveType;
@@ -2152,7 +2121,9 @@ Thunk_IDirect3DDeviceImpl_2_Begin(IDirect3DDevice2 *iface,
 {
     DWORD FVF;
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p/%p)->(%08x,%08x,%08x): Thunking to IDirect3DDevice3\n", This, iface, d3dpt, dwVertexTypeDesc, dwFlags);
+
+    TRACE("iface %p, primitive_type %#x, vertex_type %#x, flags %#x.\n",
+            iface, d3dpt, dwVertexTypeDesc, dwFlags);
 
     switch(dwVertexTypeDesc)
     {
@@ -2194,8 +2165,9 @@ IDirect3DDeviceImpl_3_BeginIndexed(IDirect3DDevice3 *iface,
                                    DWORD NumVertices,
                                    DWORD Flags)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    FIXME("(%p)->(%08x,%08x,%p,%08x,%08x): stub!\n", This, PrimitiveType, VertexType, Vertices, NumVertices, Flags);
+    FIXME("iface %p, primitive_type %#x, FVF %#x, vertices %p, vertex_count %u, flags %#x stub!\n",
+            iface, PrimitiveType, VertexType, Vertices, NumVertices, Flags);
+
     return D3D_OK;
 }
 
@@ -2210,7 +2182,9 @@ Thunk_IDirect3DDeviceImpl_2_BeginIndexed(IDirect3DDevice2 *iface,
 {
     DWORD FVF;
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p/%p)->(%08x,%08x,%p,%08x,%08x): Thunking to IDirect3DDevice3\n", This, iface, d3dptPrimitiveType, d3dvtVertexType, lpvVertices, dwNumVertices, dwFlags);
+
+    TRACE("iface %p, primitive_type %#x, vertex_type %#x, vertices %p, vertex_count %u, flags %#x stub!\n",
+            iface, d3dptPrimitiveType, d3dvtVertexType, lpvVertices, dwNumVertices, dwFlags);
 
     switch(d3dvtVertexType)
     {
@@ -2248,7 +2222,8 @@ IDirect3DDeviceImpl_3_Vertex(IDirect3DDevice3 *iface,
                              void *Vertex)
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE("(%p)->(%p)\n", This, Vertex);
+
+    TRACE("iface %p, vertex %p.\n", iface, Vertex);
 
     if(!Vertex)
         return DDERR_INVALIDPARAMS;
@@ -2278,7 +2253,9 @@ Thunk_IDirect3DDeviceImpl_2_Vertex(IDirect3DDevice2 *iface,
                                    void *lpVertexType)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice3 interface.\n", This, lpVertexType);
+
+    TRACE("iface %p, vertex %p.\n", iface, lpVertexType);
+
     return IDirect3DDevice3_Vertex((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, lpVertexType);
 }
 
@@ -2299,8 +2276,8 @@ static HRESULT WINAPI
 IDirect3DDeviceImpl_3_Index(IDirect3DDevice3 *iface,
                             WORD VertexIndex)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    FIXME("(%p)->(%04x): stub!\n", This, VertexIndex);
+    FIXME("iface %p, index %#x stub!\n", iface, VertexIndex);
+
     return D3D_OK;
 }
 
@@ -2309,7 +2286,9 @@ Thunk_IDirect3DDeviceImpl_2_Index(IDirect3DDevice2 *iface,
                                   WORD wVertexIndex)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%04x) thunking to IDirect3DDevice3 interface.\n", This, wVertexIndex);
+
+    TRACE("iface %p, index %#x.\n", iface, wVertexIndex);
+
     return IDirect3DDevice3_Index((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, wVertexIndex);
 }
 
@@ -2336,7 +2315,8 @@ IDirect3DDeviceImpl_3_End(IDirect3DDevice3 *iface,
                           DWORD Flags)
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE("(%p)->(%08x)\n", This, Flags);
+
+    TRACE("iface %p, flags %#x.\n", iface, Flags);
 
     return IDirect3DDevice7_DrawPrimitive((IDirect3DDevice7 *)This, This->primitive_type,
             This->vertex_type, This->vertex_buffer, This->nb_vertices, This->render_flags);
@@ -2347,7 +2327,9 @@ Thunk_IDirect3DDeviceImpl_2_End(IDirect3DDevice2 *iface,
                                 DWORD dwFlags)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x) thunking to IDirect3DDevice3 interface.\n", This, dwFlags);
+
+    TRACE("iface %p, flags %#x.\n", iface, dwFlags);
+
     return IDirect3DDevice3_End((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, dwFlags);
 }
 
@@ -2375,7 +2357,8 @@ IDirect3DDeviceImpl_7_GetRenderState(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p): Relay\n", This, RenderStateType, Value);
+
+    TRACE("iface %p, state %#x, value %p.\n", iface, RenderStateType, Value);
 
     if(!Value)
         return DDERR_INVALIDPARAMS;
@@ -2484,6 +2467,12 @@ IDirect3DDeviceImpl_7_GetRenderState(IDirect3DDevice7 *iface,
             hr = E_NOTIMPL;
             break;
 
+        case D3DRENDERSTATE_TEXTUREHANDLE:
+        case D3DRENDERSTATE_TEXTUREMAPBLEND:
+            WARN("Render state %#x is invalid in d3d7.\n", RenderStateType);
+            hr = DDERR_INVALIDPARAMS;
+            break;
+
         default:
             if (RenderStateType >= D3DRENDERSTATE_STIPPLEPATTERN00
                     && RenderStateType <= D3DRENDERSTATE_STIPPLEPATTERN31)
@@ -2531,7 +2520,8 @@ IDirect3DDeviceImpl_3_GetRenderState(IDirect3DDevice3 *iface,
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p)\n", This, dwRenderStateType, lpdwRenderState);
+
+    TRACE("iface %p, state %#x, value %p.\n", iface, dwRenderStateType, lpdwRenderState);
 
     switch(dwRenderStateType)
     {
@@ -2545,24 +2535,13 @@ IDirect3DDeviceImpl_3_GetRenderState(IDirect3DDevice3 *iface,
 
             EnterCriticalSection(&ddraw_cs);
 
-            hr = IWineD3DDevice_GetTexture(This->wineD3DDevice,
-                                           0,
-                                           &tex);
-
-            if(hr == WINED3D_OK && tex)
+            hr = IWineD3DDevice_GetTexture(This->wineD3DDevice, 0, &tex);
+            if (SUCCEEDED(hr) && tex)
             {
-                IDirectDrawSurface7 *parent = NULL;
-                hr = IWineD3DBaseTexture_GetParent(tex,
-                                                   (IUnknown **) &parent);
-                if(parent)
-                {
-                    /* The parent of the texture is the IDirectDrawSurface7 interface
-                     * of the ddraw surface
-                     */
-                    IDirectDrawSurfaceImpl *texImpl = (IDirectDrawSurfaceImpl *)parent;
-                    *lpdwRenderState = texImpl->Handle;
-                    IDirectDrawSurface7_Release(parent);
-                }
+                /* The parent of the texture is the IDirectDrawSurface7
+                 * interface of the ddraw surface. */
+                IDirectDrawSurfaceImpl *parent = IWineD3DBaseTexture_GetParent(tex);
+                if (parent) *lpdwRenderState = parent->Handle;
                 IWineD3DBaseTexture_Release(tex);
             }
 
@@ -2655,7 +2634,9 @@ Thunk_IDirect3DDeviceImpl_2_GetRenderState(IDirect3DDevice2 *iface,
                                            DWORD *lpdwRenderState)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p) thunking to IDirect3DDevice3 interface.\n", This, dwRenderStateType, lpdwRenderState);
+
+    TRACE("iface %p, state %#x, value %p.\n", iface, dwRenderStateType, lpdwRenderState);
+
     return IDirect3DDevice3_GetRenderState((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl,
             dwRenderStateType, lpdwRenderState);
 }
@@ -2684,7 +2665,8 @@ IDirect3DDeviceImpl_7_SetRenderState(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%d): Relay\n", This, RenderStateType, Value);
+
+    TRACE("iface %p, state %#x, value %#x.\n", iface, RenderStateType, Value);
 
     EnterCriticalSection(&ddraw_cs);
     /* Some render states need special care */
@@ -2801,6 +2783,12 @@ IDirect3DDeviceImpl_7_SetRenderState(IDirect3DDevice7 *iface,
             hr = E_NOTIMPL;
             break;
 
+        case D3DRENDERSTATE_TEXTUREHANDLE:
+        case D3DRENDERSTATE_TEXTUREMAPBLEND:
+            WARN("Render state %#x is invalid in d3d7.\n", RenderStateType);
+            hr = DDERR_INVALIDPARAMS;
+            break;
+
         default:
             if (RenderStateType >= D3DRENDERSTATE_STIPPLEPATTERN00
                     && RenderStateType <= D3DRENDERSTATE_STIPPLEPATTERN31)
@@ -2869,7 +2857,8 @@ IDirect3DDeviceImpl_3_SetRenderState(IDirect3DDevice3 *iface,
 
     HRESULT hr;
     IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE("(%p)->(%08x,%d)\n", This, RenderStateType, Value);
+
+    TRACE("iface %p, state %#x, value %#x.\n", iface, RenderStateType, Value);
 
     EnterCriticalSection(&ddraw_cs);
 
@@ -2877,6 +2866,8 @@ IDirect3DDeviceImpl_3_SetRenderState(IDirect3DDevice3 *iface,
     {
         case D3DRENDERSTATE_TEXTUREHANDLE:
         {
+            IDirectDrawSurfaceImpl *surf;
+
             if(Value == 0)
             {
                 hr = IWineD3DDevice_SetTexture(This->wineD3DDevice,
@@ -2885,25 +2876,16 @@ IDirect3DDeviceImpl_3_SetRenderState(IDirect3DDevice3 *iface,
                 break;
             }
 
-            if(Value > This->numHandles)
+            surf = ddraw_get_object(&This->handle_table, Value - 1, DDRAW_HANDLE_SURFACE);
+            if (!surf)
             {
-                FIXME("Specified handle %d out of range\n", Value);
+                WARN("Invalid texture handle.\n");
                 hr = DDERR_INVALIDPARAMS;
                 break;
             }
-            if(This->Handles[Value - 1].type != DDrawHandle_Texture)
-            {
-                FIXME("Handle %d isn't a texture handle\n", Value);
-                hr = DDERR_INVALIDPARAMS;
-                break;
-            }
-            else
-            {
-                IDirectDrawSurfaceImpl *surf = This->Handles[Value - 1].ptr;
-                IDirect3DTexture2 *tex = surf ? (IDirect3DTexture2 *)&surf->IDirect3DTexture2_vtbl : NULL;
-                hr = IDirect3DDevice3_SetTexture(iface, 0, tex);
-                break;
-            }
+
+            hr = IDirect3DDevice3_SetTexture(iface, 0, (IDirect3DTexture2 *)&surf->IDirect3DTexture2_vtbl);
+            break;
         }
 
         case D3DRENDERSTATE_TEXTUREMAPBLEND:
@@ -3007,7 +2989,9 @@ Thunk_IDirect3DDeviceImpl_2_SetRenderState(IDirect3DDevice2 *iface,
                                            DWORD Value)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%d) thunking to IDirect3DDevice3 interface.\n", This, RenderStateType, Value);
+
+    TRACE("iface %p, state %#x, value %#x.\n", iface, RenderStateType, Value);
+
     return IDirect3DDevice3_SetRenderState((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, RenderStateType, Value);
 }
 
@@ -3037,7 +3021,7 @@ IDirect3DDeviceImpl_3_SetLightState(IDirect3DDevice3 *iface,
     IDirect3DDeviceImpl *This = device_from_device3(iface);
     HRESULT hr;
 
-    TRACE("(%p)->(%08x,%08x)\n", This, LightStateType, Value);
+    TRACE("iface %p, state %#x, value %#x.\n", iface, LightStateType, Value);
 
     if (!LightStateType || (LightStateType > D3DLIGHTSTATE_COLORVERTEX))
     {
@@ -3048,35 +3032,17 @@ IDirect3DDeviceImpl_3_SetLightState(IDirect3DDevice3 *iface,
     EnterCriticalSection(&ddraw_cs);
     if (LightStateType == D3DLIGHTSTATE_MATERIAL /* 1 */)
     {
-        IDirect3DMaterialImpl *mat;
-
-        if(Value == 0) mat = NULL;
-        else if(Value > This->numHandles)
+        IDirect3DMaterialImpl *m = ddraw_get_object(&This->handle_table, Value - 1, DDRAW_HANDLE_MATERIAL);
+        if (!m)
         {
-            ERR("Material handle out of range(%d)\n", Value);
+            WARN("Invalid material handle.\n");
             LeaveCriticalSection(&ddraw_cs);
             return DDERR_INVALIDPARAMS;
         }
-        else if(This->Handles[Value - 1].type != DDrawHandle_Material)
-        {
-            ERR("Invalid handle %d\n", Value);
-            LeaveCriticalSection(&ddraw_cs);
-            return DDERR_INVALIDPARAMS;
-        }
-        else
-        {
-            mat = This->Handles[Value - 1].ptr;
-        }
 
-        if (mat != NULL)
-        {
-            TRACE(" activating material %p.\n", mat);
-            mat->activate(mat);
-        }
-        else
-        {
-            FIXME(" D3DLIGHTSTATE_MATERIAL called with NULL material !!!\n");
-        }
+        TRACE(" activating material %p.\n", m);
+        material_activate(m);
+
         This->material = Value;
     }
     else if (LightStateType == D3DLIGHTSTATE_COLORMODEL /* 3 */)
@@ -3103,7 +3069,7 @@ IDirect3DDeviceImpl_3_SetLightState(IDirect3DDevice3 *iface,
         {
             case D3DLIGHTSTATE_AMBIENT:       /* 2 */
                 rs = D3DRENDERSTATE_AMBIENT;
-                break;         
+                break;
             case D3DLIGHTSTATE_FOGMODE:       /* 4 */
                 rs = D3DRENDERSTATE_FOGVERTEXMODE;
                 break;
@@ -3140,7 +3106,9 @@ Thunk_IDirect3DDeviceImpl_2_SetLightState(IDirect3DDevice2 *iface,
                                           DWORD Value)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x) thunking to IDirect3DDevice3 interface.\n", This, LightStateType, Value);
+
+    TRACE("iface %p, state %#x, value %#x.\n", iface, LightStateType, Value);
+
     return IDirect3DDevice3_SetLightState((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, LightStateType, Value);
 }
 
@@ -3170,7 +3138,7 @@ IDirect3DDeviceImpl_3_GetLightState(IDirect3DDevice3 *iface,
     IDirect3DDeviceImpl *This = device_from_device3(iface);
     HRESULT hr;
 
-    TRACE("(%p)->(%08x,%p)\n", This, LightStateType, Value);
+    TRACE("iface %p, state %#x, value %p.\n", iface, LightStateType, Value);
 
     if (!LightStateType || (LightStateType > D3DLIGHTSTATE_COLORVERTEX))
     {
@@ -3197,7 +3165,7 @@ IDirect3DDeviceImpl_3_GetLightState(IDirect3DDevice3 *iface,
         {
             case D3DLIGHTSTATE_AMBIENT:       /* 2 */
                 rs = D3DRENDERSTATE_AMBIENT;
-                break;         
+                break;
             case D3DLIGHTSTATE_FOGMODE:       /* 4 */
                 rs = D3DRENDERSTATE_FOGVERTEXMODE;
                 break;
@@ -3234,7 +3202,9 @@ Thunk_IDirect3DDeviceImpl_2_GetLightState(IDirect3DDevice2 *iface,
                                           DWORD *Value)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p) thunking to IDirect3DDevice3 interface.\n", This, LightStateType, Value);
+
+    TRACE("iface %p, state %#x, value %p.\n", iface, LightStateType, Value);
+
     return IDirect3DDevice3_GetLightState((IDirect3DDevice3 *)&This->IDirect3DDevice3_vtbl, LightStateType, Value);
 }
 
@@ -3267,7 +3237,8 @@ IDirect3DDeviceImpl_7_SetTransform(IDirect3DDevice7 *iface,
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     D3DTRANSFORMSTATETYPE type;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p): Relay\n", This, TransformStateType, Matrix);
+
+    TRACE("iface %p, state %#x, matrix %p.\n", iface, TransformStateType, Matrix);
 
     switch(TransformStateType)
     {
@@ -3319,7 +3290,9 @@ Thunk_IDirect3DDeviceImpl_3_SetTransform(IDirect3DDevice3 *iface,
                                          D3DMATRIX *D3DMatrix)
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p) thunking to IDirect3DDevice7 interface.\n", This, TransformStateType, D3DMatrix);
+
+    TRACE("iface %p, state %#x, matrix %p.\n", iface, TransformStateType, D3DMatrix);
+
     return IDirect3DDevice7_SetTransform((IDirect3DDevice7 *)This, TransformStateType, D3DMatrix);
 }
 
@@ -3329,7 +3302,9 @@ Thunk_IDirect3DDeviceImpl_2_SetTransform(IDirect3DDevice2 *iface,
                                          D3DMATRIX *D3DMatrix)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p) thunking to IDirect3DDevice7 interface.\n", This, TransformStateType, D3DMatrix);
+
+    TRACE("iface %p, state %#x, matrix %p.\n", iface, TransformStateType, D3DMatrix);
+
     return IDirect3DDevice7_SetTransform((IDirect3DDevice7 *)This, TransformStateType, D3DMatrix);
 }
 
@@ -3358,7 +3333,8 @@ IDirect3DDeviceImpl_7_GetTransform(IDirect3DDevice7 *iface,
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     D3DTRANSFORMSTATETYPE type;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p): Relay\n", This, TransformStateType, Matrix);
+
+    TRACE("iface %p, state %#x, matrix %p.\n", iface, TransformStateType, Matrix);
 
     switch(TransformStateType)
     {
@@ -3408,7 +3384,9 @@ Thunk_IDirect3DDeviceImpl_3_GetTransform(IDirect3DDevice3 *iface,
                                          D3DMATRIX *D3DMatrix)
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p) thunking to IDirect3DDevice7 interface.\n", This, TransformStateType, D3DMatrix);
+
+    TRACE("iface %p, state %#x, matrix %p.\n", iface, TransformStateType, D3DMatrix);
+
     return IDirect3DDevice7_GetTransform((IDirect3DDevice7 *)This, TransformStateType, D3DMatrix);
 }
 
@@ -3418,7 +3396,9 @@ Thunk_IDirect3DDeviceImpl_2_GetTransform(IDirect3DDevice2 *iface,
                                          D3DMATRIX *D3DMatrix)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p) thunking to IDirect3DDevice7 interface.\n", This, TransformStateType, D3DMatrix);
+
+    TRACE("iface %p, state %#x, matrix %p.\n", iface, TransformStateType, D3DMatrix);
+
     return IDirect3DDevice7_GetTransform((IDirect3DDevice7 *)This, TransformStateType, D3DMatrix);
 }
 
@@ -3448,7 +3428,8 @@ IDirect3DDeviceImpl_7_MultiplyTransform(IDirect3DDevice7 *iface,
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
     D3DTRANSFORMSTATETYPE type;
-    TRACE("(%p)->(%08x,%p): Relay\n", This, TransformStateType, D3DMatrix);
+
+    TRACE("iface %p, state %#x, matrix %p.\n", iface, TransformStateType, D3DMatrix);
 
     switch(TransformStateType)
     {
@@ -3497,7 +3478,9 @@ Thunk_IDirect3DDeviceImpl_3_MultiplyTransform(IDirect3DDevice3 *iface,
                                               D3DMATRIX *D3DMatrix)
 {
     IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p) thunking to IDirect3DDevice7 interface.\n", This, TransformStateType, D3DMatrix);
+
+    TRACE("iface %p, state %#x, matrix %p.\n", iface, TransformStateType, D3DMatrix);
+
     return IDirect3DDevice7_MultiplyTransform((IDirect3DDevice7 *)This, TransformStateType, D3DMatrix);
 }
 
@@ -3507,7 +3490,9 @@ Thunk_IDirect3DDeviceImpl_2_MultiplyTransform(IDirect3DDevice2 *iface,
                                               D3DMATRIX *D3DMatrix)
 {
     IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p) thunking to IDirect3DDevice7 interface.\n", This, TransformStateType, D3DMatrix);
+
+    TRACE("iface %p, state %#x, matrix %p.\n", iface, TransformStateType, D3DMatrix);
+
     return IDirect3DDevice7_MultiplyTransform((IDirect3DDevice7 *)This, TransformStateType, D3DMatrix);
 }
 
@@ -3543,7 +3528,9 @@ IDirect3DDeviceImpl_7_DrawPrimitive(IDirect3DDevice7 *iface,
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     UINT stride;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%08x,%p,%08x,%08x): Relay!\n", This, PrimitiveType, VertexType, Vertices, VertexCount, Flags);
+
+    TRACE("iface %p, primitive_type %#x, FVF %#x, vertices %p, vertex_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, Vertices, VertexCount, Flags);
 
     if(!Vertices)
         return DDERR_INVALIDPARAMS;
@@ -3553,8 +3540,7 @@ IDirect3DDeviceImpl_7_DrawPrimitive(IDirect3DDevice7 *iface,
 
     /* Set the FVF */
     EnterCriticalSection(&ddraw_cs);
-    hr = IWineD3DDevice_SetVertexDeclaration(This->wineD3DDevice,
-                                             IDirectDrawImpl_FindDecl(This->ddraw, VertexType));
+    hr = IWineD3DDevice_SetVertexDeclaration(This->wineD3DDevice, ddraw_find_decl(This->ddraw, VertexType));
     if(hr != D3D_OK)
     {
         LeaveCriticalSection(&ddraw_cs);
@@ -3605,9 +3591,10 @@ Thunk_IDirect3DDeviceImpl_3_DrawPrimitive(IDirect3DDevice3 *iface,
                                           DWORD VertexCount,
                                           DWORD Flags)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x,%p,%08x,%08x) thunking to IDirect3DDevice7 interface.\n", This, PrimitiveType, VertexType, Vertices, VertexCount, Flags);
-    return IDirect3DDevice7_DrawPrimitive((IDirect3DDevice7 *)This,
+    TRACE("iface %p, primitive_type %#x, FVF %#x, vertices %p, vertex_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, Vertices, VertexCount, Flags);
+
+    return IDirect3DDevice7_DrawPrimitive((IDirect3DDevice7 *)device_from_device3(iface),
             PrimitiveType, VertexType, Vertices, VertexCount, Flags);
 }
 
@@ -3619,9 +3606,10 @@ Thunk_IDirect3DDeviceImpl_2_DrawPrimitive(IDirect3DDevice2 *iface,
                                           DWORD VertexCount,
                                           DWORD Flags)
 {
-    IDirect3DDeviceImpl *This = device_from_device2(iface);
     DWORD FVF;
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x,%p,%08x,%08x) thunking to IDirect3DDevice7 interface.\n", This, PrimitiveType, VertexType, Vertices, VertexCount, Flags);
+
+    TRACE("iface %p, primitive_type %#x, vertex_type %#x, vertices %p, vertex_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, Vertices, VertexCount, Flags);
 
     switch(VertexType)
     {
@@ -3633,7 +3621,8 @@ Thunk_IDirect3DDeviceImpl_2_DrawPrimitive(IDirect3DDevice2 *iface,
             return DDERR_INVALIDPARAMS;  /* Should never happen */
     }
 
-    return IDirect3DDevice7_DrawPrimitive((IDirect3DDevice7 *)This, PrimitiveType, FVF, Vertices, VertexCount, Flags);
+    return IDirect3DDevice7_DrawPrimitive((IDirect3DDevice7 *)device_from_device2(iface),
+            PrimitiveType, FVF, Vertices, VertexCount, Flags);
 }
 
 /*****************************************************************************
@@ -3672,12 +3661,13 @@ IDirect3DDeviceImpl_7_DrawIndexedPrimitive(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%08x,%p,%08x,%p,%08x,%08x): Relay!\n", This, PrimitiveType, VertexType, Vertices, VertexCount, Indices, IndexCount, Flags);
+
+    TRACE("iface %p, primitive_type %#x, FVF %#x, vertices %p, vertex_count %u, indices %p, index_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, Vertices, VertexCount, Indices, IndexCount, Flags);
 
     /* Set the D3DDevice's FVF */
     EnterCriticalSection(&ddraw_cs);
-    hr = IWineD3DDevice_SetVertexDeclaration(This->wineD3DDevice,
-                                             IDirectDrawImpl_FindDecl(This->ddraw, VertexType));
+    hr = IWineD3DDevice_SetVertexDeclaration(This->wineD3DDevice, ddraw_find_decl(This->ddraw, VertexType));
     if(FAILED(hr))
     {
         ERR(" (%p) Setting the FVF failed, hr = %x!\n", This, hr);
@@ -3735,9 +3725,10 @@ Thunk_IDirect3DDeviceImpl_3_DrawIndexedPrimitive(IDirect3DDevice3 *iface,
                                                  DWORD IndexCount,
                                                  DWORD Flags)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x,%p,%08x,%p,%08x,%08x) thunking to IDirect3DDevice7 interface.\n", This, PrimitiveType, VertexType, Vertices, VertexCount, Indices, IndexCount, Flags);
-    return IDirect3DDevice7_DrawIndexedPrimitive((IDirect3DDevice7 *)This,
+    TRACE("iface %p, primitive_type %#x, FVF %#x, vertices %p, vertex_count %u, indices %p, index_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, Vertices, VertexCount, Indices, IndexCount, Flags);
+
+    return IDirect3DDevice7_DrawIndexedPrimitive((IDirect3DDevice7 *)device_from_device3(iface),
             PrimitiveType, VertexType, Vertices, VertexCount, Indices, IndexCount, Flags);
 }
 
@@ -3752,8 +3743,9 @@ Thunk_IDirect3DDeviceImpl_2_DrawIndexedPrimitive(IDirect3DDevice2 *iface,
                                                  DWORD Flags)
 {
     DWORD FVF;
-    IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x,%p,%08x,%p,%08x,%08x) thunking to IDirect3DDevice7 interface.\n", This, PrimitiveType, VertexType, Vertices, VertexCount, Indices, IndexCount, Flags);
+
+    TRACE("iface %p, primitive_type %#x, vertex_type %#x, vertices %p, vertex_count %u, indices %p, index_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, Vertices, VertexCount, Indices, IndexCount, Flags);
 
     switch(VertexType)
     {
@@ -3765,7 +3757,7 @@ Thunk_IDirect3DDeviceImpl_2_DrawIndexedPrimitive(IDirect3DDevice2 *iface,
             return DDERR_INVALIDPARAMS;  /* Should never happen */
     }
 
-    return IDirect3DDevice7_DrawIndexedPrimitive((IDirect3DDevice7 *)This,
+    return IDirect3DDevice7_DrawIndexedPrimitive((IDirect3DDevice7 *)device_from_device2(iface),
             PrimitiveType, FVF, Vertices, VertexCount, Indices, IndexCount, Flags);
 }
 
@@ -3789,8 +3781,7 @@ static HRESULT WINAPI
 IDirect3DDeviceImpl_7_SetClipStatus(IDirect3DDevice7 *iface,
                                     D3DCLIPSTATUS *ClipStatus)
 {
-    IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
-    FIXME("(%p)->(%p): Stub!\n", This, ClipStatus);
+    FIXME("iface %p, clip_status %p stub!\n", iface, ClipStatus);
 
     /* D3DCLIPSTATUS and WINED3DCLIPSTATUS are different. I don't know how to convert them
      * Perhaps this needs a new data type and an additional IWineD3DDevice method
@@ -3803,18 +3794,18 @@ static HRESULT WINAPI
 Thunk_IDirect3DDeviceImpl_3_SetClipStatus(IDirect3DDevice3 *iface,
                                           D3DCLIPSTATUS *ClipStatus)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, ClipStatus);
-    return IDirect3DDevice7_SetClipStatus((IDirect3DDevice7 *)This, ClipStatus);
+    TRACE("iface %p, clip_status %p.\n", iface, ClipStatus);
+
+    return IDirect3DDevice7_SetClipStatus((IDirect3DDevice7 *)device_from_device3(iface), ClipStatus);
 }
 
 static HRESULT WINAPI
 Thunk_IDirect3DDeviceImpl_2_SetClipStatus(IDirect3DDevice2 *iface,
                                           D3DCLIPSTATUS *ClipStatus)
 {
-    IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, ClipStatus);
-    return IDirect3DDevice7_SetClipStatus((IDirect3DDevice7 *)This, ClipStatus);
+    TRACE("iface %p, clip_status %p.\n", iface, ClipStatus);
+
+    return IDirect3DDevice7_SetClipStatus((IDirect3DDevice7 *)device_from_device2(iface), ClipStatus);
 }
 
 /*****************************************************************************
@@ -3833,8 +3824,7 @@ static HRESULT WINAPI
 IDirect3DDeviceImpl_7_GetClipStatus(IDirect3DDevice7 *iface,
                                     D3DCLIPSTATUS *ClipStatus)
 {
-    IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
-    FIXME("(%p)->(%p): Stub!\n", This, ClipStatus);
+    FIXME("iface %p, clip_status %p stub!\n", iface, ClipStatus);
 
     /* D3DCLIPSTATUS and WINED3DCLIPSTATUS are different. I don't know how to convert them */
     /* return IWineD3DDevice_GetClipStatus(This->wineD3DDevice, ClipStatus);*/
@@ -3845,18 +3835,18 @@ static HRESULT WINAPI
 Thunk_IDirect3DDeviceImpl_3_GetClipStatus(IDirect3DDevice3 *iface,
                                           D3DCLIPSTATUS *ClipStatus)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, ClipStatus);
-    return IDirect3DDevice7_GetClipStatus((IDirect3DDevice7 *)This, ClipStatus);
+    TRACE("iface %p, clip_status %p.\n", iface, ClipStatus);
+
+    return IDirect3DDevice7_GetClipStatus((IDirect3DDevice7 *)device_from_device3(iface), ClipStatus);
 }
 
 static HRESULT WINAPI
 Thunk_IDirect3DDeviceImpl_2_GetClipStatus(IDirect3DDevice2 *iface,
                                           D3DCLIPSTATUS *ClipStatus)
 {
-    IDirect3DDeviceImpl *This = device_from_device2(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, ClipStatus);
-    return IDirect3DDevice7_GetClipStatus((IDirect3DDevice7 *)This, ClipStatus);
+    TRACE("iface %p, clip_status %p.\n", iface, ClipStatus);
+
+    return IDirect3DDevice7_GetClipStatus((IDirect3DDevice7 *)device_from_device2(iface), ClipStatus);
 }
 
 /*****************************************************************************
@@ -3893,7 +3883,8 @@ IDirect3DDeviceImpl_7_DrawPrimitiveStrided(IDirect3DDevice7 *iface,
     DWORD i;
     HRESULT hr;
 
-    TRACE("(%p)->(%08x,%08x,%p,%08x,%08x): stub!\n", This, PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Flags);
+    TRACE("iface %p, primitive_type %#x, FVF %#x, strided_data %p, vertex_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Flags);
 
     memset(&WineD3DStrided, 0, sizeof(WineD3DStrided));
     /* Get the strided data right. the wined3d structure is a bit bigger
@@ -3996,9 +3987,10 @@ Thunk_IDirect3DDeviceImpl_3_DrawPrimitiveStrided(IDirect3DDevice3 *iface,
                                                  DWORD VertexCount,
                                                  DWORD Flags)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x,%p,%08x,%08x) thunking to IDirect3DDevice7 interface.\n", This, PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Flags);
-    return IDirect3DDevice7_DrawPrimitiveStrided((IDirect3DDevice7 *)This,
+    TRACE("iface %p, primitive_type %#x, FVF %#x, strided_data %p, vertex_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Flags);
+
+    return IDirect3DDevice7_DrawPrimitiveStrided((IDirect3DDevice7 *)device_from_device3(iface),
             PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Flags);
 }
 
@@ -4034,7 +4026,8 @@ IDirect3DDeviceImpl_7_DrawIndexedPrimitiveStrided(IDirect3DDevice7 *iface,
     DWORD i;
     HRESULT hr;
 
-    TRACE("(%p)->(%08x,%08x,%p,%08x,%p,%08x,%08x)\n", This, PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Indices, IndexCount, Flags);
+    TRACE("iface %p, primitive_type %#x, FVF %#x, strided_data %p, vertex_count %u, indices %p, index_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Indices, IndexCount, Flags);
 
     memset(&WineD3DStrided, 0, sizeof(WineD3DStrided));
     /* Get the strided data right. the wined3d structure is a bit bigger
@@ -4144,10 +4137,11 @@ Thunk_IDirect3DDeviceImpl_3_DrawIndexedPrimitiveStrided(IDirect3DDevice3 *iface,
                                                         DWORD IndexCount,
                                                         DWORD Flags)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x,%p,%08x,%p,%08x,%08x) thunking to IDirect3DDevice7 interface.\n", iface, PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Indices, IndexCount, Flags);
-    return IDirect3DDevice7_DrawIndexedPrimitiveStrided((IDirect3DDevice7 *)This, PrimitiveType,
-            VertexType, D3DDrawPrimStrideData, VertexCount, Indices, IndexCount, Flags);
+    TRACE("iface %p, primitive_type %#x, FVF %#x, strided_data %p, vertex_count %u, indices %p, index_count %u, flags %#x.\n",
+            iface, PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Indices, IndexCount, Flags);
+
+    return IDirect3DDevice7_DrawIndexedPrimitiveStrided((IDirect3DDevice7 *)device_from_device3(iface),
+            PrimitiveType, VertexType, D3DDrawPrimStrideData, VertexCount, Indices, IndexCount, Flags);
 }
 
 /*****************************************************************************
@@ -4182,7 +4176,8 @@ IDirect3DDeviceImpl_7_DrawPrimitiveVB(IDirect3DDevice7 *iface,
     HRESULT hr;
     DWORD stride;
 
-    TRACE("(%p)->(%08x,%p,%08x,%08x,%08x)\n", This, PrimitiveType, D3DVertexBuf, StartVertex, NumVertices, Flags);
+    TRACE("iface %p, primitive_type %#x, vb %p, start_vertex %u, vertex_count %u, flags %#x.\n",
+            iface, PrimitiveType, D3DVertexBuf, StartVertex, NumVertices, Flags);
 
     /* Sanity checks */
     if(!vb)
@@ -4259,11 +4254,13 @@ Thunk_IDirect3DDeviceImpl_3_DrawPrimitiveVB(IDirect3DDevice3 *iface,
                                             DWORD NumVertices,
                                             DWORD Flags)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
     IDirect3DVertexBufferImpl *vb = D3DVertexBuf ? vb_from_vb1(D3DVertexBuf) : NULL;
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p,%08x,%08x,%08x) thunking to IDirect3DDevice7 interface.\n", This,  PrimitiveType, vb, StartVertex, NumVertices, Flags);
-    return IDirect3DDevice7_DrawPrimitiveVB((IDirect3DDevice7 *)This, PrimitiveType,
-            (IDirect3DVertexBuffer7 *)vb, StartVertex, NumVertices, Flags);
+
+    TRACE("iface %p, primitive_type %#x, vb %p, start_vertex %u, vertex_count %u, flags %#x.\n",
+            iface, PrimitiveType, D3DVertexBuf, StartVertex, NumVertices, Flags);
+
+    return IDirect3DDevice7_DrawPrimitiveVB((IDirect3DDevice7 *)device_from_device3(iface),
+            PrimitiveType, (IDirect3DVertexBuffer7 *)vb, StartVertex, NumVertices, Flags);
 }
 
 
@@ -4299,8 +4296,10 @@ IDirect3DDeviceImpl_7_DrawIndexedPrimitiveVB(IDirect3DDevice7 *iface,
     DWORD stride = get_flexible_vertex_size(vb->fvf);
     WORD *LockedIndices;
     HRESULT hr;
+    WINED3DBUFFER_DESC desc;
 
-    TRACE("(%p)->(%08x,%p,%d,%d,%p,%d,%08x)\n", This, PrimitiveType, vb, StartVertex, NumVertices, Indices, IndexCount, Flags);
+    TRACE("iface %p, primitive_type %#x, vb %p, start_vertex %u, vertex_count %u, indices %p, index_count %u, flags %#x.\n",
+            iface, PrimitiveType, D3DVertexBuf, StartVertex, NumVertices, Indices, IndexCount, Flags);
 
     /* Steps:
      * 1) Upload the Indices to the index buffer
@@ -4320,6 +4319,33 @@ IDirect3DDeviceImpl_7_DrawIndexedPrimitiveVB(IDirect3DDevice7 *iface,
         return hr;
     }
 
+    /* check that the buffer is large enough to hold the indices,
+     * reallocate if necessary. */
+    IWineD3DBuffer_GetDesc(This->indexbuffer, &desc);
+    if (desc.Size < IndexCount * sizeof(WORD))
+    {
+        UINT size = max(desc.Size * 2, IndexCount * sizeof(WORD));
+        IWineD3DBuffer *buffer;
+        IParentImpl *parent;
+
+        TRACE("Growing index buffer to %u bytes\n", size);
+
+        parent = IWineD3DBuffer_GetParent(This->indexbuffer);
+        hr = IWineD3DDevice_CreateIndexBuffer(This->wineD3DDevice, size, WINED3DUSAGE_DYNAMIC /* Usage */,
+                WINED3DPOOL_DEFAULT, parent, &ddraw_null_wined3d_parent_ops, &buffer);
+        if (FAILED(hr))
+        {
+            ERR("(%p) IWineD3DDevice::CreateIndexBuffer failed with hr = %08x\n", This, hr);
+            LeaveCriticalSection(&ddraw_cs);
+            return hr;
+        }
+
+        IWineD3DBuffer_Release(This->indexbuffer);
+        This->indexbuffer = buffer;
+
+        parent->child = (IUnknown *)buffer;
+    }
+
     /* copy the index stream into the index buffer.
      * A new IWineD3DDevice method could be created
      * which takes an user pointer containing the indices
@@ -4331,7 +4357,6 @@ IDirect3DDeviceImpl_7_DrawIndexedPrimitiveVB(IDirect3DDevice7 *iface,
                             IndexCount * sizeof(WORD),
                             (BYTE **) &LockedIndices,
                             0 /* Flags */);
-    assert(IndexCount < 0x100000);
     if(hr != D3D_OK)
     {
         ERR("(%p) IWineD3DBuffer::Map failed with hr = %08x\n", This, hr);
@@ -4414,12 +4439,13 @@ Thunk_IDirect3DDeviceImpl_3_DrawIndexedPrimitiveVB(IDirect3DDevice3 *iface,
                                                    DWORD IndexCount,
                                                    DWORD Flags)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
     IDirect3DVertexBufferImpl *VB = vb_from_vb1(D3DVertexBuf);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p,%p,%08x,%08x) thunking to IDirect3DDevice7 interface.\n", This, PrimitiveType, VB, Indices, IndexCount, Flags);
 
-    return IDirect3DDevice7_DrawIndexedPrimitiveVB((IDirect3DDevice7 *)This, PrimitiveType,
-            (IDirect3DVertexBuffer7 *)VB, 0, IndexCount, Indices, IndexCount, Flags);
+    TRACE("iface %p, primitive_type %#x, vb %p, indices %p, index_count %u, flags %#x.\n",
+            iface, PrimitiveType, D3DVertexBuf, Indices, IndexCount, Flags);
+
+    return IDirect3DDevice7_DrawIndexedPrimitiveVB((IDirect3DDevice7 *)device_from_device3(iface),
+            PrimitiveType, (IDirect3DVertexBuffer7 *)VB, 0, IndexCount, Indices, IndexCount, Flags);
 }
 
 /*****************************************************************************
@@ -4475,7 +4501,8 @@ IDirect3DDeviceImpl_7_ComputeSphereVisibility(IDirect3DDevice7 *iface,
     HRESULT hr;
     UINT i, j;
 
-    TRACE("(%p)->(%p,%p,%08x,%08x,%p)\n", iface, Centers, Radii, NumSpheres, Flags, ReturnValues);
+    TRACE("iface %p, centers %p, radii %p, sphere_count %u, flags %#x, return_values %p.\n",
+            iface, Centers, Radii, NumSpheres, Flags, ReturnValues);
 
     hr = IDirect3DDeviceImpl_7_GetTransform(iface, D3DTRANSFORMSTATE_WORLD, &m);
     if ( hr != DD_OK ) return DDERR_INVALIDPARAMS;
@@ -4540,9 +4567,10 @@ Thunk_IDirect3DDeviceImpl_3_ComputeSphereVisibility(IDirect3DDevice3 *iface,
                                                     DWORD Flags,
                                                     DWORD *ReturnValues)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p,%08x,%08x,%p) thunking to IDirect3DDevice7 interface.\n", This, Centers, Radii, NumSpheres, Flags, ReturnValues);
-    return IDirect3DDevice7_ComputeSphereVisibility((IDirect3DDevice7 *)This,
+    TRACE("iface %p, centers %p, radii %p, sphere_count %u, flags %#x, return_values %p.\n",
+            iface, Centers, Radii, NumSpheres, Flags, ReturnValues);
+
+    return IDirect3DDevice7_ComputeSphereVisibility((IDirect3DDevice7 *)device_from_device3(iface),
             Centers, Radii, NumSpheres, Flags, ReturnValues);
 }
 
@@ -4573,7 +4601,8 @@ IDirect3DDeviceImpl_7_GetTexture(IDirect3DDevice7 *iface,
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     IWineD3DBaseTexture *Surf;
     HRESULT hr;
-    TRACE("(%p)->(%d,%p): Relay\n", This, Stage, Texture);
+
+    TRACE("iface %p, stage %u, texture %p.\n", iface, Stage, Texture);
 
     if(!Texture)
     {
@@ -4590,11 +4619,8 @@ IDirect3DDeviceImpl_7_GetTexture(IDirect3DDevice7 *iface,
         return hr;
     }
 
-    /* GetParent AddRef()s, which is perfectly OK.
-     * We have passed the IDirectDrawSurface7 interface to WineD3D, so that's OK too.
-     */
-    hr = IWineD3DBaseTexture_GetParent(Surf,
-                                       (IUnknown **) Texture);
+    *Texture = IWineD3DBaseTexture_GetParent(Surf);
+    IDirectDrawSurface7_AddRef(*Texture);
     LeaveCriticalSection(&ddraw_cs);
     return hr;
 }
@@ -4627,16 +4653,16 @@ Thunk_IDirect3DDeviceImpl_3_GetTexture(IDirect3DDevice3 *iface,
                                        DWORD Stage,
                                        IDirect3DTexture2 **Texture2)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
     HRESULT ret;
     IDirectDrawSurface7 *ret_val;
 
-    TRACE_(ddraw_thunk)("(%p)->(%d,%p) thunking to IDirect3DDevice7 interface.\n", This, Stage, Texture2);
-    ret = IDirect3DDevice7_GetTexture((IDirect3DDevice7 *)This, Stage, &ret_val);
+    TRACE("iface %p, stage %u, texture %p.\n", iface, Stage, Texture2);
+
+    ret = IDirect3DDevice7_GetTexture((IDirect3DDevice7 *)device_from_device3(iface), Stage, &ret_val);
 
     *Texture2 = ret_val ? (IDirect3DTexture2 *)&((IDirectDrawSurfaceImpl *)ret_val)->IDirect3DTexture2_vtbl : NULL;
 
-    TRACE_(ddraw_thunk)(" returning interface %p.\n", *Texture2);
+    TRACE("Returning texture %p.\n", *Texture2);
 
     return ret;
 }
@@ -4665,7 +4691,8 @@ IDirect3DDeviceImpl_7_SetTexture(IDirect3DDevice7 *iface,
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     IDirectDrawSurfaceImpl *surf = (IDirectDrawSurfaceImpl *)Texture;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p): Relay!\n", This, Stage, surf);
+
+    TRACE("iface %p, stage %u, texture %p.\n", iface, Stage, Texture);
 
     /* Texture may be NULL here */
     EnterCriticalSection(&ddraw_cs);
@@ -4708,7 +4735,8 @@ IDirect3DDeviceImpl_3_SetTexture(IDirect3DDevice3 *iface,
     IDirectDrawSurfaceImpl *tex = Texture2 ? surface_from_texture2(Texture2) : NULL;
     DWORD texmapblend;
     HRESULT hr;
-    TRACE("(%p)->(%d,%p)\n", This, Stage, tex);
+
+    TRACE("iface %p, stage %u, texture %p.\n", iface, Stage, Texture2);
 
     EnterCriticalSection(&ddraw_cs);
 
@@ -4817,8 +4845,10 @@ IDirect3DDeviceImpl_7_GetTextureStageState(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    const struct tss_lookup *l = &tss_lookup[TexStageStateType];
-    TRACE("(%p)->(%08x,%08x,%p): Relay!\n", This, Stage, TexStageStateType, State);
+    const struct tss_lookup *l;
+
+    TRACE("iface %p, stage %u, state %#x, value %p.\n",
+            iface, Stage, TexStageStateType, State);
 
     if(!State)
         return DDERR_INVALIDPARAMS;
@@ -4826,10 +4856,11 @@ IDirect3DDeviceImpl_7_GetTextureStageState(IDirect3DDevice7 *iface,
     if (TexStageStateType > D3DTSS_TEXTURETRANSFORMFLAGS)
     {
         WARN("Invalid TexStageStateType %#x passed.\n", TexStageStateType);
-        *State = 0;
         return DD_OK;
     }
 
+    l = &tss_lookup[TexStageStateType];
+
     EnterCriticalSection(&ddraw_cs);
 
     if (l->sampler_state)
@@ -4916,9 +4947,11 @@ Thunk_IDirect3DDeviceImpl_3_GetTextureStageState(IDirect3DDevice3 *iface,
                                                  D3DTEXTURESTAGESTATETYPE TexStageStateType,
                                                  DWORD *State)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x,%p) thunking to IDirect3DDevice7 interface.\n", This, Stage, TexStageStateType, State);
-    return IDirect3DDevice7_GetTextureStageState((IDirect3DDevice7 *)This, Stage, TexStageStateType, State);
+    TRACE("iface %p, stage %u, state %#x, value %p.\n",
+            iface, Stage, TexStageStateType, State);
+
+    return IDirect3DDevice7_GetTextureStageState((IDirect3DDevice7 *)device_from_device3(iface),
+            Stage, TexStageStateType, State);
 }
 
 /*****************************************************************************
@@ -4946,9 +4979,11 @@ IDirect3DDeviceImpl_7_SetTextureStageState(IDirect3DDevice7 *iface,
                                            DWORD State)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
-    const struct tss_lookup *l = &tss_lookup[TexStageStateType];
+    const struct tss_lookup *l;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%08x,%08x): Relay!\n", This, Stage, TexStageStateType, State);
+
+    TRACE("iface %p, stage %u, state %#x, value %#x.\n",
+            iface, Stage, TexStageStateType, State);
 
     if (TexStageStateType > D3DTSS_TEXTURETRANSFORMFLAGS)
     {
@@ -4956,6 +4991,8 @@ IDirect3DDeviceImpl_7_SetTextureStageState(IDirect3DDevice7 *iface,
         return DD_OK;
     }
 
+    l = &tss_lookup[TexStageStateType];
+
     EnterCriticalSection(&ddraw_cs);
 
     if (l->sampler_state)
@@ -5047,9 +5084,11 @@ Thunk_IDirect3DDeviceImpl_3_SetTextureStageState(IDirect3DDevice3 *iface,
                                                  D3DTEXTURESTAGESTATETYPE TexStageStateType,
                                                  DWORD State)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x,%08x) thunking to IDirect3DDevice7 interface.\n", This, Stage, TexStageStateType, State);
-    return IDirect3DDevice7_SetTextureStageState((IDirect3DDevice7 *)This, Stage, TexStageStateType, State);
+    TRACE("iface %p, stage %u, state %#x, value %#x.\n",
+            iface, Stage, TexStageStateType, State);
+
+    return IDirect3DDevice7_SetTextureStageState((IDirect3DDevice7 *)device_from_device3(iface),
+            Stage, TexStageStateType, State);
 }
 
 /*****************************************************************************
@@ -5076,7 +5115,8 @@ IDirect3DDeviceImpl_7_ValidateDevice(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p): Relay\n", This, NumPasses);
+
+    TRACE("iface %p, pass_count %p.\n", iface, NumPasses);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DDevice_ValidateDevice(This->wineD3DDevice, NumPasses);
@@ -5109,9 +5149,9 @@ static HRESULT WINAPI
 Thunk_IDirect3DDeviceImpl_3_ValidateDevice(IDirect3DDevice3 *iface,
                                            DWORD *Passes)
 {
-    IDirect3DDeviceImpl *This = device_from_device3(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DDevice7 interface.\n", This, Passes);
-    return IDirect3DDevice7_ValidateDevice((IDirect3DDevice7 *)This, Passes);
+    TRACE("iface %p, pass_count %p.\n", iface, Passes);
+
+    return IDirect3DDevice7_ValidateDevice((IDirect3DDevice7 *)device_from_device3(iface), Passes);
 }
 
 /*****************************************************************************
@@ -5146,11 +5186,12 @@ IDirect3DDeviceImpl_7_Clear(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p,%08x,%08x,%f,%08x): Relay\n", This, Count, Rects, Flags, Color, Z, Stencil);
 
-    /* Note; D3DRECT is compatible with WINED3DRECT */
+    TRACE("iface %p, count %u, rects %p, flags %#x, color 0x%08x, z %.8e, stencil %#x.\n",
+            iface, Count, Rects, Flags, Color, Z, Stencil);
+
     EnterCriticalSection(&ddraw_cs);
-    hr = IWineD3DDevice_Clear(This->wineD3DDevice, Count, (WINED3DRECT*) Rects, Flags, Color, Z, Stencil);
+    hr = IWineD3DDevice_Clear(This->wineD3DDevice, Count, (RECT *)Rects, Flags, Color, Z, Stencil);
     LeaveCriticalSection(&ddraw_cs);
     return hr;
 }
@@ -5209,7 +5250,8 @@ IDirect3DDeviceImpl_7_SetViewport(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p) Relay!\n", This, Data);
+
+    TRACE("iface %p, viewport %p.\n", iface, Data);
 
     if(!Data)
         return DDERR_INVALIDPARAMS;
@@ -5265,7 +5307,8 @@ IDirect3DDeviceImpl_7_GetViewport(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p) Relay!\n", This, Data);
+
+    TRACE("iface %p, viewport %p.\n", iface, Data);
 
     if(!Data)
         return DDERR_INVALIDPARAMS;
@@ -5322,7 +5365,8 @@ IDirect3DDeviceImpl_7_SetMaterial(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p): Relay!\n", This, Mat);
+
+    TRACE("iface %p, material %p.\n", iface, Mat);
 
     if (!Mat) return DDERR_INVALIDPARAMS;
     /* Note: D3DMATERIAL7 is compatible with WINED3DMATERIAL */
@@ -5376,7 +5420,8 @@ IDirect3DDeviceImpl_7_GetMaterial(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p): Relay!\n", This, Mat);
+
+    TRACE("iface %p, material %p.\n", iface, Mat);
 
     EnterCriticalSection(&ddraw_cs);
     /* Note: D3DMATERIAL7 is compatible with WINED3DMATERIAL */
@@ -5430,7 +5475,8 @@ IDirect3DDeviceImpl_7_SetLight(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p): Relay!\n", This, LightIndex, Light);
+
+    TRACE("iface %p, light_idx %u, light %p.\n", iface, LightIndex, Light);
 
     EnterCriticalSection(&ddraw_cs);
     /* Note: D3DLIGHT7 is compatible with WINED3DLIGHT */
@@ -5485,7 +5531,8 @@ IDirect3DDeviceImpl_7_GetLight(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT rc;
-    TRACE("(%p)->(%08x,%p): Relay!\n", This, LightIndex, Light);
+
+    TRACE("iface %p, light_idx %u, light %p.\n", iface, LightIndex, Light);
 
     EnterCriticalSection(&ddraw_cs);
     /* Note: D3DLIGHT7 is compatible with WINED3DLIGHT */
@@ -5538,7 +5585,8 @@ IDirect3DDeviceImpl_7_BeginStateBlock(IDirect3DDevice7 *iface)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(): Relay!\n", This);
+
+    TRACE("iface %p.\n", iface);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DDevice_BeginStateBlock(This->wineD3DDevice);
@@ -5587,8 +5635,11 @@ IDirect3DDeviceImpl_7_EndStateBlock(IDirect3DDevice7 *iface,
                                     DWORD *BlockHandle)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
+    IWineD3DStateBlock *wined3d_sb;
     HRESULT hr;
-    TRACE("(%p)->(%p): Relay!\n", This, BlockHandle);
+    DWORD h;
+
+    TRACE("iface %p, stateblock %p.\n", iface, BlockHandle);
 
     if(!BlockHandle)
     {
@@ -5597,17 +5648,29 @@ IDirect3DDeviceImpl_7_EndStateBlock(IDirect3DDevice7 *iface,
     }
 
     EnterCriticalSection(&ddraw_cs);
-    *BlockHandle = IDirect3DDeviceImpl_CreateHandle(This);
-    if(!*BlockHandle)
+
+    hr = IWineD3DDevice_EndStateBlock(This->wineD3DDevice, &wined3d_sb);
+    if (FAILED(hr))
     {
-        ERR("Cannot get a handle number for the stateblock\n");
+        WARN("Failed to end stateblock, hr %#x.\n", hr);
         LeaveCriticalSection(&ddraw_cs);
+        *BlockHandle = 0;
+        return hr_ddraw_from_wined3d(hr);
+    }
+
+    h = ddraw_allocate_handle(&This->handle_table, wined3d_sb, DDRAW_HANDLE_STATEBLOCK);
+    if (h == DDRAW_INVALID_HANDLE)
+    {
+        ERR("Failed to allocate a stateblock handle.\n");
+        IWineD3DStateBlock_Release(wined3d_sb);
+        LeaveCriticalSection(&ddraw_cs);
+        *BlockHandle = 0;
         return DDERR_OUTOFMEMORY;
     }
-    This->Handles[*BlockHandle - 1].type = DDrawHandle_StateBlock;
-    hr = IWineD3DDevice_EndStateBlock(This->wineD3DDevice,
-                                      (IWineD3DStateBlock **) &This->Handles[*BlockHandle - 1].ptr);
+
     LeaveCriticalSection(&ddraw_cs);
+    *BlockHandle = h + 1;
+
     return hr_ddraw_from_wined3d(hr);
 }
 
@@ -5653,10 +5716,9 @@ static HRESULT
 IDirect3DDeviceImpl_7_PreLoad(IDirect3DDevice7 *iface,
                               IDirectDrawSurface7 *Texture)
 {
-    IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     IDirectDrawSurfaceImpl *surf = (IDirectDrawSurfaceImpl *)Texture;
 
-    TRACE("(%p)->(%p): Relay!\n", This, surf);
+    TRACE("iface %p, texture %p.\n", iface, Texture);
 
     if(!Texture)
         return DDERR_INVALIDPARAMS;
@@ -5706,25 +5768,24 @@ IDirect3DDeviceImpl_7_ApplyStateBlock(IDirect3DDevice7 *iface,
                                       DWORD BlockHandle)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
+    IWineD3DStateBlock *wined3d_sb;
     HRESULT hr;
-    TRACE("(%p)->(%08x): Relay!\n", This, BlockHandle);
+
+    TRACE("iface %p, stateblock %#x.\n", iface, BlockHandle);
 
     EnterCriticalSection(&ddraw_cs);
-    if(!BlockHandle || BlockHandle > This->numHandles)
-    {
-        WARN("Out of range handle %d, returning D3DERR_INVALIDSTATEBLOCK\n", BlockHandle);
-        LeaveCriticalSection(&ddraw_cs);
-        return D3DERR_INVALIDSTATEBLOCK;
-    }
-    if(This->Handles[BlockHandle - 1].type != DDrawHandle_StateBlock)
+
+    wined3d_sb = ddraw_get_object(&This->handle_table, BlockHandle - 1, DDRAW_HANDLE_STATEBLOCK);
+    if (!wined3d_sb)
     {
-        WARN("Handle %d is not a stateblock, returning D3DERR_INVALIDSTATEBLOCK\n", BlockHandle);
+        WARN("Invalid stateblock handle.\n");
         LeaveCriticalSection(&ddraw_cs);
         return D3DERR_INVALIDSTATEBLOCK;
     }
 
-    hr = IWineD3DStateBlock_Apply((IWineD3DStateBlock *) This->Handles[BlockHandle - 1].ptr);
+    hr = IWineD3DStateBlock_Apply(wined3d_sb);
     LeaveCriticalSection(&ddraw_cs);
+
     return hr_ddraw_from_wined3d(hr);
 }
 
@@ -5770,24 +5831,22 @@ IDirect3DDeviceImpl_7_CaptureStateBlock(IDirect3DDevice7 *iface,
                                         DWORD BlockHandle)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
+    IWineD3DStateBlock *wined3d_sb;
     HRESULT hr;
-    TRACE("(%p)->(%08x): Relay!\n", This, BlockHandle);
+
+    TRACE("iface %p, stateblock %#x.\n", iface, BlockHandle);
 
     EnterCriticalSection(&ddraw_cs);
-    if(BlockHandle == 0 || BlockHandle > This->numHandles)
-    {
-        WARN("Out of range handle %d, returning D3DERR_INVALIDSTATEBLOCK\n", BlockHandle);
-        LeaveCriticalSection(&ddraw_cs);
-        return D3DERR_INVALIDSTATEBLOCK;
-    }
-    if(This->Handles[BlockHandle - 1].type != DDrawHandle_StateBlock)
+
+    wined3d_sb = ddraw_get_object(&This->handle_table, BlockHandle - 1, DDRAW_HANDLE_STATEBLOCK);
+    if (!wined3d_sb)
     {
-        WARN("Handle %d is not a stateblock, returning D3DERR_INVALIDSTATEBLOCK\n", BlockHandle);
+        WARN("Invalid stateblock handle.\n");
         LeaveCriticalSection(&ddraw_cs);
         return D3DERR_INVALIDSTATEBLOCK;
     }
 
-    hr = IWineD3DStateBlock_Capture((IWineD3DStateBlock *) This->Handles[BlockHandle - 1].ptr);
+    hr = IWineD3DStateBlock_Capture(wined3d_sb);
     LeaveCriticalSection(&ddraw_cs);
     return hr_ddraw_from_wined3d(hr);
 }
@@ -5833,30 +5892,25 @@ IDirect3DDeviceImpl_7_DeleteStateBlock(IDirect3DDevice7 *iface,
                                        DWORD BlockHandle)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
+    IWineD3DStateBlock *wined3d_sb;
     ULONG ref;
-    TRACE("(%p)->(%08x): Relay!\n", This, BlockHandle);
+
+    TRACE("iface %p, stateblock %#x.\n", iface, BlockHandle);
 
     EnterCriticalSection(&ddraw_cs);
-    if(BlockHandle == 0 || BlockHandle > This->numHandles)
-    {
-        WARN("Out of range handle %d, returning D3DERR_INVALIDSTATEBLOCK\n", BlockHandle);
-        LeaveCriticalSection(&ddraw_cs);
-        return D3DERR_INVALIDSTATEBLOCK;
-    }
-    if(This->Handles[BlockHandle - 1].type != DDrawHandle_StateBlock)
+
+    wined3d_sb = ddraw_free_handle(&This->handle_table, BlockHandle - 1, DDRAW_HANDLE_STATEBLOCK);
+    if (!wined3d_sb)
     {
-        WARN("Handle %d is not a stateblock, returning D3DERR_INVALIDSTATEBLOCK\n", BlockHandle);
+        WARN("Invalid stateblock handle.\n");
         LeaveCriticalSection(&ddraw_cs);
         return D3DERR_INVALIDSTATEBLOCK;
     }
 
-    ref = IWineD3DStateBlock_Release((IWineD3DStateBlock *) This->Handles[BlockHandle - 1].ptr);
-    if(ref)
+    if ((ref = IWineD3DStateBlock_Release(wined3d_sb)))
     {
-        ERR("Something is still holding the stateblock %p(Handle %d). Ref = %d\n", This->Handles[BlockHandle - 1].ptr, BlockHandle, ref);
+        ERR("Something is still holding stateblock %p (refcount %u).\n", wined3d_sb, ref);
     }
-    This->Handles[BlockHandle - 1].ptr = NULL;
-    This->Handles[BlockHandle - 1].type = DDrawHandle_Unknown;
 
     LeaveCriticalSection(&ddraw_cs);
     return D3D_OK;
@@ -5905,8 +5959,11 @@ IDirect3DDeviceImpl_7_CreateStateBlock(IDirect3DDevice7 *iface,
                                        DWORD *BlockHandle)
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
+    IWineD3DStateBlock *wined3d_sb;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p)!\n", This, Type, BlockHandle);
+    DWORD h;
+
+    TRACE("iface %p, type %#x, stateblock %p.\n", iface, Type, BlockHandle);
 
     if(!BlockHandle)
     {
@@ -5920,21 +5977,28 @@ IDirect3DDeviceImpl_7_CreateStateBlock(IDirect3DDevice7 *iface,
     }
 
     EnterCriticalSection(&ddraw_cs);
-    *BlockHandle = IDirect3DDeviceImpl_CreateHandle(This);
-    if(!*BlockHandle)
+
+    /* The D3DSTATEBLOCKTYPE enum is fine here. */
+    hr = IWineD3DDevice_CreateStateBlock(This->wineD3DDevice, Type, &wined3d_sb);
+    if (FAILED(hr))
     {
-        ERR("Cannot get a handle number for the stateblock\n");
+        WARN("Failed to create stateblock, hr %#x.\n", hr);
+        LeaveCriticalSection(&ddraw_cs);
+        return hr_ddraw_from_wined3d(hr);
+    }
+
+    h = ddraw_allocate_handle(&This->handle_table, wined3d_sb, DDRAW_HANDLE_STATEBLOCK);
+    if (h == DDRAW_INVALID_HANDLE)
+    {
+        ERR("Failed to allocate stateblock handle.\n");
+        IWineD3DStateBlock_Release(wined3d_sb);
         LeaveCriticalSection(&ddraw_cs);
         return DDERR_OUTOFMEMORY;
     }
-    This->Handles[*BlockHandle - 1].type = DDrawHandle_StateBlock;
 
-    /* The D3DSTATEBLOCKTYPE enum is fine here */
-    hr = IWineD3DDevice_CreateStateBlock(This->wineD3DDevice,
-                                         Type,
-                                         (IWineD3DStateBlock **) &This->Handles[*BlockHandle - 1].ptr,
-                                         NULL /* Parent, hope that works */);
+    *BlockHandle = h + 1;
     LeaveCriticalSection(&ddraw_cs);
+
     return hr_ddraw_from_wined3d(hr);
 }
 
@@ -6074,7 +6138,7 @@ static void copy_mipmap_chain(IDirect3DDeviceImpl *device,
             /* Try UpdateSurface that may perform a more direct opengl loading. But skip this if destination is paletted texture and has no palette.
              * Some games like Sacrifice set palette after Load, and it is a waste of effort to try to load texture without palette and generates
              * warnings in wined3d. */
-           if (!palette_missing)
+            if (!palette_missing)
                 hr = IWineD3DDevice_UpdateSurface(device->wineD3DDevice, src_level->WineD3DSurface, &rect, dest_level->WineD3DSurface,
                                 &point);
 
@@ -6154,7 +6218,9 @@ IDirect3DDeviceImpl_7_Load(IDirect3DDevice7 *iface,
     IDirectDrawSurfaceImpl *src = (IDirectDrawSurfaceImpl *)SrcTex;
     POINT destpoint;
     RECT srcrect;
-    TRACE("(%p)->(%p,%p,%p,%p,%08x)\n", This, dest, DestPoint, src, SrcRect, Flags);
+
+    TRACE("iface %p, dst_texture %p, dst_pos %s, src_texture %p, src_rect %s, flags %#x.\n",
+            iface, DestTex, wine_dbgstr_point(DestPoint), SrcTex, wine_dbgstr_rect(SrcRect), Flags);
 
     if( (!src) || (!dest) )
         return DDERR_INVALIDPARAMS;
@@ -6364,7 +6430,8 @@ IDirect3DDeviceImpl_7_LightEnable(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%d): Relay!\n", This, LightIndex, Enable);
+
+    TRACE("iface %p, light_idx %u, enabled %#x.\n", iface, LightIndex, Enable);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DDevice_SetLightEnable(This->wineD3DDevice, LightIndex, Enable);
@@ -6419,7 +6486,8 @@ IDirect3DDeviceImpl_7_GetLightEnable(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p): Relay\n", This, LightIndex, Enable);
+
+    TRACE("iface %p, light_idx %u, enabled %p.\n", iface, LightIndex, Enable);
 
     if(!Enable)
         return DDERR_INVALIDPARAMS;
@@ -6477,7 +6545,8 @@ IDirect3DDeviceImpl_7_SetClipPlane(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%08x,%p): Relay!\n", This, Index, PlaneEquation);
+
+    TRACE("iface %p, idx %u, plane %p.\n", iface, Index, PlaneEquation);
 
     if(!PlaneEquation)
         return DDERR_INVALIDPARAMS;
@@ -6533,7 +6602,8 @@ IDirect3DDeviceImpl_7_GetClipPlane(IDirect3DDevice7 *iface,
 {
     IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%d,%p): Relay!\n", This, Index, PlaneEquation);
+
+    TRACE("iface %p, idx %u, plane %p.\n", iface, Index, PlaneEquation);
 
     if(!PlaneEquation)
         return DDERR_INVALIDPARAMS;
@@ -6589,10 +6659,10 @@ IDirect3DDeviceImpl_7_GetInfo(IDirect3DDevice7 *iface,
                               void *DevInfoStruct,
                               DWORD Size)
 {
-    IDirect3DDeviceImpl *This = (IDirect3DDeviceImpl *)iface;
-    TRACE("(%p)->(%08x,%p,%08x)\n", This, DevInfoID, DevInfoStruct, Size);
+    TRACE("iface %p, info_id %#x, info %p, info_size %u.\n",
+            iface, DevInfoID, DevInfoStruct, Size);
 
-    if (TRACE_ON(d3d7))
+    if (TRACE_ON(ddraw))
     {
         TRACE(" info requested : ");
         switch (DevInfoID)
@@ -6617,7 +6687,7 @@ IDirect3DDeviceImpl_7_GetInfo(IDirect3DDevice7 *iface,
  * Device created with DDSCL_FPUPRESERVE - resets and restores FPU mode when necessary in
  * d3d calls (FPU may be in a mode non-suitable for d3d when the app calls d3d). Required
  * by Sacrifice (game). */
-const IDirect3DDevice7Vtbl IDirect3DDevice7_FPUSetup_Vtbl =
+static const struct IDirect3DDevice7Vtbl d3d_device7_fpu_setup_vtbl =
 {
     /*** IUnknown Methods ***/
     IDirect3DDeviceImpl_7_QueryInterface,
@@ -6672,7 +6742,7 @@ const IDirect3DDevice7Vtbl IDirect3DDevice7_FPUSetup_Vtbl =
     IDirect3DDeviceImpl_7_GetInfo
 };
 
-const IDirect3DDevice7Vtbl IDirect3DDevice7_FPUPreserve_Vtbl =
+static const struct IDirect3DDevice7Vtbl d3d_device7_fpu_preserve_vtbl =
 {
     /*** IUnknown Methods ***/
     IDirect3DDeviceImpl_7_QueryInterface,
@@ -6727,7 +6797,7 @@ const IDirect3DDevice7Vtbl IDirect3DDevice7_FPUPreserve_Vtbl =
     IDirect3DDeviceImpl_7_GetInfo
 };
 
-const IDirect3DDevice3Vtbl IDirect3DDevice3_Vtbl =
+static const struct IDirect3DDevice3Vtbl d3d_device3_vtbl =
 {
     /*** IUnknown Methods ***/
     Thunk_IDirect3DDeviceImpl_3_QueryInterface,
@@ -6775,7 +6845,7 @@ const IDirect3DDevice3Vtbl IDirect3DDevice3_Vtbl =
     Thunk_IDirect3DDeviceImpl_3_ValidateDevice
 };
 
-const IDirect3DDevice2Vtbl IDirect3DDevice2_Vtbl =
+static const struct IDirect3DDevice2Vtbl d3d_device2_vtbl =
 {
     /*** IUnknown Methods ***/
     Thunk_IDirect3DDeviceImpl_2_QueryInterface,
@@ -6814,7 +6884,7 @@ const IDirect3DDevice2Vtbl IDirect3DDevice2_Vtbl =
     Thunk_IDirect3DDeviceImpl_2_GetClipStatus
 };
 
-const IDirect3DDeviceVtbl IDirect3DDevice1_Vtbl =
+static const struct IDirect3DDeviceVtbl d3d_device1_vtbl =
 {
     /*** IUnknown Methods ***/
     Thunk_IDirect3DDeviceImpl_1_QueryInterface,
@@ -6842,71 +6912,6 @@ const IDirect3DDeviceVtbl IDirect3DDevice1_Vtbl =
     Thunk_IDirect3DDeviceImpl_1_GetDirect3D
 };
 
-/*****************************************************************************
- * IDirect3DDeviceImpl_CreateHandle
- *
- * Not called from the VTable
- *
- * Some older interface versions operate with handles, which are basically
- * DWORDs which identify an interface, for example
- * IDirect3DDevice::SetRenderState with DIRECT3DRENDERSTATE_TEXTUREHANDLE
- *
- * Those handle could be just casts to the interface pointers or vice versa,
- * but that is not 64 bit safe and would mean blindly derefering a DWORD
- * passed by the app. Instead there is a dynamic array in the device which
- * keeps a DWORD to pointer information and a type for the handle.
- *
- * Basically this array only grows, when a handle is freed its pointer is
- * just set to NULL. There will be much more reads from the array than
- * insertion operations, so a dynamic array is fine.
- *
- * Params:
- *  This: D3DDevice implementation for which this handle should be created
- *
- * Returns:
- *  A free handle on success
- *  0 on failure
- *
- *****************************************************************************/
-DWORD
-IDirect3DDeviceImpl_CreateHandle(IDirect3DDeviceImpl *This)
-{
-    DWORD i;
-    struct HandleEntry *oldHandles = This->Handles;
-
-    TRACE("(%p)\n", This);
-
-    for(i = 0; i < This->numHandles; i++)
-    {
-        if(This->Handles[i].ptr == NULL &&
-           This->Handles[i].type == DDrawHandle_Unknown)
-        {
-            TRACE("Reusing freed handle %d\n", i + 1);
-            return i + 1;
-        }
-    }
-
-    TRACE("Growing the handle array\n");
-
-    This->numHandles++;
-    This->Handles = HeapAlloc(GetProcessHeap(), 0, sizeof(struct HandleEntry) * This->numHandles);
-    if(!This->Handles)
-    {
-        ERR("Out of memory\n");
-        This->Handles = oldHandles;
-        This->numHandles--;
-        return 0;
-    }
-    if(oldHandles)
-    {
-        memcpy(This->Handles, oldHandles, (This->numHandles - 1) * sizeof(struct HandleEntry));
-        HeapFree(GetProcessHeap(), 0, oldHandles);
-    }
-
-    TRACE("Returning %d\n", This->numHandles);
-    return This->numHandles;
-}
-
 /*****************************************************************************
  * IDirect3DDeviceImpl_UpdateDepthStencil
  *
@@ -6941,3 +6946,85 @@ IDirect3DDeviceImpl_UpdateDepthStencil(IDirect3DDeviceImpl *This)
     IDirectDrawSurface7_Release(depthStencil);
     return WINED3DZB_TRUE;
 }
+
+HRESULT d3d_device_init(IDirect3DDeviceImpl *device, IDirectDrawImpl *ddraw, IDirectDrawSurfaceImpl *target)
+{
+    IParentImpl *index_buffer_parent;
+    HRESULT hr;
+
+    if (ddraw->cooperative_level & DDSCL_FPUPRESERVE)
+        device->lpVtbl = &d3d_device7_fpu_preserve_vtbl;
+    else
+        device->lpVtbl = &d3d_device7_fpu_setup_vtbl;
+
+    device->IDirect3DDevice3_vtbl = &d3d_device3_vtbl;
+    device->IDirect3DDevice2_vtbl = &d3d_device2_vtbl;
+    device->IDirect3DDevice_vtbl = &d3d_device1_vtbl;
+    device->ref = 1;
+    device->ddraw = ddraw;
+    device->target = target;
+
+    if (!ddraw_handle_table_init(&device->handle_table, 64))
+    {
+        ERR("Failed to initialize handle table.\n");
+        return DDERR_OUTOFMEMORY;
+    }
+
+    device->legacyTextureBlending = FALSE;
+
+    /* Create an index buffer, it's needed for indexed drawing */
+    index_buffer_parent = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*index_buffer_parent));
+    if (!index_buffer_parent)
+    {
+        ERR("Failed to allocate index buffer parent memory.\n");
+        ddraw_handle_table_destroy(&device->handle_table);
+        return DDERR_OUTOFMEMORY;
+    }
+
+    ddraw_parent_init(index_buffer_parent);
+
+    hr = IWineD3DDevice_CreateIndexBuffer(ddraw->wineD3DDevice, 0x40000 /* Length. Don't know how long it should be */,
+            WINED3DUSAGE_DYNAMIC /* Usage */, WINED3DPOOL_DEFAULT, index_buffer_parent,
+            &ddraw_null_wined3d_parent_ops, &device->indexbuffer);
+    if (FAILED(hr))
+    {
+        ERR("Failed to create an index buffer, hr %#x.\n", hr);
+        HeapFree(GetProcessHeap(), 0, index_buffer_parent);
+        ddraw_handle_table_destroy(&device->handle_table);
+        return hr;
+    }
+    index_buffer_parent->child = (IUnknown *)device->indexbuffer;
+
+    /* This is for convenience. */
+    device->wineD3DDevice = ddraw->wineD3DDevice;
+    IWineD3DDevice_AddRef(ddraw->wineD3DDevice);
+
+    /* Render to the back buffer */
+    hr = IWineD3DDevice_SetRenderTarget(ddraw->wineD3DDevice, 0, target->WineD3DSurface, TRUE);
+    if (FAILED(hr))
+    {
+        ERR("Failed to set render target, hr %#x.\n", hr);
+        IParent_Release((IParent *)index_buffer_parent);
+        ddraw_handle_table_destroy(&device->handle_table);
+        return hr;
+    }
+
+    /* FIXME: This is broken. The target AddRef() makes some sense, because
+     * we store a pointer during initialization, but then that's also where
+     * the AddRef() should be. We don't store ddraw->d3d_target anywhere. */
+    /* AddRef the render target. Also AddRef the render target from ddraw,
+     * because if it is released before the app releases the D3D device, the
+     * D3D capabilities of wined3d will be uninitialized, which has bad effects.
+     *
+     * In most cases, those surfaces are the same anyway, but this will simply
+     * add another ref which is released when the device is destroyed. */
+    IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)target);
+    IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)ddraw->d3d_target);
+
+    ddraw->d3ddevice = device;
+
+    IWineD3DDevice_SetRenderState(ddraw->wineD3DDevice, WINED3DRS_ZENABLE,
+            IDirect3DDeviceImpl_UpdateDepthStencil(device));
+
+    return D3D_OK;
+}
diff --git a/reactos/dll/directx/wine/ddraw/direct3d.c b/reactos/dll/directx/wine/ddraw/direct3d.c
deleted file mode 100644 (file)
index 3f2410f..0000000
+++ /dev/null
@@ -1,1595 +0,0 @@
-/*
- * Copyright (c) 2006 Stefan Dösinger
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "wine/port.h"
-#include "wine/debug.h"
-
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
-#include "ddraw_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d7);
-
-/*****************************************************************************
- * IDirect3D7::QueryInterface
- *
- * QueryInterface implementation with thunks to IDirectDraw7
- *
- *****************************************************************************/
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_7_QueryInterface(IDirect3D7 *iface,
-                                    REFIID refiid,
-                                    void **obj)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d7(iface);
-    TRACE("(%p)->(%s,%p): Thunking to IDirectDraw7\n", This, debugstr_guid(refiid), obj);
-
-    return IDirectDraw7_QueryInterface((IDirectDraw7 *)This, refiid, obj);
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_3_QueryInterface(IDirect3D3 *iface,
-                                    REFIID refiid,
-                                    void **obj)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    TRACE("(%p)->(%s,%p): Thunking to IDirectDraw7\n", This, debugstr_guid(refiid), obj);
-
-    return IDirectDraw7_QueryInterface((IDirectDraw7 *)This, refiid, obj);
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_2_QueryInterface(IDirect3D2 *iface,
-                                    REFIID refiid,
-                                    void **obj)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d2(iface);
-    TRACE("(%p)->(%s,%p): Thunking to IDirectDraw7\n", This, debugstr_guid(refiid), obj);
-
-    return IDirectDraw7_QueryInterface((IDirectDraw7 *)This, refiid, obj);
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_1_QueryInterface(IDirect3D *iface,
-                                    REFIID refiid,
-                                    void **obj)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d1(iface);
-    TRACE("(%p)->(%s,%p): Thunking to IDirectDraw7\n", This, debugstr_guid(refiid), obj);
-
-    return IDirectDraw7_QueryInterface((IDirectDraw7 *)This, refiid, obj);
-}
-
-/*****************************************************************************
- * IDirect3D7::AddRef
- *
- * DirectDraw refcounting is a bit odd. Every version of the ddraw interface
- * has its own refcount, but IDirect3D 1/2/3 refcounts are linked to
- * IDirectDraw, and IDirect3D7 is linked to IDirectDraw7
- *
- * IDirect3D7 -> IDirectDraw7
- * IDirect3D3 -> IDirectDraw
- * IDirect3D2 -> IDirectDraw
- * IDirect3D  -> IDirectDraw
- *
- * So every AddRef implementation thunks to a different interface, and the
- * IDirectDrawX::AddRef implementations have different counters...
- *
- * Returns
- *  The new refcount
- *
- *****************************************************************************/
-static ULONG WINAPI
-Thunk_IDirect3DImpl_7_AddRef(IDirect3D7 *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d7(iface);
-    TRACE("(%p) : Thunking to IDirectDraw7.\n", This);
-
-    return IDirectDraw7_AddRef((IDirectDraw7 *)This);
-}
-
-static ULONG WINAPI
-Thunk_IDirect3DImpl_3_AddRef(IDirect3D3 *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    TRACE("(%p) : Thunking to IDirectDraw.\n", This);
-
-    return IDirectDraw_AddRef((IDirectDraw *)&This->IDirectDraw_vtbl);
-}
-
-static ULONG WINAPI
-Thunk_IDirect3DImpl_2_AddRef(IDirect3D2 *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d2(iface);
-    TRACE("(%p) : Thunking to IDirectDraw.\n", This);
-
-    return IDirectDraw_AddRef((IDirectDraw *)&This->IDirectDraw_vtbl);
-}
-
-static ULONG WINAPI
-Thunk_IDirect3DImpl_1_AddRef(IDirect3D *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d1(iface);
-    TRACE("(%p) : Thunking to IDirectDraw.\n", This);
-
-    return IDirectDraw_AddRef((IDirectDraw *)&This->IDirectDraw_vtbl);
-}
-
-/*****************************************************************************
- * IDirect3D7::Release
- *
- * Same story as IDirect3D7::AddRef
- *
- * Returns: The new refcount
- *
- *****************************************************************************/
-static ULONG WINAPI
-Thunk_IDirect3DImpl_7_Release(IDirect3D7 *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d7(iface);
-    TRACE("(%p) : Thunking to IDirectDraw7.\n", This);
-
-    return IDirectDraw7_Release((IDirectDraw7 *)This);
-}
-
-static ULONG WINAPI
-Thunk_IDirect3DImpl_3_Release(IDirect3D3 *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    TRACE("(%p) : Thunking to IDirectDraw.\n", This);
-
-    return IDirectDraw_Release((IDirectDraw *)&This->IDirectDraw_vtbl);
-}
-
-static ULONG WINAPI
-Thunk_IDirect3DImpl_2_Release(IDirect3D2 *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d2(iface);
-    TRACE("(%p) : Thunking to IDirectDraw.\n", This);
-
-    return IDirectDraw_Release((IDirectDraw *)&This->IDirectDraw_vtbl);
-}
-
-static ULONG WINAPI
-Thunk_IDirect3DImpl_1_Release(IDirect3D *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d1(iface);
-    TRACE("(%p) : Thunking to IDirectDraw.\n", This);
-
-    return IDirectDraw_Release((IDirectDraw *)&This->IDirectDraw_vtbl);
-}
-
-/*****************************************************************************
- * IDirect3D Methods
- *****************************************************************************/
-
-/*****************************************************************************
- * IDirect3D::Initialize
- *
- * Initializes the IDirect3D interface. This is a no-op implementation,
- * as all initialization is done at create time.
- *
- * Version 1
- *
- * Params:
- *  refiid: ?
- *
- * Returns:
- *  D3D_OK, because it's a no-op
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_1_Initialize(IDirect3D *iface,
-                           REFIID refiid)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d1(iface);
-
-    TRACE("(%p)->(%s) no-op...\n", This, debugstr_guid(refiid));
-    return D3D_OK;
-}
-
-/*****************************************************************************
- * IDirect3D7::EnumDevices
- *
- * The EnumDevices method for IDirect3D7. It enumerates all supported
- * D3D7 devices. Currently the T&L, HAL and RGB devices are enumerated.
- *
- * Params:
- *  Callback: Function to call for each enumerated device
- *  Context: Pointer to pass back to the app
- *
- * Returns:
- *  D3D_OK, or the return value of the GetCaps call
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_7_EnumDevices(IDirect3D7 *iface,
-                          LPD3DENUMDEVICESCALLBACK7 Callback,
-                          void *Context)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d7(iface);
-    char interface_name_tnl[] = "WINE Direct3D7 Hardware Transform and Lighting acceleration using WineD3D";
-    char device_name_tnl[] = "Wine D3D7 T&L HAL";
-    char interface_name_hal[] = "WINE Direct3D7 Hardware acceleration using WineD3D";
-    char device_name_hal[] = "Wine D3D7 HAL";
-    char interface_name_rgb[] = "WINE Direct3D7 RGB Software Emulation using WineD3D";
-    char device_name_rgb[] = "Wine D3D7 RGB";
-    D3DDEVICEDESC7 ddesc;
-    D3DDEVICEDESC oldDesc;
-    HRESULT hr;
-
-    TRACE("(%p)->(%p,%p)\n", This, Callback, Context);
-    EnterCriticalSection(&ddraw_cs);
-
-    TRACE("(%p) Enumerating WineD3D D3Device7 interface\n", This);
-    hr = IDirect3DImpl_GetCaps(This->wineD3D, &oldDesc, &ddesc);
-    if(hr != D3D_OK)
-    {
-        LeaveCriticalSection(&ddraw_cs);
-        return hr;
-    }
-    Callback(interface_name_tnl, device_name_tnl, &ddesc, Context);
-
-    ddesc.deviceGUID = IID_IDirect3DHALDevice;
-    Callback(interface_name_hal, device_name_hal, &ddesc, Context);
-
-    ddesc.deviceGUID = IID_IDirect3DRGBDevice;
-    Callback(interface_name_rgb, device_name_rgb, &ddesc, Context);
-
-    TRACE("(%p) End of enumeration\n", This);
-    LeaveCriticalSection(&ddraw_cs);
-    return D3D_OK;
-}
-
-/*****************************************************************************
- * IDirect3D3::EnumDevices
- *
- * Enumerates all supported Direct3DDevice interfaces. This is the
- * implementation for Direct3D 1 to Direc3D 3, Version 7 has its own.
- *
- * Version 1, 2 and 3
- *
- * Params:
- *  Callback: Application-provided routine to call for each enumerated device
- *  Context: Pointer to pass to the callback
- *
- * Returns:
- *  D3D_OK on success,
- *  The result of IDirect3DImpl_GetCaps if it failed
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_3_EnumDevices(IDirect3D3 *iface,
-                            LPD3DENUMDEVICESCALLBACK Callback,
-                            void *Context)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    D3DDEVICEDESC dref, d1, d2;
-    D3DDEVICEDESC7 newDesc;
-    static CHAR wined3d_description[] = "Wine D3DDevice using WineD3D and OpenGL";
-    HRESULT hr;
-
-    /* Some games (Motoracer 2 demo) have the bad idea to modify the device name string.
-       Let's put the string in a sufficiently sized array in writable memory. */
-    char device_name[50];
-    strcpy(device_name,"Direct3D HEL");
-
-    TRACE("(%p)->(%p,%p)\n", This, Callback, Context);
-    EnterCriticalSection(&ddraw_cs);
-
-    hr = IDirect3DImpl_GetCaps(This->wineD3D, &dref, &newDesc);
-    if(hr != D3D_OK)
-    {
-        LeaveCriticalSection(&ddraw_cs);
-        return hr;
-    }
-
-    /* Do I have to enumerate the reference id? Note from old d3d7:
-     * "It seems that enumerating the reference IID on Direct3D 1 games
-     * (AvP / Motoracer2) breaks them". So do not enumerate this iid in V1
-     *
-     * There's a registry key HKLM\Software\Microsoft\Direct3D\Drivers, EnumReference
-     * which enables / disables enumerating the reference rasterizer. It's a DWORD,
-     * 0 means disabled, 2 means enabled. The enablerefrast.reg and disablerefrast.reg
-     * files in the DirectX 7.0 sdk demo directory suggest this.
-     *
-     * Some games(GTA 2) seem to use the second enumerated device, so I have to enumerate
-     * at least 2 devices. So enumerate the reference device to have 2 devices.
-     *
-     * Other games(Rollcage) tell emulation and hal device apart by certain flags.
-     * Rollcage expects D3DPTEXTURECAPS_POW2 to be set(yeah, it is a limitation flag),
-     * and it refuses all devices that have the perspective flag set. This way it refuses
-     * the emulation device, and HAL devices never have POW2 unset in d3d7 on windows.
-     */
-
-    if(This->d3dversion != 1)
-    {
-        static CHAR reference_description[] = "RGB Direct3D emulation";
-
-        TRACE("(%p) Enumerating WineD3D D3DDevice interface\n", This);
-        d1 = dref;
-        d2 = dref;
-        /* The rgb device has the pow2 flag set in the hel caps, but not in the hal caps */
-        d1.dpcLineCaps.dwTextureCaps &= ~(D3DPTEXTURECAPS_POW2 | D3DPTEXTURECAPS_NONPOW2CONDITIONAL | D3DPTEXTURECAPS_PERSPECTIVE);
-        d1.dpcTriCaps.dwTextureCaps &= ~(D3DPTEXTURECAPS_POW2 | D3DPTEXTURECAPS_NONPOW2CONDITIONAL | D3DPTEXTURECAPS_PERSPECTIVE);
-        hr = Callback( (LPIID) &IID_IDirect3DRGBDevice, reference_description, device_name, &d1, &d2, Context);
-        if(hr != D3DENUMRET_OK)
-        {
-            TRACE("Application cancelled the enumeration\n");
-            LeaveCriticalSection(&ddraw_cs);
-            return D3D_OK;
-        }
-    }
-
-    strcpy(device_name,"Direct3D HAL");
-
-    TRACE("(%p) Enumerating HAL Direct3D device\n", This);
-    d1 = dref;
-    d2 = dref;
-    /* The hal device does not have the pow2 flag set in hel, but in hal */
-    d2.dpcLineCaps.dwTextureCaps &= ~(D3DPTEXTURECAPS_POW2 | D3DPTEXTURECAPS_NONPOW2CONDITIONAL | D3DPTEXTURECAPS_PERSPECTIVE);
-    d2.dpcTriCaps.dwTextureCaps &= ~(D3DPTEXTURECAPS_POW2 | D3DPTEXTURECAPS_NONPOW2CONDITIONAL | D3DPTEXTURECAPS_PERSPECTIVE);
-    hr = Callback( (LPIID) &IID_IDirect3DHALDevice, wined3d_description, device_name, &d1, &d2, Context);
-    if(hr != D3DENUMRET_OK)
-    {
-        TRACE("Application cancelled the enumeration\n");
-        LeaveCriticalSection(&ddraw_cs);
-        return D3D_OK;
-    }
-    TRACE("(%p) End of enumeration\n", This);
-
-    LeaveCriticalSection(&ddraw_cs);
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_2_EnumDevices(IDirect3D2 *iface,
-                                  LPD3DENUMDEVICESCALLBACK Callback,
-                                  void *Context)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d2(iface);
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", This, Callback, Context);
-    return IDirect3D3_EnumDevices((IDirect3D3 *)&This->IDirect3D3_vtbl, Callback, Context);
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_1_EnumDevices(IDirect3D *iface,
-                                  LPD3DENUMDEVICESCALLBACK Callback,
-                                  void *Context)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d1(iface);
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", This, Callback, Context);
-    return IDirect3D3_EnumDevices((IDirect3D3 *)&This->IDirect3D3_vtbl, Callback, Context);
-}
-
-/*****************************************************************************
- * IDirect3D3::CreateLight
- *
- * Creates an IDirect3DLight interface. This interface is used in
- * Direct3D3 or earlier for lighting. In Direct3D7 it has been replaced
- * by the DIRECT3DLIGHT7 structure. Wine's Direct3DLight implementation
- * uses the IDirect3DDevice7 interface with D3D7 lights.
- *
- * Version 1, 2 and 3
- *
- * Params:
- *  Light: Address to store the new interface pointer
- *  UnkOuter: Basically for aggregation, but ddraw doesn't support it.
- *            Must be NULL
- *
- * Returns:
- *  D3D_OK on success
- *  DDERR_OUTOFMEMORY if memory allocation failed
- *  CLASS_E_NOAGGREGATION if UnkOuter != NULL
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_3_CreateLight(IDirect3D3 *iface,
-                            IDirect3DLight **Light,
-                            IUnknown *UnkOuter )
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    IDirect3DLightImpl *object;
-
-    TRACE("(%p)->(%p,%p)\n", This, Light, UnkOuter);
-
-    if(UnkOuter)
-        return CLASS_E_NOAGGREGATION;
-
-    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IDirect3DLightImpl));
-    if (object == NULL)
-        return DDERR_OUTOFMEMORY;
-
-    object->lpVtbl = &IDirect3DLight_Vtbl;
-    object->ref = 1;
-    object->ddraw = This;
-    object->next = NULL;
-    object->active_viewport = NULL;
-
-    /* Update functions */
-    object->activate = light_update;
-    object->desactivate = light_activate;
-    object->update = light_desactivate;
-    object->active_viewport = NULL;
-
-    *Light = (IDirect3DLight *)object;
-
-    TRACE("(%p) creating implementation at %p.\n", This, object);
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_2_CreateLight(IDirect3D2 *iface,
-                                  IDirect3DLight **Direct3DLight,
-                                  IUnknown *UnkOuter)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d2(iface);
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", This, Direct3DLight, UnkOuter);
-    return IDirect3D3_CreateLight((IDirect3D3 *)&This->IDirect3D3_vtbl, Direct3DLight, UnkOuter);
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_1_CreateLight(IDirect3D *iface,
-                                  IDirect3DLight **Direct3DLight,
-                                  IUnknown *UnkOuter)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d1(iface);
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", This, Direct3DLight, UnkOuter);
-    return IDirect3D3_CreateLight((IDirect3D3 *)&This->IDirect3D3_vtbl, Direct3DLight, UnkOuter);
-}
-
-/*****************************************************************************
- * IDirect3D3::CreateMaterial
- *
- * Creates an IDirect3DMaterial interface. This interface is used by Direct3D3
- * and older versions. The IDirect3DMaterial implementation wraps its
- * functionality to IDirect3DDevice7::SetMaterial and friends.
- *
- * Version 1, 2 and 3
- *
- * Params:
- *  Material: Address to store the new interface's pointer to
- *  UnkOuter: Basically for aggregation, but ddraw doesn't support it.
- *            Must be NULL
- *
- * Returns:
- *  D3D_OK on success
- *  DDERR_OUTOFMEMORY if memory allocation failed
- *  CLASS_E_NOAGGREGATION if UnkOuter != NULL
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_3_CreateMaterial(IDirect3D3 *iface,
-                               IDirect3DMaterial3 **Material,
-                               IUnknown *UnkOuter )
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    IDirect3DMaterialImpl *object;
-
-    TRACE("(%p)->(%p,%p)\n", This, Material, UnkOuter);
-
-    if(UnkOuter)
-        return CLASS_E_NOAGGREGATION;
-
-    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IDirect3DMaterialImpl));
-    if (object == NULL)
-        return DDERR_OUTOFMEMORY;
-
-    object->lpVtbl = &IDirect3DMaterial3_Vtbl;
-    object->IDirect3DMaterial2_vtbl = &IDirect3DMaterial2_Vtbl;
-    object->IDirect3DMaterial_vtbl = &IDirect3DMaterial_Vtbl;
-    object->ref = 1;
-    object->ddraw = This;
-    object->activate = material_activate;
-
-    *Material = (IDirect3DMaterial3 *)object;
-
-    TRACE("(%p) creating implementation at %p.\n", This, object);
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_2_CreateMaterial(IDirect3D2 *iface,
-                                     IDirect3DMaterial2 **Direct3DMaterial,
-                                     IUnknown* UnkOuter)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d2(iface);
-    HRESULT ret;
-    IDirect3DMaterial3 *ret_val;
-
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", This, Direct3DMaterial, UnkOuter);
-    ret = IDirect3D3_CreateMaterial((IDirect3D3 *)&This->IDirect3D3_vtbl, &ret_val, UnkOuter);
-
-    *Direct3DMaterial = ret_val ?
-            (IDirect3DMaterial2 *)&((IDirect3DMaterialImpl *)ret_val)->IDirect3DMaterial2_vtbl : NULL;
-
-    TRACE(" returning interface %p.\n", *Direct3DMaterial);
-
-    return ret;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_1_CreateMaterial(IDirect3D *iface,
-                                     IDirect3DMaterial **Direct3DMaterial,
-                                     IUnknown* UnkOuter)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d1(iface);
-    HRESULT ret;
-    LPDIRECT3DMATERIAL3 ret_val;
-
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", This, Direct3DMaterial, UnkOuter);
-    ret = IDirect3D3_CreateMaterial((IDirect3D3 *)&This->IDirect3D3_vtbl, &ret_val, UnkOuter);
-
-    *Direct3DMaterial = ret_val ?
-            (IDirect3DMaterial *)&((IDirect3DMaterialImpl *)ret_val)->IDirect3DMaterial_vtbl : NULL;
-
-    TRACE(" returning interface %p.\n", *Direct3DMaterial);
-
-    return ret;
-}
-
-/*****************************************************************************
- * IDirect3D3::CreateViewport
- *
- * Creates an IDirect3DViewport interface. This interface is used
- * by Direct3D and earlier versions for Viewport management. In Direct3D7
- * it has been replaced by a viewport structure and
- * IDirect3DDevice7::*Viewport. Wine's IDirect3DViewport implementation
- * uses the IDirect3DDevice7 methods for its functionality
- *
- * Params:
- *  Viewport: Address to store the new interface pointer
- *  UnkOuter: Basically for aggregation, but ddraw doesn't support it.
- *            Must be NULL
- *
- * Returns:
- *  D3D_OK on success
- *  DDERR_OUTOFMEMORY if memory allocation failed
- *  CLASS_E_NOAGGREGATION if UnkOuter != NULL
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_3_CreateViewport(IDirect3D3 *iface,
-                              IDirect3DViewport3 **Viewport,
-                              IUnknown *UnkOuter )
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    IDirect3DViewportImpl *object;
-
-    if(UnkOuter)
-        return CLASS_E_NOAGGREGATION;
-
-    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IDirect3DViewportImpl));
-    if (object == NULL)
-        return DDERR_OUTOFMEMORY;
-
-    object->lpVtbl = &IDirect3DViewport3_Vtbl;
-    object->ref = 1;
-    object->ddraw = This;
-    object->activate = viewport_activate;
-    object->use_vp2 = 0xFF;
-    object->next = NULL;
-    object->lights = NULL;
-    object->num_lights = 0;
-    object->map_lights = 0;
-
-    *Viewport = (IDirect3DViewport3 *)object;
-
-    TRACE("(%p) creating implementation at %p.\n",This, object);
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_2_CreateViewport(IDirect3D2 *iface,
-                                     IDirect3DViewport2 **D3DViewport2,
-                                     IUnknown *UnkOuter)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d2(iface);
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", This, D3DViewport2, UnkOuter);
-
-    return IDirect3D3_CreateViewport((IDirect3D3 *)&This->IDirect3D3_vtbl,
-                                     (IDirect3DViewport3 **) D3DViewport2 /* No need to cast here */,
-                                     UnkOuter);
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_1_CreateViewport(IDirect3D *iface,
-                                     IDirect3DViewport **D3DViewport,
-                                     IUnknown* UnkOuter)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d1(iface);
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", This, D3DViewport, UnkOuter);
-
-    return IDirect3D3_CreateViewport((IDirect3D3 *)&This->IDirect3D3_vtbl,
-                                     (IDirect3DViewport3 **) D3DViewport /* No need to cast here */,
-                                     UnkOuter);
-}
-
-/*****************************************************************************
- * IDirect3D3::FindDevice
- *
- * This method finds a device with the requested properties and returns a
- * device description
- *
- * Verion 1, 2 and 3
- * Params:
- *  D3DDFS: Describes the requested device characteristics
- *  D3DFDR: Returns the device description
- *
- * Returns:
- *  D3D_OK on success
- *  DDERR_INVALIDPARAMS if no device was found
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_3_FindDevice(IDirect3D3 *iface,
-                           D3DFINDDEVICESEARCH *D3DDFS,
-                           D3DFINDDEVICERESULT *D3DFDR)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    D3DDEVICEDESC desc;
-    D3DDEVICEDESC7 newDesc;
-    HRESULT hr;
-
-    TRACE("(%p)->(%p,%p)\n", This, D3DDFS, D3DFDR);
-
-    if ((D3DDFS->dwFlags & D3DFDS_COLORMODEL) &&
-        (D3DDFS->dcmColorModel != D3DCOLOR_RGB))
-    {
-        TRACE(" trying to request a non-RGB D3D color model. Not supported.\n");
-        return DDERR_INVALIDPARAMS; /* No real idea what to return here :-) */
-    }
-    if (D3DDFS->dwFlags & D3DFDS_GUID)
-    {
-        TRACE(" trying to match guid %s.\n", debugstr_guid(&(D3DDFS->guid)));
-        if ((IsEqualGUID(&IID_D3DDEVICE_WineD3D, &(D3DDFS->guid)) == 0) &&
-            (IsEqualGUID(&IID_IDirect3DHALDevice, &(D3DDFS->guid)) == 0) &&
-            (IsEqualGUID(&IID_IDirect3DRefDevice, &(D3DDFS->guid)) == 0))
-        {
-            TRACE(" no match for this GUID.\n");
-            return DDERR_INVALIDPARAMS;
-        }
-    }
-
-    /* Get the caps */
-    hr = IDirect3DImpl_GetCaps(This->wineD3D, &desc, &newDesc);
-    if(hr != D3D_OK) return hr;
-
-    /* Now return our own GUID */
-    D3DFDR->guid = IID_D3DDEVICE_WineD3D;
-    D3DFDR->ddHwDesc = desc;
-    D3DFDR->ddSwDesc = desc;
-
-    TRACE(" returning Wine's WineD3D device with (undumped) capabilities\n");
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_2_FindDevice(IDirect3D2 *iface,
-                                 D3DFINDDEVICESEARCH *D3DDFS,
-                                 D3DFINDDEVICERESULT *D3DFDR)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d2(iface);
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", iface, D3DDFS, D3DFDR);
-    return IDirect3D3_FindDevice((IDirect3D3 *)&This->IDirect3D3_vtbl, D3DDFS, D3DFDR);
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_1_FindDevice(IDirect3D *iface,
-                                D3DFINDDEVICESEARCH *D3DDFS,
-                                D3DFINDDEVICERESULT *D3DDevice)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d1(iface);
-    TRACE("(%p)->(%p,%p) thunking to IDirect3D3 interface.\n", This, D3DDFS, D3DDevice);
-    return IDirect3D3_FindDevice((IDirect3D3 *)&This->IDirect3D3_vtbl, D3DDFS, D3DDevice);
-}
-
-/*****************************************************************************
- * IDirect3D7::CreateDevice
- *
- * Creates an IDirect3DDevice7 interface.
- *
- * Version 2, 3 and 7. IDirect3DDevice 1 interfaces are interfaces to
- * DirectDraw surfaces and are created with
- * IDirectDrawSurface::QueryInterface. This method uses CreateDevice to
- * create the device object and QueryInterfaces for IDirect3DDevice
- *
- * Params:
- *  refiid: IID of the device to create
- *  Surface: Initial rendertarget
- *  Device: Address to return the interface pointer
- *
- * Returns:
- *  D3D_OK on success
- *  DDERR_OUTOFMEMORY if memory allocation failed
- *  DDERR_INVALIDPARAMS if a device exists already
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_7_CreateDevice(IDirect3D7 *iface,
-                             REFCLSID refiid,
-                             IDirectDrawSurface7 *Surface,
-                             IDirect3DDevice7 **Device)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d7(iface);
-    IDirect3DDeviceImpl *object;
-    IParentImpl *IndexBufferParent;
-    HRESULT hr;
-    IDirectDrawSurfaceImpl *target = (IDirectDrawSurfaceImpl *)Surface;
-    TRACE("(%p)->(%s,%p,%p)\n", iface, debugstr_guid(refiid), Surface, Device);
-
-    EnterCriticalSection(&ddraw_cs);
-    *Device = NULL;
-
-    /* Fail device creation if non-opengl surfaces are used */
-    if(This->ImplType != SURFACE_OPENGL)
-    {
-        ERR("The application wants to create a Direct3D device, but non-opengl surfaces are set in the registry. Please set the surface implementation to opengl or autodetection to allow 3D rendering\n");
-
-        /* We only hit this path if a default surface is set in the registry. Incorrect autodetection
-         * is caught in CreateSurface or QueryInterface
-         */
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_NO3D;
-    }
-
-    /* So far we can only create one device per ddraw object */
-    if(This->d3ddevice)
-    {
-        FIXME("(%p): Only one Direct3D device per DirectDraw object supported\n", This);
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_INVALIDPARAMS;
-    }
-
-    object = HeapAlloc(GetProcessHeap(), 0, sizeof(IDirect3DDeviceImpl));
-    if(!object)
-    {
-        ERR("Out of memory when allocating a IDirect3DDevice implementation\n");
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_OUTOFMEMORY;
-    }
-
-    if (This->cooperative_level & DDSCL_FPUPRESERVE)
-        object->lpVtbl = &IDirect3DDevice7_FPUPreserve_Vtbl;
-    else
-        object->lpVtbl = &IDirect3DDevice7_FPUSetup_Vtbl;
-
-    object->IDirect3DDevice3_vtbl = &IDirect3DDevice3_Vtbl;
-    object->IDirect3DDevice2_vtbl = &IDirect3DDevice2_Vtbl;
-    object->IDirect3DDevice_vtbl = &IDirect3DDevice1_Vtbl;
-    object->ref = 1;
-    object->ddraw = This;
-    object->viewport_list = NULL;
-    object->current_viewport = NULL;
-    object->material = 0;
-    object->target = target;
-
-    object->Handles = NULL;
-    object->numHandles = 0;
-
-    object->legacyTextureBlending = FALSE;
-
-    /* This is for convenience */
-    object->wineD3DDevice = This->wineD3DDevice;
-
-    /* Create an index buffer, it's needed for indexed drawing */
-    IndexBufferParent = HeapAlloc(GetProcessHeap(), 0, sizeof(IParentImpl));
-    if(!IndexBufferParent)
-    {
-        ERR("Allocating memory for an index buffer parent failed\n");
-        HeapFree(GetProcessHeap(), 0, object);
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_OUTOFMEMORY;
-    }
-    IndexBufferParent->lpVtbl = &IParent_Vtbl;
-    IndexBufferParent->ref = 1;
-
-    /* Create an Index Buffer. WineD3D needs one for Drawing indexed primitives
-     * Create a (hopefully) long enough buffer, and copy the indices into it
-     * Ideally, a IWineD3DBuffer::SetData method could be created, which
-     * takes the pointer and avoids the memcpy
-     */
-    hr = IWineD3DDevice_CreateIndexBuffer(This->wineD3DDevice, 0x40000 /* Length. Don't know how long it should be */,
-            WINED3DUSAGE_DYNAMIC /* Usage */, WINED3DPOOL_DEFAULT, &object->indexbuffer, (IUnknown *)IndexBufferParent,
-            &ddraw_null_wined3d_parent_ops);
-
-    if(FAILED(hr))
-    {
-        ERR("Failed to create an index buffer\n");
-        HeapFree(GetProcessHeap(), 0, object);
-        LeaveCriticalSection(&ddraw_cs);
-        return hr;
-    }
-    IndexBufferParent->child = (IUnknown *) object->indexbuffer;
-
-    /* No need to set the indices, it's done when necessary */
-
-    /* AddRef the WineD3D Device */
-    IWineD3DDevice_AddRef(This->wineD3DDevice);
-
-    /* Don't forget to return the interface ;) */
-    *Device = (IDirect3DDevice7 *)object;
-
-    TRACE(" (%p) Created an IDirect3DDeviceImpl object at %p\n", This, object);
-
-    /* This is for apps which create a non-flip, non-d3d primary surface
-     * and an offscreen D3DDEVICE surface, then render to the offscreen surface
-     * and do a Blt from the offscreen to the primary surface.
-     *
-     * Set the offscreen D3DDDEVICE surface(=target) as the back buffer,
-     * and the primary surface(=This->d3d_target) as the front buffer.
-     *
-     * This way the app will render to the D3DDEVICE surface and WineD3D
-     * will catch the Blt was Back Buffer -> Front buffer blt and perform
-     * a flip instead. This way we don't have to deal with a mixed GL / GDI
-     * environment.
-     *
-     * This should be checked against windowed apps. The only app tested with
-     * this is moto racer 2 during the loading screen.
-     */
-    TRACE("Isrendertarget: %s, d3d_target=%p\n", target->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE ? "true" : "false", This->d3d_target);
-    if(!(target->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) &&
-       (This->d3d_target != target))
-    {
-        TRACE("(%p) Using %p as front buffer, %p as back buffer\n", This, This->d3d_target, target);
-        hr = IWineD3DDevice_SetFrontBackBuffers(This->wineD3DDevice,
-                                                This->d3d_target->WineD3DSurface,
-                                                target->WineD3DSurface);
-        if(hr != D3D_OK)
-            ERR("(%p) Error %08x setting the front and back buffer\n", This, hr);
-
-        /* Render to the back buffer */
-        IWineD3DDevice_SetRenderTarget(This->wineD3DDevice, 0,
-                                       target->WineD3DSurface,
-                                       TRUE);
-        object->OffScreenTarget = TRUE;
-    }
-    else
-    {
-        object->OffScreenTarget = FALSE;
-    }
-
-    /* AddRef the render target. Also AddRef the render target from ddraw,
-     * because if it is released before the app releases the D3D device, the D3D capabilities
-     * of WineD3D will be uninitialized, which has bad effects.
-     *
-     * In most cases, those surfaces are the surfaces are the same anyway, but this will simply
-     * add another ref which is released when the device is destroyed.
-     */
-    IDirectDrawSurface7_AddRef(Surface);
-    IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)This->d3d_target);
-
-    This->d3ddevice = object;
-
-    IWineD3DDevice_SetRenderState(This->wineD3DDevice,
-                                  WINED3DRS_ZENABLE,
-                                  IDirect3DDeviceImpl_UpdateDepthStencil(object));
-    LeaveCriticalSection(&ddraw_cs);
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_3_CreateDevice(IDirect3D3 *iface,
-                                   REFCLSID refiid,
-                                   IDirectDrawSurface4 *Surface,
-                                   IDirect3DDevice3 **Device,
-                                   IUnknown *UnkOuter)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    HRESULT hr;
-    TRACE("(%p)->(%s,%p,%p,%p): Thunking to IDirect3D7\n", This, debugstr_guid(refiid), Surface, Device, UnkOuter);
-
-    if(UnkOuter != NULL)
-        return CLASS_E_NOAGGREGATION;
-
-    hr =  IDirect3D7_CreateDevice((IDirect3D7 *)&This->IDirect3D7_vtbl, refiid,
-            (IDirectDrawSurface7 *)Surface /* Same VTables */, (IDirect3DDevice7 **)Device);
-
-    *Device = *Device ? (IDirect3DDevice3 *)&((IDirect3DDeviceImpl *)*Device)->IDirect3DDevice3_vtbl : NULL;
-    return hr;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_2_CreateDevice(IDirect3D2 *iface,
-                                   REFCLSID refiid,
-                                   IDirectDrawSurface *Surface,
-                                   IDirect3DDevice2 **Device)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d2(iface);
-    HRESULT hr;
-    TRACE("(%p)->(%s,%p,%p): Thunking to IDirect3D7\n", This, debugstr_guid(refiid), Surface, Device);
-
-    hr =  IDirect3D7_CreateDevice((IDirect3D7 *)&This->IDirect3D7_vtbl, refiid,
-            Surface ? (IDirectDrawSurface7 *)surface_from_surface3((IDirectDrawSurface3 *)Surface) : NULL,
-            (IDirect3DDevice7 **)Device);
-
-    *Device = *Device ? (IDirect3DDevice2 *)&((IDirect3DDeviceImpl *)*Device)->IDirect3DDevice2_vtbl : NULL;
-    return hr;
-}
-
-/*****************************************************************************
- * IDirect3D7::CreateVertexBuffer
- *
- * Creates a new vertex buffer object and returns a IDirect3DVertexBuffer7
- * interface.
- *
- * Version 3 and 7
- *
- * Params:
- *  Desc: Requested Vertex buffer properties
- *  VertexBuffer: Address to return the interface pointer at
- *  Flags: Some flags, must be 0
- *
- * Returns
- *  D3D_OK on success
- *  DDERR_OUTOFMEMORY if memory allocation failed
- *  The return value of IWineD3DDevice::CreateVertexBuffer if this call fails
- *  DDERR_INVALIDPARAMS if Desc or VertexBuffer are NULL, or Flags != 0
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_7_CreateVertexBuffer(IDirect3D7 *iface,
-                                   D3DVERTEXBUFFERDESC *Desc,
-                                   IDirect3DVertexBuffer7 **VertexBuffer,
-                                   DWORD Flags)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d7(iface);
-    IDirect3DVertexBufferImpl *object;
-    HRESULT hr;
-    DWORD usage;
-    TRACE("(%p)->(%p,%p,%08x)\n", This, Desc, VertexBuffer, Flags);
-
-    TRACE("(%p) Vertex buffer description:\n", This);
-    TRACE("(%p)  dwSize=%d\n", This, Desc->dwSize);
-    TRACE("(%p)  dwCaps=%08x\n", This, Desc->dwCaps);
-    TRACE("(%p)  FVF=%08x\n", This, Desc->dwFVF);
-    TRACE("(%p)  dwNumVertices=%d\n", This, Desc->dwNumVertices);
-
-    /* D3D7 SDK: "No Flags are currently defined for this method. This
-     * parameter must be 0"
-     *
-     * Never trust the documentation - this is wrong
-    if(Flags != 0)
-    {
-        ERR("(%p) Flags is %08lx, returning DDERR_INVALIDPARAMS\n", This, Flags);
-        return DDERR_INVALIDPARAMS;
-    }
-     */
-
-    /* Well, this sounds sane */
-    if( (!VertexBuffer) || (!Desc) )
-        return DDERR_INVALIDPARAMS;
-
-    /* Now create the vertex buffer */
-    object = HeapAlloc(GetProcessHeap(), 0, sizeof(IDirect3DVertexBufferImpl));
-    if(!object)
-    {
-        ERR("(%p) Out of memory when allocating a IDirect3DVertexBufferImpl structure\n", This);
-        return DDERR_OUTOFMEMORY;
-    }
-
-    object->ref = 1;
-    object->lpVtbl = &IDirect3DVertexBuffer7_Vtbl;
-    object->IDirect3DVertexBuffer_vtbl = &IDirect3DVertexBuffer1_Vtbl;
-
-    object->Caps = Desc->dwCaps;
-    object->ddraw = This;
-    object->fvf = Desc->dwFVF;
-
-    usage = Desc->dwCaps & D3DVBCAPS_WRITEONLY ? WINED3DUSAGE_WRITEONLY : 0;
-    usage |= WINED3DUSAGE_STATICDECL;
-
-    EnterCriticalSection(&ddraw_cs);
-    hr = IWineD3DDevice_CreateVertexBuffer(This->wineD3DDevice,
-            get_flexible_vertex_size(Desc->dwFVF) * Desc->dwNumVertices,
-            usage, Desc->dwCaps & D3DVBCAPS_SYSTEMMEMORY ? WINED3DPOOL_SYSTEMMEM : WINED3DPOOL_DEFAULT,
-            &object->wineD3DVertexBuffer, (IUnknown *)object, &ddraw_null_wined3d_parent_ops);
-    if(hr != D3D_OK)
-    {
-        ERR("(%p) IWineD3DDevice::CreateVertexBuffer failed with hr=%08x\n", This, hr);
-        HeapFree(GetProcessHeap(), 0, object);
-        LeaveCriticalSection(&ddraw_cs);
-        if (hr == WINED3DERR_INVALIDCALL)
-            return DDERR_INVALIDPARAMS;
-        else
-            return hr;
-    }
-
-    object->wineD3DVertexDeclaration = IDirectDrawImpl_FindDecl(This,
-                                                                Desc->dwFVF);
-    if(!object->wineD3DVertexDeclaration)
-    {
-        ERR("Cannot find the vertex declaration for fvf %08x\n", Desc->dwFVF);
-        IWineD3DBuffer_Release(object->wineD3DVertexBuffer);
-        HeapFree(GetProcessHeap(), 0, object);
-        LeaveCriticalSection(&ddraw_cs);
-        return DDERR_INVALIDPARAMS;
-    }
-    IWineD3DVertexDeclaration_AddRef(object->wineD3DVertexDeclaration);
-
-    /* Return the interface */
-    *VertexBuffer = (IDirect3DVertexBuffer7 *)object;
-
-    TRACE("(%p) Created new vertex buffer implementation at %p, returning interface at %p\n", This, object, *VertexBuffer);
-    LeaveCriticalSection(&ddraw_cs);
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_3_CreateVertexBuffer(IDirect3D3 *iface,
-                                         D3DVERTEXBUFFERDESC *Desc,
-                                         IDirect3DVertexBuffer **VertexBuffer,
-                                         DWORD Flags,
-                                         IUnknown *UnkOuter)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    HRESULT hr;
-    TRACE("(%p)->(%p,%p,%08x,%p): Relaying to IDirect3D7\n", This, Desc, VertexBuffer, Flags, UnkOuter);
-
-    if(UnkOuter != NULL) return CLASS_E_NOAGGREGATION;
-
-    hr = IDirect3D7_CreateVertexBuffer((IDirect3D7 *)&This->IDirect3D7_vtbl,
-            Desc, (IDirect3DVertexBuffer7 **)VertexBuffer, Flags);
-
-    *VertexBuffer = *VertexBuffer ?
-            (IDirect3DVertexBuffer *)&((IDirect3DVertexBufferImpl *)*VertexBuffer)->IDirect3DVertexBuffer_vtbl : NULL;
-
-    return hr;
-}
-
-
-/*****************************************************************************
- * IDirect3D7::EnumZBufferFormats
- *
- * Enumerates all supported Z buffer pixel formats
- *
- * Version 3 and 7
- *
- * Params:
- *  refiidDevice:
- *  Callback: Callback to call for each pixel format
- *  Context: Pointer to pass back to the callback
- *
- * Returns:
- *  D3D_OK on success
- *  DDERR_INVALIDPARAMS if Callback is NULL
- *  For details, see IWineD3DDevice::EnumZBufferFormats
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_7_EnumZBufferFormats(IDirect3D7 *iface,
-                                   REFCLSID refiidDevice,
-                                   LPD3DENUMPIXELFORMATSCALLBACK Callback,
-                                   void *Context)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d7(iface);
-    HRESULT hr;
-    unsigned int i;
-    WINED3DDISPLAYMODE d3ddm;
-    WINED3DDEVTYPE type;
-
-    /* Order matters. Specifically, BattleZone II (full version) expects the
-     * 16-bit depth formats to be listed before the 24 and 32 ones. */
-    WINED3DFORMAT FormatList[] = {
-        WINED3DFMT_S1_UINT_D15_UNORM,
-        WINED3DFMT_D16_UNORM,
-        WINED3DFMT_X8D24_UNORM,
-        WINED3DFMT_S4X4_UINT_D24_UNORM,
-        WINED3DFMT_D24_UNORM_S8_UINT,
-        WINED3DFMT_D32_UNORM,
-    };
-
-    TRACE("(%p)->(%s,%p,%p): Relay\n", iface, debugstr_guid(refiidDevice), Callback, Context);
-
-    if(!Callback)
-        return DDERR_INVALIDPARAMS;
-
-    if(IsEqualGUID(refiidDevice, &IID_IDirect3DHALDevice)    ||
-       IsEqualGUID(refiidDevice, &IID_IDirect3DTnLHalDevice) ||
-       IsEqualGUID(refiidDevice, &IID_D3DDEVICE_WineD3D))
-    {
-        TRACE("Asked for HAL device\n");
-        type = WINED3DDEVTYPE_HAL;
-    }
-    else if(IsEqualGUID(refiidDevice, &IID_IDirect3DRGBDevice) ||
-            IsEqualGUID(refiidDevice, &IID_IDirect3DMMXDevice))
-    {
-        TRACE("Asked for SW device\n");
-        type = WINED3DDEVTYPE_SW;
-    }
-    else if(IsEqualGUID(refiidDevice, &IID_IDirect3DRefDevice))
-    {
-        TRACE("Asked for REF device\n");
-        type = WINED3DDEVTYPE_REF;
-    }
-    else if(IsEqualGUID(refiidDevice, &IID_IDirect3DNullDevice))
-    {
-        TRACE("Asked for NULLREF device\n");
-        type = WINED3DDEVTYPE_NULLREF;
-    }
-    else
-    {
-        FIXME("Unexpected device GUID %s\n", debugstr_guid(refiidDevice));
-        type = WINED3DDEVTYPE_HAL;
-    }
-
-    EnterCriticalSection(&ddraw_cs);
-    /* We need an adapter format from somewhere to please wined3d and WGL. Use the current display mode.
-     * So far all cards offer the same depth stencil format for all modes, but if some do not and apps
-     * do not like that we'll have to find some workaround, like iterating over all imaginable formats
-     * and collecting all the depth stencil formats we can get
-     */
-    hr = IWineD3DDevice_GetDisplayMode(This->wineD3DDevice,
-                                       0 /* swapchain 0 */,
-                                       &d3ddm);
-
-    for(i = 0; i < (sizeof(FormatList) / sizeof(FormatList[0])); i++)
-    {
-        hr = IWineD3D_CheckDeviceFormat(This->wineD3D,
-                                        WINED3DADAPTER_DEFAULT /* Adapter */,
-                                        type /* DeviceType */,
-                                        d3ddm.Format /* AdapterFormat */,
-                                        WINED3DUSAGE_DEPTHSTENCIL /* Usage */,
-                                        WINED3DRTYPE_SURFACE,
-                                        FormatList[i],
-                                        SURFACE_OPENGL);
-        if(hr == D3D_OK)
-        {
-            DDPIXELFORMAT pformat;
-
-            memset(&pformat, 0, sizeof(pformat));
-            pformat.dwSize = sizeof(pformat);
-            PixelFormat_WineD3DtoDD(&pformat, FormatList[i]);
-
-            TRACE("Enumerating WineD3DFormat %d\n", FormatList[i]);
-            hr = Callback(&pformat, Context);
-            if(hr != DDENUMRET_OK)
-            {
-                TRACE("Format enumeration cancelled by application\n");
-                LeaveCriticalSection(&ddraw_cs);
-                return D3D_OK;
-            }
-        }
-    }
-    TRACE("End of enumeration\n");
-    LeaveCriticalSection(&ddraw_cs);
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_3_EnumZBufferFormats(IDirect3D3 *iface,
-                                         REFCLSID riidDevice,
-                                         LPD3DENUMPIXELFORMATSCALLBACK Callback,
-                                         void *Context)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    TRACE("(%p)->(%s,%p,%p) thunking to IDirect3D7 interface.\n", This, debugstr_guid(riidDevice), Callback, Context);
-    return IDirect3D7_EnumZBufferFormats((IDirect3D7 *)&This->IDirect3D7_vtbl, riidDevice, Callback, Context);
-}
-
-/*****************************************************************************
- * IDirect3D7::EvictManagedTextures
- *
- * Removes all managed textures (=surfaces with DDSCAPS2_TEXTUREMANAGE or
- * DDSCAPS2_D3DTEXTUREMANAGE caps) to be removed from video memory.
- *
- * Version 3 and 7
- *
- * Returns:
- *  D3D_OK, because it's a stub
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DImpl_7_EvictManagedTextures(IDirect3D7 *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d7(iface);
-    FIXME("(%p): Stub!\n", This);
-
-    /* Implementation idea:
-     * Add an IWineD3DSurface method which sets the opengl texture
-     * priority low or even removes the opengl texture.
-     */
-
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DImpl_3_EvictManagedTextures(IDirect3D3 *iface)
-{
-    IDirectDrawImpl *This = ddraw_from_d3d3(iface);
-    TRACE("(%p)->() thunking to IDirect3D7 interface.\n", This);
-    return IDirect3D7_EvictManagedTextures((IDirect3D7 *)&This->IDirect3D7_vtbl);
-}
-
-/*****************************************************************************
- * IDirect3DImpl_GetCaps
- *
- * This function retrieves the device caps from wined3d
- * and converts it into a D3D7 and D3D - D3D3 structure
- * This is a helper function called from various places in ddraw
- *
- * Params:
- *  WineD3D: The interface to get the caps from
- *  Desc123: Old D3D <3 structure to fill (needed)
- *  Desc7: D3D7 device desc structure to fill (needed)
- *
- * Returns
- *  D3D_OK on success, or the return value of IWineD3D::GetCaps
- *
- *****************************************************************************/
-HRESULT
-IDirect3DImpl_GetCaps(IWineD3D *WineD3D,
-                      D3DDEVICEDESC *Desc123,
-                      D3DDEVICEDESC7 *Desc7)
-{
-    WINED3DCAPS WCaps;
-    HRESULT hr;
-
-    /* Some variables to assign to the pointers in WCaps */
-    TRACE("()->(%p,%p,%p\n", WineD3D, Desc123, Desc7);
-
-    memset(&WCaps, 0, sizeof(WCaps));
-    EnterCriticalSection(&ddraw_cs);
-    hr = IWineD3D_GetDeviceCaps(WineD3D, 0, WINED3DDEVTYPE_HAL, &WCaps);
-    LeaveCriticalSection(&ddraw_cs);
-    if(hr != D3D_OK)
-    {
-        return hr;
-    }
-
-    /* Copy the results into the d3d7 and d3d3 structures */
-    Desc7->dwDevCaps = WCaps.DevCaps;
-    Desc7->dpcLineCaps.dwMiscCaps = WCaps.PrimitiveMiscCaps;
-    Desc7->dpcLineCaps.dwRasterCaps = WCaps.RasterCaps;
-    Desc7->dpcLineCaps.dwZCmpCaps = WCaps.ZCmpCaps;
-    Desc7->dpcLineCaps.dwSrcBlendCaps = WCaps.SrcBlendCaps;
-    Desc7->dpcLineCaps.dwDestBlendCaps = WCaps.DestBlendCaps;
-    Desc7->dpcLineCaps.dwAlphaCmpCaps = WCaps.AlphaCmpCaps;
-    Desc7->dpcLineCaps.dwShadeCaps = WCaps.ShadeCaps;
-    Desc7->dpcLineCaps.dwTextureCaps = WCaps.TextureCaps;
-    Desc7->dpcLineCaps.dwTextureFilterCaps = WCaps.TextureFilterCaps;
-    Desc7->dpcLineCaps.dwTextureAddressCaps = WCaps.TextureAddressCaps;
-
-    Desc7->dwMaxTextureWidth = WCaps.MaxTextureWidth;
-    Desc7->dwMaxTextureHeight = WCaps.MaxTextureHeight;
-
-    Desc7->dwMaxTextureRepeat = WCaps.MaxTextureRepeat;
-    Desc7->dwMaxTextureAspectRatio = WCaps.MaxTextureAspectRatio;
-    Desc7->dwMaxAnisotropy = WCaps.MaxAnisotropy;
-    Desc7->dvMaxVertexW = WCaps.MaxVertexW;
-
-    Desc7->dvGuardBandLeft = WCaps.GuardBandLeft;
-    Desc7->dvGuardBandTop = WCaps.GuardBandTop;
-    Desc7->dvGuardBandRight = WCaps.GuardBandRight;
-    Desc7->dvGuardBandBottom = WCaps.GuardBandBottom;
-
-    Desc7->dvExtentsAdjust = WCaps.ExtentsAdjust;
-    Desc7->dwStencilCaps = WCaps.StencilCaps;
-
-    Desc7->dwFVFCaps = WCaps.FVFCaps;
-    Desc7->dwTextureOpCaps = WCaps.TextureOpCaps;
-
-    Desc7->dwVertexProcessingCaps = WCaps.VertexProcessingCaps;
-    Desc7->dwMaxActiveLights = WCaps.MaxActiveLights;
-
-    /* Remove all non-d3d7 caps */
-    Desc7->dwDevCaps &= (
-        D3DDEVCAPS_FLOATTLVERTEX         | D3DDEVCAPS_SORTINCREASINGZ          | D3DDEVCAPS_SORTDECREASINGZ          |
-        D3DDEVCAPS_SORTEXACT             | D3DDEVCAPS_EXECUTESYSTEMMEMORY      | D3DDEVCAPS_EXECUTEVIDEOMEMORY       |
-        D3DDEVCAPS_TLVERTEXSYSTEMMEMORY  | D3DDEVCAPS_TLVERTEXVIDEOMEMORY      | D3DDEVCAPS_TEXTURESYSTEMMEMORY      |
-        D3DDEVCAPS_TEXTUREVIDEOMEMORY    | D3DDEVCAPS_DRAWPRIMTLVERTEX         | D3DDEVCAPS_CANRENDERAFTERFLIP       |
-        D3DDEVCAPS_TEXTURENONLOCALVIDMEM | D3DDEVCAPS_DRAWPRIMITIVES2          | D3DDEVCAPS_SEPARATETEXTUREMEMORIES  |
-        D3DDEVCAPS_DRAWPRIMITIVES2EX     | D3DDEVCAPS_HWTRANSFORMANDLIGHT      | D3DDEVCAPS_CANBLTSYSTONONLOCAL      |
-        D3DDEVCAPS_HWRASTERIZATION);
-
-    Desc7->dwStencilCaps &= (
-        D3DSTENCILCAPS_KEEP              | D3DSTENCILCAPS_ZERO                 | D3DSTENCILCAPS_REPLACE              |
-        D3DSTENCILCAPS_INCRSAT           | D3DSTENCILCAPS_DECRSAT              | D3DSTENCILCAPS_INVERT               |
-        D3DSTENCILCAPS_INCR              | D3DSTENCILCAPS_DECR);
-
-    /* FVF caps ?*/
-
-    Desc7->dwTextureOpCaps &= (
-        D3DTEXOPCAPS_DISABLE             | D3DTEXOPCAPS_SELECTARG1             | D3DTEXOPCAPS_SELECTARG2             |
-        D3DTEXOPCAPS_MODULATE            | D3DTEXOPCAPS_MODULATE2X             | D3DTEXOPCAPS_MODULATE4X             |
-        D3DTEXOPCAPS_ADD                 | D3DTEXOPCAPS_ADDSIGNED              | D3DTEXOPCAPS_ADDSIGNED2X            |
-        D3DTEXOPCAPS_SUBTRACT            | D3DTEXOPCAPS_ADDSMOOTH              | D3DTEXOPCAPS_BLENDTEXTUREALPHA      |
-        D3DTEXOPCAPS_BLENDFACTORALPHA    | D3DTEXOPCAPS_BLENDTEXTUREALPHAPM    | D3DTEXOPCAPS_BLENDCURRENTALPHA      |
-        D3DTEXOPCAPS_PREMODULATE         | D3DTEXOPCAPS_MODULATEALPHA_ADDCOLOR | D3DTEXOPCAPS_MODULATECOLOR_ADDALPHA |
-        D3DTEXOPCAPS_MODULATEINVALPHA_ADDCOLOR | D3DTEXOPCAPS_MODULATEINVCOLOR_ADDALPHA | D3DTEXOPCAPS_BUMPENVMAP    |
-        D3DTEXOPCAPS_BUMPENVMAPLUMINANCE | D3DTEXOPCAPS_DOTPRODUCT3);
-
-    Desc7->dwVertexProcessingCaps &= (
-        D3DVTXPCAPS_TEXGEN               | D3DVTXPCAPS_MATERIALSOURCE7         | D3DVTXPCAPS_VERTEXFOG               |
-        D3DVTXPCAPS_DIRECTIONALLIGHTS    | D3DVTXPCAPS_POSITIONALLIGHTS        | D3DVTXPCAPS_LOCALVIEWER);
-
-    Desc7->dpcLineCaps.dwMiscCaps &= (
-        D3DPMISCCAPS_MASKPLANES          | D3DPMISCCAPS_MASKZ                  | D3DPMISCCAPS_LINEPATTERNREP         |
-        D3DPMISCCAPS_CONFORMANT          | D3DPMISCCAPS_CULLNONE               | D3DPMISCCAPS_CULLCW                 |
-        D3DPMISCCAPS_CULLCCW);
-
-    Desc7->dpcLineCaps.dwRasterCaps &= (
-        D3DPRASTERCAPS_DITHER            | D3DPRASTERCAPS_ROP2                 | D3DPRASTERCAPS_XOR                  |
-        D3DPRASTERCAPS_PAT               | D3DPRASTERCAPS_ZTEST                | D3DPRASTERCAPS_SUBPIXEL             |
-        D3DPRASTERCAPS_SUBPIXELX         | D3DPRASTERCAPS_FOGVERTEX            | D3DPRASTERCAPS_FOGTABLE             |
-        D3DPRASTERCAPS_STIPPLE           | D3DPRASTERCAPS_ANTIALIASSORTDEPENDENT | D3DPRASTERCAPS_ANTIALIASSORTINDEPENDENT |
-        D3DPRASTERCAPS_ANTIALIASEDGES    | D3DPRASTERCAPS_MIPMAPLODBIAS        | D3DPRASTERCAPS_ZBIAS                |
-        D3DPRASTERCAPS_ZBUFFERLESSHSR    | D3DPRASTERCAPS_FOGRANGE             | D3DPRASTERCAPS_ANISOTROPY           |
-        D3DPRASTERCAPS_WBUFFER           | D3DPRASTERCAPS_TRANSLUCENTSORTINDEPENDENT | D3DPRASTERCAPS_WFOG           |
-        D3DPRASTERCAPS_ZFOG);
-
-    Desc7->dpcLineCaps.dwZCmpCaps &= (
-        D3DPCMPCAPS_NEVER                | D3DPCMPCAPS_LESS                    | D3DPCMPCAPS_EQUAL                   |
-        D3DPCMPCAPS_LESSEQUAL            | D3DPCMPCAPS_GREATER                 | D3DPCMPCAPS_NOTEQUAL                |
-        D3DPCMPCAPS_GREATEREQUAL         | D3DPCMPCAPS_ALWAYS);
-
-    Desc7->dpcLineCaps.dwSrcBlendCaps &= (
-        D3DPBLENDCAPS_ZERO               | D3DPBLENDCAPS_ONE                   | D3DPBLENDCAPS_SRCCOLOR              |
-        D3DPBLENDCAPS_INVSRCCOLOR        | D3DPBLENDCAPS_SRCALPHA              | D3DPBLENDCAPS_INVSRCALPHA           |
-        D3DPBLENDCAPS_DESTALPHA          | D3DPBLENDCAPS_INVDESTALPHA          | D3DPBLENDCAPS_DESTCOLOR             |
-        D3DPBLENDCAPS_INVDESTCOLOR       | D3DPBLENDCAPS_SRCALPHASAT           | D3DPBLENDCAPS_BOTHSRCALPHA          |
-        D3DPBLENDCAPS_BOTHINVSRCALPHA);
-
-    Desc7->dpcLineCaps.dwDestBlendCaps &= (
-        D3DPBLENDCAPS_ZERO               | D3DPBLENDCAPS_ONE                   | D3DPBLENDCAPS_SRCCOLOR              |
-        D3DPBLENDCAPS_INVSRCCOLOR        | D3DPBLENDCAPS_SRCALPHA              | D3DPBLENDCAPS_INVSRCALPHA           |
-        D3DPBLENDCAPS_DESTALPHA          | D3DPBLENDCAPS_INVDESTALPHA          | D3DPBLENDCAPS_DESTCOLOR             |
-        D3DPBLENDCAPS_INVDESTCOLOR       | D3DPBLENDCAPS_SRCALPHASAT           | D3DPBLENDCAPS_BOTHSRCALPHA          |
-        D3DPBLENDCAPS_BOTHINVSRCALPHA);
-
-    Desc7->dpcLineCaps.dwAlphaCmpCaps &= (
-        D3DPCMPCAPS_NEVER                | D3DPCMPCAPS_LESS                    | D3DPCMPCAPS_EQUAL                   |
-        D3DPCMPCAPS_LESSEQUAL            | D3DPCMPCAPS_GREATER                 | D3DPCMPCAPS_NOTEQUAL                |
-        D3DPCMPCAPS_GREATEREQUAL         | D3DPCMPCAPS_ALWAYS);
-
-    Desc7->dpcLineCaps.dwShadeCaps &= (
-        D3DPSHADECAPS_COLORFLATMONO      | D3DPSHADECAPS_COLORFLATRGB          | D3DPSHADECAPS_COLORGOURAUDMONO      |
-        D3DPSHADECAPS_COLORGOURAUDRGB    | D3DPSHADECAPS_COLORPHONGMONO        | D3DPSHADECAPS_COLORPHONGRGB         |
-        D3DPSHADECAPS_SPECULARFLATMONO   | D3DPSHADECAPS_SPECULARFLATRGB       | D3DPSHADECAPS_SPECULARGOURAUDMONO   |
-        D3DPSHADECAPS_SPECULARGOURAUDRGB | D3DPSHADECAPS_SPECULARPHONGMONO     | D3DPSHADECAPS_SPECULARPHONGRGB      |
-        D3DPSHADECAPS_ALPHAFLATBLEND     | D3DPSHADECAPS_ALPHAFLATSTIPPLED     | D3DPSHADECAPS_ALPHAGOURAUDBLEND     |
-        D3DPSHADECAPS_ALPHAGOURAUDSTIPPLED | D3DPSHADECAPS_ALPHAPHONGBLEND     | D3DPSHADECAPS_ALPHAPHONGSTIPPLED    |
-        D3DPSHADECAPS_FOGFLAT            | D3DPSHADECAPS_FOGGOURAUD            | D3DPSHADECAPS_FOGPHONG);
-
-    Desc7->dpcLineCaps.dwTextureCaps &= (
-        D3DPTEXTURECAPS_PERSPECTIVE      | D3DPTEXTURECAPS_POW2                | D3DPTEXTURECAPS_ALPHA               |
-        D3DPTEXTURECAPS_TRANSPARENCY     | D3DPTEXTURECAPS_BORDER              | D3DPTEXTURECAPS_SQUAREONLY          |
-        D3DPTEXTURECAPS_TEXREPEATNOTSCALEDBYSIZE | D3DPTEXTURECAPS_ALPHAPALETTE| D3DPTEXTURECAPS_NONPOW2CONDITIONAL  |
-        D3DPTEXTURECAPS_PROJECTED        | D3DPTEXTURECAPS_CUBEMAP             | D3DPTEXTURECAPS_COLORKEYBLEND);
-
-    Desc7->dpcLineCaps.dwTextureFilterCaps &= (
-        D3DPTFILTERCAPS_NEAREST          | D3DPTFILTERCAPS_LINEAR              | D3DPTFILTERCAPS_MIPNEAREST          |
-        D3DPTFILTERCAPS_MIPLINEAR        | D3DPTFILTERCAPS_LINEARMIPNEAREST    | D3DPTFILTERCAPS_LINEARMIPLINEAR     |
-        D3DPTFILTERCAPS_MINFPOINT        | D3DPTFILTERCAPS_MINFLINEAR          | D3DPTFILTERCAPS_MINFANISOTROPIC     |
-        D3DPTFILTERCAPS_MIPFPOINT        | D3DPTFILTERCAPS_MIPFLINEAR          | D3DPTFILTERCAPS_MAGFPOINT           |
-        D3DPTFILTERCAPS_MAGFLINEAR       | D3DPTFILTERCAPS_MAGFANISOTROPIC     | D3DPTFILTERCAPS_MAGFAFLATCUBIC      |
-        D3DPTFILTERCAPS_MAGFGAUSSIANCUBIC);
-
-    Desc7->dpcLineCaps.dwTextureBlendCaps &= (
-        D3DPTBLENDCAPS_DECAL             | D3DPTBLENDCAPS_MODULATE             | D3DPTBLENDCAPS_DECALALPHA           |
-        D3DPTBLENDCAPS_MODULATEALPHA     | D3DPTBLENDCAPS_DECALMASK            | D3DPTBLENDCAPS_MODULATEMASK         |
-        D3DPTBLENDCAPS_COPY              | D3DPTBLENDCAPS_ADD);
-
-    Desc7->dpcLineCaps.dwTextureAddressCaps &= (
-        D3DPTADDRESSCAPS_WRAP            | D3DPTADDRESSCAPS_MIRROR             | D3DPTADDRESSCAPS_CLAMP              |
-        D3DPTADDRESSCAPS_BORDER          | D3DPTADDRESSCAPS_INDEPENDENTUV);
-
-    if(!(Desc7->dpcLineCaps.dwTextureCaps & D3DPTEXTURECAPS_POW2)) {
-        /* DirectX7 always has the np2 flag set, no matter what the card supports. Some old games(rollcage)
-         * check the caps incorrectly. If wined3d supports nonpow2 textures it also has np2 conditional support
-         */
-        Desc7->dpcLineCaps.dwTextureCaps |= D3DPTEXTURECAPS_POW2 | D3DPTEXTURECAPS_NONPOW2CONDITIONAL;
-    }
-    /* Fill the missing members, and do some fixup */
-    Desc7->dpcLineCaps.dwSize = sizeof(Desc7->dpcLineCaps);
-    Desc7->dpcLineCaps.dwTextureBlendCaps = D3DPTBLENDCAPS_ADD | D3DPTBLENDCAPS_MODULATEMASK |
-                                            D3DPTBLENDCAPS_COPY | D3DPTBLENDCAPS_DECAL |
-                                            D3DPTBLENDCAPS_DECALALPHA | D3DPTBLENDCAPS_DECALMASK |
-                                            D3DPTBLENDCAPS_MODULATE | D3DPTBLENDCAPS_MODULATEALPHA;
-    Desc7->dpcLineCaps.dwStippleWidth = 32;
-    Desc7->dpcLineCaps.dwStippleHeight = 32;
-    /* Use the same for the TriCaps */
-    Desc7->dpcTriCaps = Desc7->dpcLineCaps;
-
-    Desc7->dwDeviceRenderBitDepth = DDBD_16 | DDBD_24 | DDBD_32;
-    Desc7->dwDeviceZBufferBitDepth = DDBD_16 | DDBD_24;
-    Desc7->dwMinTextureWidth = 1;
-    Desc7->dwMinTextureHeight = 1;
-
-    /* Convert DWORDs safely to WORDs */
-    if(WCaps.MaxTextureBlendStages > 65535) Desc7->wMaxTextureBlendStages = 65535;
-    else Desc7->wMaxTextureBlendStages = (WORD) WCaps.MaxTextureBlendStages;
-    if(WCaps.MaxSimultaneousTextures > 65535) Desc7->wMaxSimultaneousTextures = 65535;
-    else Desc7->wMaxSimultaneousTextures = (WORD) WCaps.MaxSimultaneousTextures;
-
-    if(WCaps.MaxUserClipPlanes > 65535) Desc7->wMaxUserClipPlanes = 65535;
-    else Desc7->wMaxUserClipPlanes = (WORD) WCaps.MaxUserClipPlanes;
-    if(WCaps.MaxVertexBlendMatrices > 65535) Desc7->wMaxVertexBlendMatrices = 65535;
-    else Desc7->wMaxVertexBlendMatrices = (WORD) WCaps.MaxVertexBlendMatrices;
-
-    Desc7->deviceGUID = IID_IDirect3DTnLHalDevice;
-
-    Desc7->dwReserved1 = 0;
-    Desc7->dwReserved2 = 0;
-    Desc7->dwReserved3 = 0;
-    Desc7->dwReserved4 = 0;
-
-    /* Fill the old structure */
-    memset(Desc123, 0x0, sizeof(D3DDEVICEDESC));
-    Desc123->dwSize = sizeof(D3DDEVICEDESC);
-    Desc123->dwFlags = D3DDD_COLORMODEL            |
-                       D3DDD_DEVCAPS               |
-                       D3DDD_TRANSFORMCAPS         |
-                       D3DDD_BCLIPPING             |
-                       D3DDD_LIGHTINGCAPS          |
-                       D3DDD_LINECAPS              |
-                       D3DDD_TRICAPS               |
-                       D3DDD_DEVICERENDERBITDEPTH  |
-                       D3DDD_DEVICEZBUFFERBITDEPTH |
-                       D3DDD_MAXBUFFERSIZE         |
-                       D3DDD_MAXVERTEXCOUNT;
-    Desc123->dcmColorModel = D3DCOLOR_RGB;
-    Desc123->dwDevCaps = Desc7->dwDevCaps;
-    Desc123->dtcTransformCaps.dwSize = sizeof(D3DTRANSFORMCAPS);
-    Desc123->dtcTransformCaps.dwCaps = D3DTRANSFORMCAPS_CLIP;
-    Desc123->bClipping = TRUE;
-    Desc123->dlcLightingCaps.dwSize = sizeof(D3DLIGHTINGCAPS);
-    Desc123->dlcLightingCaps.dwCaps = D3DLIGHTCAPS_DIRECTIONAL | D3DLIGHTCAPS_PARALLELPOINT | D3DLIGHTCAPS_POINT | D3DLIGHTCAPS_SPOT;
-    Desc123->dlcLightingCaps.dwLightingModel = D3DLIGHTINGMODEL_RGB;
-    Desc123->dlcLightingCaps.dwNumLights = Desc7->dwMaxActiveLights;
-
-    Desc123->dpcLineCaps.dwSize = sizeof(D3DPRIMCAPS);
-    Desc123->dpcLineCaps.dwMiscCaps = Desc7->dpcLineCaps.dwMiscCaps;
-    Desc123->dpcLineCaps.dwRasterCaps = Desc7->dpcLineCaps.dwRasterCaps;
-    Desc123->dpcLineCaps.dwZCmpCaps = Desc7->dpcLineCaps.dwZCmpCaps;
-    Desc123->dpcLineCaps.dwSrcBlendCaps = Desc7->dpcLineCaps.dwSrcBlendCaps;
-    Desc123->dpcLineCaps.dwDestBlendCaps = Desc7->dpcLineCaps.dwDestBlendCaps;
-    Desc123->dpcLineCaps.dwShadeCaps = Desc7->dpcLineCaps.dwShadeCaps;
-    Desc123->dpcLineCaps.dwTextureCaps = Desc7->dpcLineCaps.dwTextureCaps;
-    Desc123->dpcLineCaps.dwTextureFilterCaps = Desc7->dpcLineCaps.dwTextureFilterCaps;
-    Desc123->dpcLineCaps.dwTextureBlendCaps = Desc7->dpcLineCaps.dwTextureBlendCaps;
-    Desc123->dpcLineCaps.dwTextureAddressCaps = Desc7->dpcLineCaps.dwTextureAddressCaps;
-    Desc123->dpcLineCaps.dwStippleWidth = Desc7->dpcLineCaps.dwStippleWidth;
-    Desc123->dpcLineCaps.dwAlphaCmpCaps = Desc7->dpcLineCaps.dwAlphaCmpCaps;
-
-    Desc123->dpcTriCaps.dwSize = sizeof(D3DPRIMCAPS);
-    Desc123->dpcTriCaps.dwMiscCaps = Desc7->dpcTriCaps.dwMiscCaps;
-    Desc123->dpcTriCaps.dwRasterCaps = Desc7->dpcTriCaps.dwRasterCaps;
-    Desc123->dpcTriCaps.dwZCmpCaps = Desc7->dpcTriCaps.dwZCmpCaps;
-    Desc123->dpcTriCaps.dwSrcBlendCaps = Desc7->dpcTriCaps.dwSrcBlendCaps;
-    Desc123->dpcTriCaps.dwDestBlendCaps = Desc7->dpcTriCaps.dwDestBlendCaps;
-    Desc123->dpcTriCaps.dwShadeCaps = Desc7->dpcTriCaps.dwShadeCaps;
-    Desc123->dpcTriCaps.dwTextureCaps = Desc7->dpcTriCaps.dwTextureCaps;
-    Desc123->dpcTriCaps.dwTextureFilterCaps = Desc7->dpcTriCaps.dwTextureFilterCaps;
-    Desc123->dpcTriCaps.dwTextureBlendCaps = Desc7->dpcTriCaps.dwTextureBlendCaps;
-    Desc123->dpcTriCaps.dwTextureAddressCaps = Desc7->dpcTriCaps.dwTextureAddressCaps;
-    Desc123->dpcTriCaps.dwStippleWidth = Desc7->dpcTriCaps.dwStippleWidth;
-    Desc123->dpcTriCaps.dwAlphaCmpCaps = Desc7->dpcTriCaps.dwAlphaCmpCaps;
-
-    Desc123->dwDeviceRenderBitDepth = Desc7->dwDeviceRenderBitDepth;
-    Desc123->dwDeviceZBufferBitDepth = Desc7->dwDeviceZBufferBitDepth;
-    Desc123->dwMaxBufferSize = 0;
-    Desc123->dwMaxVertexCount = 65536;
-    Desc123->dwMinTextureWidth  = Desc7->dwMinTextureWidth;
-    Desc123->dwMinTextureHeight = Desc7->dwMinTextureHeight;
-    Desc123->dwMaxTextureWidth  = Desc7->dwMaxTextureWidth;
-    Desc123->dwMaxTextureHeight = Desc7->dwMaxTextureHeight;
-    Desc123->dwMinStippleWidth  = 1;
-    Desc123->dwMinStippleHeight = 1;
-    Desc123->dwMaxStippleWidth  = 32;
-    Desc123->dwMaxStippleHeight = 32;
-    Desc123->dwMaxTextureRepeat = Desc7->dwMaxTextureRepeat;
-    Desc123->dwMaxTextureAspectRatio = Desc7->dwMaxTextureAspectRatio;
-    Desc123->dwMaxAnisotropy = Desc7->dwMaxAnisotropy;
-    Desc123->dvGuardBandLeft = Desc7->dvGuardBandLeft;
-    Desc123->dvGuardBandRight = Desc7->dvGuardBandRight;
-    Desc123->dvGuardBandTop = Desc7->dvGuardBandTop;
-    Desc123->dvGuardBandBottom = Desc7->dvGuardBandBottom;
-    Desc123->dvExtentsAdjust = Desc7->dvExtentsAdjust;
-    Desc123->dwStencilCaps = Desc7->dwStencilCaps;
-    Desc123->dwFVFCaps = Desc7->dwFVFCaps;
-    Desc123->dwTextureOpCaps = Desc7->dwTextureOpCaps;
-    Desc123->wMaxTextureBlendStages = Desc7->wMaxTextureBlendStages;
-    Desc123->wMaxSimultaneousTextures = Desc7->wMaxSimultaneousTextures;
-
-    return DD_OK;
-}
-/*****************************************************************************
- * IDirect3D vtables in various versions
- *****************************************************************************/
-
-const IDirect3DVtbl IDirect3D1_Vtbl =
-{
-    /*** IUnknown methods ***/
-    Thunk_IDirect3DImpl_1_QueryInterface,
-    Thunk_IDirect3DImpl_1_AddRef,
-    Thunk_IDirect3DImpl_1_Release,
-    /*** IDirect3D methods ***/
-    IDirect3DImpl_1_Initialize,
-    Thunk_IDirect3DImpl_1_EnumDevices,
-    Thunk_IDirect3DImpl_1_CreateLight,
-    Thunk_IDirect3DImpl_1_CreateMaterial,
-    Thunk_IDirect3DImpl_1_CreateViewport,
-    Thunk_IDirect3DImpl_1_FindDevice
-};
-
-const IDirect3D2Vtbl IDirect3D2_Vtbl =
-{
-    /*** IUnknown methods ***/
-    Thunk_IDirect3DImpl_2_QueryInterface,
-    Thunk_IDirect3DImpl_2_AddRef,
-    Thunk_IDirect3DImpl_2_Release,
-    /*** IDirect3D2 methods ***/
-    Thunk_IDirect3DImpl_2_EnumDevices,
-    Thunk_IDirect3DImpl_2_CreateLight,
-    Thunk_IDirect3DImpl_2_CreateMaterial,
-    Thunk_IDirect3DImpl_2_CreateViewport,
-    Thunk_IDirect3DImpl_2_FindDevice,
-    Thunk_IDirect3DImpl_2_CreateDevice
-};
-
-const IDirect3D3Vtbl IDirect3D3_Vtbl =
-{
-    /*** IUnknown methods ***/
-    Thunk_IDirect3DImpl_3_QueryInterface,
-    Thunk_IDirect3DImpl_3_AddRef,
-    Thunk_IDirect3DImpl_3_Release,
-    /*** IDirect3D3 methods ***/
-    IDirect3DImpl_3_EnumDevices,
-    IDirect3DImpl_3_CreateLight,
-    IDirect3DImpl_3_CreateMaterial,
-    IDirect3DImpl_3_CreateViewport,
-    IDirect3DImpl_3_FindDevice,
-    Thunk_IDirect3DImpl_3_CreateDevice,
-    Thunk_IDirect3DImpl_3_CreateVertexBuffer,
-    Thunk_IDirect3DImpl_3_EnumZBufferFormats,
-    Thunk_IDirect3DImpl_3_EvictManagedTextures
-};
-
-const IDirect3D7Vtbl IDirect3D7_Vtbl =
-{
-    /*** IUnknown methods ***/
-    Thunk_IDirect3DImpl_7_QueryInterface,
-    Thunk_IDirect3DImpl_7_AddRef,
-    Thunk_IDirect3DImpl_7_Release,
-    /*** IDirect3D7 methods ***/
-    IDirect3DImpl_7_EnumDevices,
-    IDirect3DImpl_7_CreateDevice,
-    IDirect3DImpl_7_CreateVertexBuffer,
-    IDirect3DImpl_7_EnumZBufferFormats,
-    IDirect3DImpl_7_EvictManagedTextures
-};
index 29fd65e..d4d2dd0 100644 (file)
 #include "config.h"
 #include "wine/port.h"
 
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-#define NONAMELESSUNION
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
 #include "ddraw_private.h"
-#include "wine/debug.h"
 
-WINE_DEFAULT_DEBUG_CHANNEL(d3d7);
+WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
 /*****************************************************************************
  * _dump_executedata
@@ -103,10 +85,10 @@ IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
 
     /* Activate the viewport */
     lpViewport->active_device = lpDevice;
-    lpViewport->activate(lpViewport, FALSE);
+    viewport_activate(lpViewport, FALSE);
 
     TRACE("ExecuteData :\n");
-    if (TRACE_ON(d3d7))
+    if (TRACE_ON(ddraw))
       _dump_executedata(&(This->data));
 
     while (1) {
@@ -142,27 +124,28 @@ IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
                        
                for (i = 0; i < count; i++) {
                     LPD3DTRIANGLE ci = (LPD3DTRIANGLE) instr;
-                   TRACE_(d3d7)("  v1: %d  v2: %d  v3: %d\n",ci->u1.v1, ci->u2.v2, ci->u3.v3);
-                   TRACE_(d3d7)("  Flags : ");
-                   if (TRACE_ON(d3d7)) {
-                       /* Wireframe */
-                       if (ci->wFlags & D3DTRIFLAG_EDGEENABLE1)
-                           TRACE_(d3d7)("EDGEENABLE1 ");
-                       if (ci->wFlags & D3DTRIFLAG_EDGEENABLE2)
-                           TRACE_(d3d7)("EDGEENABLE2 ");
-                       if (ci->wFlags & D3DTRIFLAG_EDGEENABLE1)
-                           TRACE_(d3d7)("EDGEENABLE3 ");
-                       /* Strips / Fans */
-                       if (ci->wFlags == D3DTRIFLAG_EVEN)
-                           TRACE_(d3d7)("EVEN ");
-                       if (ci->wFlags == D3DTRIFLAG_ODD)
-                           TRACE_(d3d7)("ODD ");
-                       if (ci->wFlags == D3DTRIFLAG_START)
-                           TRACE_(d3d7)("START ");
-                       if ((ci->wFlags > 0) && (ci->wFlags < 30))
-                           TRACE_(d3d7)("STARTFLAT(%d) ", ci->wFlags);
-                       TRACE_(d3d7)("\n");
-                   }
+                   TRACE("  v1: %d  v2: %d  v3: %d\n",ci->u1.v1, ci->u2.v2, ci->u3.v3);
+                   TRACE("  Flags : ");
+                    if (TRACE_ON(ddraw))
+                    {
+                        /* Wireframe */
+                        if (ci->wFlags & D3DTRIFLAG_EDGEENABLE1)
+                            TRACE("EDGEENABLE1 ");
+                        if (ci->wFlags & D3DTRIFLAG_EDGEENABLE2)
+                            TRACE("EDGEENABLE2 ");
+                        if (ci->wFlags & D3DTRIFLAG_EDGEENABLE1)
+                            TRACE("EDGEENABLE3 ");
+                        /* Strips / Fans */
+                        if (ci->wFlags == D3DTRIFLAG_EVEN)
+                            TRACE("EVEN ");
+                        if (ci->wFlags == D3DTRIFLAG_ODD)
+                            TRACE("ODD ");
+                        if (ci->wFlags == D3DTRIFLAG_START)
+                            TRACE("START ");
+                        if ((ci->wFlags > 0) && (ci->wFlags < 30))
+                            TRACE("STARTFLAT(%u) ", ci->wFlags);
+                        TRACE("\n");
+                    }
                    This->indices[(i * 3)    ] = ci->u1.v1;
                    This->indices[(i * 3) + 1] = ci->u2.v2;
                    This->indices[(i * 3) + 2] = ci->u3.v3;
@@ -188,25 +171,24 @@ IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
                int i;
                TRACE("MATRIXMULTIPLY   (%d)\n", count);
                
-               for (i = 0; i < count; i++) {
-                   LPD3DMATRIXMULTIPLY ci = (LPD3DMATRIXMULTIPLY) instr;
-                    LPD3DMATRIX a, b, c;
-
-                    if(!ci->hDestMatrix || ci->hDestMatrix > lpDevice->numHandles ||
-                       !ci->hSrcMatrix1 || ci->hSrcMatrix1 > lpDevice->numHandles ||
-                       !ci->hSrcMatrix2 || ci->hSrcMatrix2 > lpDevice->numHandles) {
-                        ERR("Handles out of bounds\n");
-                    } else if (lpDevice->Handles[ci->hDestMatrix - 1].type != DDrawHandle_Matrix ||
-                               lpDevice->Handles[ci->hSrcMatrix1 - 1].type != DDrawHandle_Matrix ||
-                               lpDevice->Handles[ci->hSrcMatrix2 - 1].type != DDrawHandle_Matrix) {
-                        ERR("Handle types invalid\n");
-                    } else {
-                        a = (LPD3DMATRIX) lpDevice->Handles[ci->hDestMatrix - 1].ptr;
-                        b = (LPD3DMATRIX) lpDevice->Handles[ci->hSrcMatrix1 - 1].ptr;
-                        c = (LPD3DMATRIX) lpDevice->Handles[ci->hSrcMatrix2 - 1].ptr;
-                        TRACE("  Dest : %p  Src1 : %p  Src2 : %p\n",
-                            a, b, c);
-                        multiply_matrix(a,c,b);
+                for (i = 0; i < count; ++i)
+                {
+                    D3DMATRIXMULTIPLY *ci = (D3DMATRIXMULTIPLY *)instr;
+                    D3DMATRIX *a, *b, *c;
+
+                    a = ddraw_get_object(&lpDevice->handle_table, ci->hDestMatrix - 1, DDRAW_HANDLE_MATRIX);
+                    b = ddraw_get_object(&lpDevice->handle_table, ci->hSrcMatrix1 - 1, DDRAW_HANDLE_MATRIX);
+                    c = ddraw_get_object(&lpDevice->handle_table, ci->hSrcMatrix2 - 1, DDRAW_HANDLE_MATRIX);
+
+                    if (!a || !b || !c)
+                    {
+                        ERR("Invalid matrix handle (a %#x -> %p, b %#x -> %p, c %#x -> %p).\n",
+                                ci->hDestMatrix, a, ci->hSrcMatrix1, b, ci->hSrcMatrix2, c);
+                    }
+                    else
+                    {
+                        TRACE("dst %p, src1 %p, src2 %p.\n", a, b, c);
+                        multiply_matrix(a, c, b);
                     }
 
                     instr += size;
@@ -217,27 +199,30 @@ IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
                int i;
                TRACE("STATETRANSFORM   (%d)\n", count);
                
-               for (i = 0; i < count; i++) {
-                   LPD3DSTATE ci = (LPD3DSTATE) instr;
-
-                    if(!ci->u2.dwArg[0]) {
-                        ERR("Setting a NULL matrix handle, what should I do?\n");
-                    } else if(ci->u2.dwArg[0] > lpDevice->numHandles) {
-                        ERR("Handle %d is out of bounds\n", ci->u2.dwArg[0]);
-                    } else if(lpDevice->Handles[ci->u2.dwArg[0] - 1].type != DDrawHandle_Matrix) {
-                        ERR("Handle %d is not a matrix handle\n", ci->u2.dwArg[0]);
-                    } else {
-                        if(ci->u1.dtstTransformStateType == D3DTRANSFORMSTATE_WORLD)
+                for (i = 0; i < count; ++i)
+                {
+                    D3DSTATE *ci = (D3DSTATE *)instr;
+                    D3DMATRIX *m;
+
+                    m = ddraw_get_object(&lpDevice->handle_table, ci->u2.dwArg[0] - 1, DDRAW_HANDLE_MATRIX);
+                    if (!m)
+                    {
+                        ERR("Invalid matrix handle %#x.\n", ci->u2.dwArg[0]);
+                    }
+                    else
+                    {
+                        if (ci->u1.dtstTransformStateType == D3DTRANSFORMSTATE_WORLD)
                             lpDevice->world = ci->u2.dwArg[0];
-                        if(ci->u1.dtstTransformStateType == D3DTRANSFORMSTATE_VIEW)
+                        if (ci->u1.dtstTransformStateType == D3DTRANSFORMSTATE_VIEW)
                             lpDevice->view = ci->u2.dwArg[0];
-                        if(ci->u1.dtstTransformStateType == D3DTRANSFORMSTATE_PROJECTION)
+                        if (ci->u1.dtstTransformStateType == D3DTRANSFORMSTATE_PROJECTION)
                             lpDevice->proj = ci->u2.dwArg[0];
                         IDirect3DDevice7_SetTransform((IDirect3DDevice7 *)lpDevice,
-                                ci->u1.dtstTransformStateType, (LPD3DMATRIX)lpDevice->Handles[ci->u2.dwArg[0] - 1].ptr);
+                                ci->u1.dtstTransformStateType, m);
                     }
-                   instr += size;
-               }
+
+                    instr += size;
+                }
            } break;
 
            case D3DOP_STATELIGHT: {
@@ -251,22 +236,18 @@ IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
 
                    if (!ci->u1.dlstLightStateType || (ci->u1.dlstLightStateType > D3DLIGHTSTATE_COLORVERTEX))
                        ERR("Unexpected Light State Type %d\n", ci->u1.dlstLightStateType);
-                   else if (ci->u1.dlstLightStateType == D3DLIGHTSTATE_MATERIAL /* 1 */) {
-                       DWORD matHandle = ci->u2.dwArg[0];
-
-                       if (!matHandle) {
-                           FIXME(" D3DLIGHTSTATE_MATERIAL called with NULL material !!!\n");
-                       } else if (matHandle >= lpDevice->numHandles) {
-                           WARN("Material handle %d is invalid\n", matHandle);
-                       } else if (lpDevice->Handles[matHandle - 1].type != DDrawHandle_Material) {
-                           WARN("Handle %d is not a material handle\n", matHandle);
-                       } else {
-                           IDirect3DMaterialImpl *mat =
-                                lpDevice->Handles[matHandle - 1].ptr;
-
-                           mat->activate(mat);
-                       }
-                   } else if (ci->u1.dlstLightStateType == D3DLIGHTSTATE_COLORMODEL /* 3 */) {
+                    else if (ci->u1.dlstLightStateType == D3DLIGHTSTATE_MATERIAL /* 1 */)
+                    {
+                        IDirect3DMaterialImpl *m;
+
+                        m = ddraw_get_object(&lpDevice->handle_table, ci->u2.dwArg[0] - 1, DDRAW_HANDLE_MATERIAL);
+                        if (!m)
+                            ERR("Invalid material handle %#x.\n", ci->u2.dwArg[0]);
+                        else
+                            material_activate(m);
+                    }
+                    else if (ci->u1.dlstLightStateType == D3DLIGHTSTATE_COLORMODEL /* 3 */)
+                    {
                        switch (ci->u2.dwArg[0]) {
                            case D3DCOLOR_MONO:
                                ERR("DDCOLOR_MONO should not happen!\n");
@@ -354,7 +335,8 @@ IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
                     TRACE("  Start : %d Dest : %d Count : %d\n",
                          ci->wStart, ci->wDest, ci->dwCount);
                    TRACE("  Flags : ");
-                   if (TRACE_ON(d3d7)) {
+                    if (TRACE_ON(ddraw))
+                    {
                        if (ci->dwFlags & D3DPROCESSVERTICES_COPY)
                            TRACE("COPY ");
                        if (ci->dwFlags & D3DPROCESSVERTICES_NOCOLOR)
@@ -404,7 +386,8 @@ IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
                        D3DMATRIX mat;
                        D3DVIEWPORT* Viewport = &lpViewport->viewports.vp1;
                        
-                       if (TRACE_ON(d3d7)) {
+                        if (TRACE_ON(ddraw))
+                        {
                            TRACE("  Projection Matrix : (%p)\n", &proj_mat);
                            dump_D3DMATRIX(&proj_mat);
                            TRACE("  View       Matrix : (%p)\n", &view_mat);
@@ -448,7 +431,8 @@ IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
                        D3DMATRIX mat;
                        D3DVIEWPORT* Viewport = &lpViewport->viewports.vp1;
                        
-                       if (TRACE_ON(d3d7)) {
+                        if (TRACE_ON(ddraw))
+                        {
                            TRACE("  Projection Matrix : (%p)\n", &proj_mat);
                            dump_D3DMATRIX(&proj_mat);
                            TRACE("  View       Matrix : (%p)\n",&view_mat);
@@ -591,7 +575,7 @@ IDirect3DExecuteBufferImpl_QueryInterface(IDirect3DExecuteBuffer *iface,
                                           REFIID riid,
                                           void **obj)
 {
-    TRACE("(%p)->(%s,%p)\n", iface, debugstr_guid(riid), obj);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obj);
 
     *obj = NULL;
 
@@ -627,7 +611,7 @@ IDirect3DExecuteBufferImpl_AddRef(IDirect3DExecuteBuffer *iface)
     IDirect3DExecuteBufferImpl *This = (IDirect3DExecuteBufferImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    FIXME("(%p)->()incrementing from %u.\n", This, ref - 1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -647,7 +631,7 @@ IDirect3DExecuteBufferImpl_Release(IDirect3DExecuteBuffer *iface)
     IDirect3DExecuteBufferImpl *This = (IDirect3DExecuteBufferImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
 
-    TRACE("(%p)->()decrementing from %u.\n", This, ref + 1);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (!ref) {
         if (This->need_free)
@@ -671,13 +655,11 @@ IDirect3DExecuteBufferImpl_Release(IDirect3DExecuteBuffer *iface)
  *  D3D_OK
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DExecuteBufferImpl_Initialize(IDirect3DExecuteBuffer *iface,
-                                        IDirect3DDevice *lpDirect3DDevice,
-                                        D3DEXECUTEBUFFERDESC *lpDesc)
+static HRESULT WINAPI IDirect3DExecuteBufferImpl_Initialize(IDirect3DExecuteBuffer *iface,
+        IDirect3DDevice *device, D3DEXECUTEBUFFERDESC *desc)
 {
-    IDirect3DExecuteBufferImpl *This = (IDirect3DExecuteBufferImpl *)iface;
-    TRACE("(%p)->(%p,%p) no-op....\n", This, lpDirect3DDevice, lpDesc);
+    TRACE("iface %p, device %p, desc %p.\n", iface, device, desc);
+
     return D3D_OK;
 }
 
@@ -700,12 +682,14 @@ IDirect3DExecuteBufferImpl_Lock(IDirect3DExecuteBuffer *iface,
 {
     IDirect3DExecuteBufferImpl *This = (IDirect3DExecuteBufferImpl *)iface;
     DWORD dwSize;
-    TRACE("(%p)->(%p)\n", This, lpDesc);
+
+    TRACE("iface %p, desc %p.\n", iface, lpDesc);
 
     dwSize = lpDesc->dwSize;
     memcpy(lpDesc, &This->desc, dwSize);
 
-    if (TRACE_ON(d3d7)) {
+    if (TRACE_ON(ddraw))
+    {
         TRACE("  Returning description :\n");
        _dump_D3DEXECUTEBUFFERDESC(lpDesc);
     }
@@ -721,11 +705,10 @@ IDirect3DExecuteBufferImpl_Lock(IDirect3DExecuteBuffer *iface,
  *  This implementation always returns D3D_OK
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DExecuteBufferImpl_Unlock(IDirect3DExecuteBuffer *iface)
+static HRESULT WINAPI IDirect3DExecuteBufferImpl_Unlock(IDirect3DExecuteBuffer *iface)
 {
-    IDirect3DExecuteBufferImpl *This = (IDirect3DExecuteBufferImpl *)iface;
-    TRACE("(%p)->() no-op...\n", This);
+    TRACE("iface %p.\n", iface);
+
     return D3D_OK;
 }
 
@@ -749,7 +732,8 @@ IDirect3DExecuteBufferImpl_SetExecuteData(IDirect3DExecuteBuffer *iface,
 {
     IDirect3DExecuteBufferImpl *This = (IDirect3DExecuteBufferImpl *)iface;
     DWORD nbvert;
-    TRACE("(%p)->(%p)\n", This, lpData);
+
+    TRACE("iface %p, data %p.\n", iface, lpData);
 
     memcpy(&This->data, lpData, lpData->dwSize);
 
@@ -760,9 +744,8 @@ IDirect3DExecuteBufferImpl_SetExecuteData(IDirect3DExecuteBuffer *iface,
     HeapFree(GetProcessHeap(), 0, This->vertex_data);
     This->vertex_data = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, nbvert * sizeof(D3DTLVERTEX));
 
-    if (TRACE_ON(d3d7)) {
+    if (TRACE_ON(ddraw))
         _dump_executedata(lpData);
-    }
 
     return D3D_OK;
 }
@@ -785,12 +768,14 @@ IDirect3DExecuteBufferImpl_GetExecuteData(IDirect3DExecuteBuffer *iface,
 {
     IDirect3DExecuteBufferImpl *This = (IDirect3DExecuteBufferImpl *)iface;
     DWORD dwSize;
-    TRACE("(%p)->(%p): stub!\n", This, lpData);
+
+    TRACE("iface %p, data %p.\n", iface, lpData);
 
     dwSize = lpData->dwSize;
     memcpy(lpData, &This->data, dwSize);
 
-    if (TRACE_ON(d3d7)) {
+    if (TRACE_ON(ddraw))
+    {
         TRACE("Returning data :\n");
        _dump_executedata(lpData);
     }
@@ -811,15 +796,14 @@ IDirect3DExecuteBufferImpl_GetExecuteData(IDirect3DExecuteBuffer *iface,
  *  DDERR_UNSUPPORTED, because it's not implemented in Windows.
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DExecuteBufferImpl_Validate(IDirect3DExecuteBuffer *iface,
-                                    DWORD *Offset,
-                                    LPD3DVALIDATECALLBACK Func,
-                                    void *UserArg,
-                                    DWORD Reserved)
+static HRESULT WINAPI IDirect3DExecuteBufferImpl_Validate(IDirect3DExecuteBuffer *iface,
+        DWORD *offset, LPD3DVALIDATECALLBACK callback, void *context, DWORD reserved)
 {
-    IDirect3DExecuteBufferImpl *This = (IDirect3DExecuteBufferImpl *)iface;
-    TRACE("(%p)->(%p,%p,%p,%08x): Unimplemented!\n", This, Offset, Func, UserArg, Reserved);
+    TRACE("iface %p, offset %p, callback %p, context %p, reserved %#x.\n",
+            iface, offset, callback, context, reserved);
+
+    WARN("Not implemented.\n");
+
     return DDERR_UNSUPPORTED; /* Unchecked */
 }
 
@@ -836,16 +820,16 @@ IDirect3DExecuteBufferImpl_Validate(IDirect3DExecuteBuffer *iface,
  *  DDERR_UNSUPPORTED, because it's not implemented in Windows.
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DExecuteBufferImpl_Optimize(IDirect3DExecuteBuffer *iface,
-                                    DWORD Dummy)
+static HRESULT WINAPI IDirect3DExecuteBufferImpl_Optimize(IDirect3DExecuteBuffer *iface, DWORD reserved)
 {
-    IDirect3DExecuteBufferImpl *This = (IDirect3DExecuteBufferImpl *)iface;
-    TRACE("(%p)->(%08x): Unimplemented\n", This, Dummy);
+    TRACE("iface %p, reserved %#x.\n", iface, reserved);
+
+    WARN("Not implemented.\n");
+
     return DDERR_UNSUPPORTED; /* Unchecked */
 }
 
-const IDirect3DExecuteBufferVtbl IDirect3DExecuteBuffer_Vtbl =
+static const struct IDirect3DExecuteBufferVtbl d3d_execute_buffer_vtbl =
 {
     IDirect3DExecuteBufferImpl_QueryInterface,
     IDirect3DExecuteBufferImpl_AddRef,
@@ -858,3 +842,38 @@ const IDirect3DExecuteBufferVtbl IDirect3DExecuteBuffer_Vtbl =
     IDirect3DExecuteBufferImpl_Validate,
     IDirect3DExecuteBufferImpl_Optimize,
 };
+
+HRESULT d3d_execute_buffer_init(IDirect3DExecuteBufferImpl *execute_buffer,
+        IDirect3DDeviceImpl *device, D3DEXECUTEBUFFERDESC *desc)
+{
+    execute_buffer->lpVtbl = &d3d_execute_buffer_vtbl;
+    execute_buffer->ref = 1;
+    execute_buffer->d3ddev = device;
+
+    /* Initializes memory */
+    memcpy(&execute_buffer->desc, desc, desc->dwSize);
+
+    /* No buffer given */
+    if (!(execute_buffer->desc.dwFlags & D3DDEB_LPDATA))
+        execute_buffer->desc.lpData = NULL;
+
+    /* No buffer size given */
+    if (!(execute_buffer->desc.dwFlags & D3DDEB_BUFSIZE))
+        execute_buffer->desc.dwBufferSize = 0;
+
+    /* Create buffer if asked */
+    if (!execute_buffer->desc.lpData && execute_buffer->desc.dwBufferSize)
+    {
+        execute_buffer->need_free = TRUE;
+        execute_buffer->desc.lpData = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, execute_buffer->desc.dwBufferSize);
+        if (!execute_buffer->desc.lpData)
+        {
+            ERR("Failed to allocate execute buffer data.\n");
+            return DDERR_OUTOFMEMORY;
+        }
+    }
+
+    execute_buffer->desc.dwFlags |= D3DDEB_LPDATA;
+
+    return D3D_OK;
+}
diff --git a/reactos/dll/directx/wine/ddraw/gamma.c b/reactos/dll/directx/wine/ddraw/gamma.c
deleted file mode 100644 (file)
index df631a4..0000000
+++ /dev/null
@@ -1,220 +0,0 @@
-/* DirectDrawGammaControl implementation
- *
- * Copyright 2001 TransGaming Technologies Inc.
- * Copyright 2006 Stefan Dösinger
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "wine/port.h"
-#include "wine/debug.h"
-
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
-#include "ddraw_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
-WINE_DECLARE_DEBUG_CHANNEL(ddraw_thunk);
-
-static inline IDirectDrawSurfaceImpl *surface_from_gamma_control(IDirectDrawGammaControl *iface)
-{
-    return (IDirectDrawSurfaceImpl *)((char*)iface
-            - FIELD_OFFSET(IDirectDrawSurfaceImpl, IDirectDrawGammaControl_vtbl));
-}
-
-/**********************************************************
- * IUnknown parts follow
- **********************************************************/
-
-/**********************************************************
- * IDirectDrawGammaControl::QueryInterface
- *
- * QueryInterface, thunks to IDirectDrawSurface
- *
- * Params:
- *  riid: Interface id queried for
- *  obj: Returns the interface pointer
- *
- * Returns:
- *  S_OK or E_NOINTERFACE: See IDirectDrawSurface7::QueryInterface
- *
- **********************************************************/
-static HRESULT WINAPI
-IDirectDrawGammaControlImpl_QueryInterface(IDirectDrawGammaControl *iface, REFIID riid,
-                                           void **obj)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_gamma_control(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%s,%p): Thunking to IDirectDrawSurface7\n", This, debugstr_guid(riid), obj);
-
-    return IDirectDrawSurface7_QueryInterface((IDirectDrawSurface7 *)This, riid, obj);
-}
-
-/**********************************************************
- * IDirectDrawGammaControl::AddRef
- *
- * Addref, thunks to IDirectDrawSurface
- *
- * Returns:
- *  The new refcount
- *
- **********************************************************/
-static ULONG WINAPI
-IDirectDrawGammaControlImpl_AddRef(IDirectDrawGammaControl *iface)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_gamma_control(iface);
-    TRACE_(ddraw_thunk)("(%p)->() Thunking to IDirectDrawSurface7\n", This);
-
-    return IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)This);
-}
-
-/**********************************************************
- * IDirectDrawGammaControl::Release
- *
- * Release, thunks to IDirectDrawSurface
- *
- * Returns:
- *  The new refcount
- *
- **********************************************************/
-static ULONG WINAPI
-IDirectDrawGammaControlImpl_Release(IDirectDrawGammaControl *iface)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_gamma_control(iface);
-    TRACE_(ddraw_thunk)("(%p)->() Thunking to IDirectDrawSurface7\n", This);
-
-    return IDirectDrawSurface7_Release((IDirectDrawSurface7 *)This);
-}
-
-/**********************************************************
- * IDirectDrawGammaControl
- **********************************************************/
-
-/**********************************************************
- * IDirectDrawGammaControl::GetGammaRamp
- *
- * Returns the current gamma ramp for a surface
- *
- * Params:
- *  Flags: Ignored
- *  GammaRamp: Address to write the ramp to
- *
- * Returns:
- *  DD_OK on success
- *  DDERR_INVALIDPARAMS if GammaRamp is NULL
- *
- **********************************************************/
-static HRESULT WINAPI
-IDirectDrawGammaControlImpl_GetGammaRamp(IDirectDrawGammaControl *iface,
-                                         DWORD Flags,
-                                         DDGAMMARAMP *GammaRamp)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_gamma_control(iface);
-    TRACE("(%p)->(%08x,%p)\n", This,Flags,GammaRamp);
-
-    /* This looks sane */
-    if(!GammaRamp)
-    {
-        ERR("(%p) GammaRamp is NULL, returning DDERR_INVALIDPARAMS\n", This);
-        return DDERR_INVALIDPARAMS;
-    }
-
-    EnterCriticalSection(&ddraw_cs);
-    if(This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE)
-    {
-        /* Note: DDGAMMARAMP is compatible with WINED3DGAMMARAMP */
-        IWineD3DDevice_GetGammaRamp(This->ddraw->wineD3DDevice,
-                                    0 /* Swapchain */,
-                                    (WINED3DGAMMARAMP *) GammaRamp);
-    }
-    else
-    {
-        ERR("(%p) Unimplemented for non-primary surfaces\n", This);
-    }
-    LeaveCriticalSection(&ddraw_cs);
-
-    return DD_OK;
-}
-
-/**********************************************************
- * IDirectDrawGammaControl::SetGammaRamp
- *
- * Sets the red, green and blue gamma ramps for
- *
- * Params:
- *  Flags: Can be DDSGR_CALIBRATE to request calibration
- *  GammaRamp: Structure containing the new gamma ramp
- *
- * Returns:
- *  DD_OK on success
- *  DDERR_INVALIDPARAMS if GammaRamp is NULL
- *
- **********************************************************/
-static HRESULT WINAPI
-IDirectDrawGammaControlImpl_SetGammaRamp(IDirectDrawGammaControl *iface,
-                                         DWORD Flags,
-                                         DDGAMMARAMP *GammaRamp)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_gamma_control(iface);
-    TRACE("(%p)->(%08x,%p)\n", This,Flags,GammaRamp);
-
-    /* This looks sane */
-    if(!GammaRamp)
-    {
-        ERR("(%p) GammaRamp is NULL, returning DDERR_INVALIDPARAMS\n", This);
-        return DDERR_INVALIDPARAMS;
-    }
-
-    EnterCriticalSection(&ddraw_cs);
-    if(This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE)
-    {
-
-        /* Note: DDGAMMARAMP is compatible with WINED3DGAMMARAMP */
-        IWineD3DDevice_SetGammaRamp(This->ddraw->wineD3DDevice,
-                                    0 /* Swapchain */,
-                                    Flags,
-                                    (WINED3DGAMMARAMP *) GammaRamp);
-    }
-    else
-    {
-        ERR("(%p) Unimplemented for non-primary surfaces\n", This);
-    }
-    LeaveCriticalSection(&ddraw_cs);
-
-    return DD_OK;
-}
-
-const IDirectDrawGammaControlVtbl IDirectDrawGammaControl_Vtbl =
-{
-    IDirectDrawGammaControlImpl_QueryInterface,
-    IDirectDrawGammaControlImpl_AddRef,
-    IDirectDrawGammaControlImpl_Release,
-    IDirectDrawGammaControlImpl_GetGammaRamp,
-    IDirectDrawGammaControlImpl_SetGammaRamp
-};
diff --git a/reactos/dll/directx/wine/ddraw/legacy.h b/reactos/dll/directx/wine/ddraw/legacy.h
new file mode 100644 (file)
index 0000000..c9da1e7
--- /dev/null
@@ -0,0 +1,130 @@
+/*
+* Copyright (C) the Wine project
+*
+* This library is free software; you can redistribute it and/or
+* modify it under the terms of the GNU Lesser General Public
+* License as published by the Free Software Foundation; either
+* version 2.1 of the License, or (at your option) any later version.
+*
+* This library is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+* Lesser General Public License for more details.
+*
+* You should have received a copy of the GNU Lesser General Public
+* License along with this library; if not, write to the Free Software
+* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
+*/
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+    /*****************************************************************************
+    * IDirectDraw3 interface
+    */
+
+#if defined( _WIN32 ) && !defined( _NO_COM )
+    #define INTERFACE IDirectDraw3
+    DECLARE_INTERFACE_(IDirectDraw3,IUnknown)
+    {
+        /*** IUnknown methods ***/
+        /*00*/    STDMETHOD_(HRESULT,QueryInterface)(THIS_ REFIID riid, void** ppvObject) PURE;
+        /*04*/    STDMETHOD_(ULONG,AddRef)(THIS) PURE;
+        /*08*/    STDMETHOD_(ULONG,Release)(THIS) PURE;
+        /*** IDirectDraw2 methods ***/
+        /*0c*/    STDMETHOD(Compact)(THIS) PURE;
+        /*10*/    STDMETHOD(CreateClipper)(THIS_ DWORD dwFlags, LPDIRECTDRAWCLIPPER *lplpDDClipper, IUnknown *pUnkOuter) PURE;
+        /*14*/    STDMETHOD(CreatePalette)(THIS_ DWORD dwFlags, LPPALETTEENTRY lpColorTable, LPDIRECTDRAWPALETTE *lplpDDPalette, IUnknown *pUnkOuter) PURE;
+        /*18*/    STDMETHOD(CreateSurface)(THIS_ LPDDSURFACEDESC lpDDSurfaceDesc, LPDIRECTDRAWSURFACE *lplpDDSurface, IUnknown *pUnkOuter) PURE;
+        /*1c*/    STDMETHOD(DuplicateSurface)(THIS_ LPDIRECTDRAWSURFACE lpDDSurface, LPDIRECTDRAWSURFACE *lplpDupDDSurface) PURE;
+        /*20*/    STDMETHOD(EnumDisplayModes)(THIS_ DWORD dwFlags, LPDDSURFACEDESC lpDDSurfaceDesc, LPVOID lpContext, LPDDENUMMODESCALLBACK lpEnumModesCallback) PURE;
+        /*24*/    STDMETHOD(EnumSurfaces)(THIS_ DWORD dwFlags, LPDDSURFACEDESC lpDDSD, LPVOID lpContext, LPDDENUMSURFACESCALLBACK lpEnumSurfacesCallback) PURE;
+        /*28*/    STDMETHOD(FlipToGDISurface)(THIS) PURE;
+        /*2c*/    STDMETHOD(GetCaps)(THIS_ LPDDCAPS lpDDDriverCaps, LPDDCAPS lpDDHELCaps) PURE;
+        /*30*/    STDMETHOD(GetDisplayMode)(THIS_ LPDDSURFACEDESC lpDDSurfaceDesc) PURE;
+        /*34*/    STDMETHOD(GetFourCCCodes)(THIS_ LPDWORD lpNumCodes, LPDWORD lpCodes) PURE;
+        /*38*/    STDMETHOD(GetGDISurface)(THIS_ LPDIRECTDRAWSURFACE *lplpGDIDDSurface) PURE;
+        /*3c*/    STDMETHOD(GetMonitorFrequency)(THIS_ LPDWORD lpdwFrequency) PURE;
+        /*40*/    STDMETHOD(GetScanLine)(THIS_ LPDWORD lpdwScanLine) PURE;
+        /*44*/    STDMETHOD(GetVerticalBlankStatus)(THIS_ BOOL *lpbIsInVB) PURE;
+        /*48*/    STDMETHOD(Initialize)(THIS_ GUID *lpGUID) PURE;
+        /*4c*/    STDMETHOD(RestoreDisplayMode)(THIS) PURE;
+        /*50*/    STDMETHOD(SetCooperativeLevel)(THIS_ HWND hWnd, DWORD dwFlags) PURE;
+        /*54*/    STDMETHOD(SetDisplayMode)(THIS_ DWORD dwWidth, DWORD dwHeight, DWORD dwBPP, DWORD dwRefreshRate, DWORD dwFlags) PURE;
+        /*58*/    STDMETHOD(WaitForVerticalBlank)(THIS_ DWORD dwFlags, HANDLE hEvent) PURE;
+        /* added in v2 */
+        /*5c*/    STDMETHOD(GetAvailableVidMem)(THIS_ LPDDSCAPS lpDDCaps, LPDWORD lpdwTotal, LPDWORD lpdwFree) PURE;
+        /* added in v3 */
+        /*60*/    STDMETHOD(GetSurfaceFromDC)(THIS_ HDC hdc, LPDIRECTDRAWSURFACE *pSurf) PURE;
+    };
+    #undef INTERFACE
+
+    #if !defined(__cplusplus) || defined(CINTERFACE)
+        /*** IUnknown methods ***/
+        #define IDirectDraw3_QueryInterface(p,a,b) (p)->lpVtbl->QueryInterface(p,a,b)
+        #define IDirectDraw3_AddRef(p)             (p)->lpVtbl->AddRef(p)
+        #define IDirectDraw3_Release(p)            (p)->lpVtbl->Release(p)
+        /*** IDirectDraw methods ***/
+        #define IDirectDraw3_Compact(p)                  (p)->lpVtbl->Compact(p)
+        #define IDirectDraw3_CreateClipper(p,a,b,c)      (p)->lpVtbl->CreateClipper(p,a,b,c)
+        #define IDirectDraw3_CreatePalette(p,a,b,c,d)    (p)->lpVtbl->CreatePalette(p,a,b,c,d)
+        #define IDirectDraw3_CreateSurface(p,a,b,c)      (p)->lpVtbl->CreateSurface(p,a,b,c)
+        #define IDirectDraw3_DuplicateSurface(p,a,b)     (p)->lpVtbl->DuplicateSurface(p,a,b)
+        #define IDirectDraw3_EnumDisplayModes(p,a,b,c,d) (p)->lpVtbl->EnumDisplayModes(p,a,b,c,d)
+        #define IDirectDraw3_EnumSurfaces(p,a,b,c,d)     (p)->lpVtbl->EnumSurfaces(p,a,b,c,d)
+        #define IDirectDraw3_FlipToGDISurface(p)         (p)->lpVtbl->FlipToGDISurface(p)
+        #define IDirectDraw3_GetCaps(p,a,b)              (p)->lpVtbl->GetCaps(p,a,b)
+        #define IDirectDraw3_GetDisplayMode(p,a)         (p)->lpVtbl->GetDisplayMode(p,a)
+        #define IDirectDraw3_GetFourCCCodes(p,a,b)       (p)->lpVtbl->GetFourCCCodes(p,a,b)
+        #define IDirectDraw3_GetGDISurface(p,a)          (p)->lpVtbl->GetGDISurface(p,a)
+        #define IDirectDraw3_GetMonitorFrequency(p,a)    (p)->lpVtbl->GetMonitorFrequency(p,a)
+        #define IDirectDraw3_GetScanLine(p,a)            (p)->lpVtbl->GetScanLine(p,a)
+        #define IDirectDraw3_GetVerticalBlankStatus(p,a) (p)->lpVtbl->GetVerticalBlankStatus(p,a)
+        #define IDirectDraw3_Initialize(p,a)             (p)->lpVtbl->Initialize(p,a)
+        #define IDirectDraw3_RestoreDisplayMode(p)       (p)->lpVtbl->RestoreDisplayMode(p)
+        #define IDirectDraw3_SetCooperativeLevel(p,a,b)  (p)->lpVtbl->SetCooperativeLevel(p,a,b)
+        #define IDirectDraw3_SetDisplayMode(p,a,b,c,d,e) (p)->lpVtbl->SetDisplayMode(p,a,b,c,d,e)
+        #define IDirectDraw3_WaitForVerticalBlank(p,a,b) (p)->lpVtbl->WaitForVerticalBlank(p,a,b)
+        /*** IDirectDraw2 methods ***/
+        #define IDirectDraw3_GetAvailableVidMem(p,a,b,c) (p)->lpVtbl->GetAvailableVidMem(p,a,b,c)
+        /*** IDirectDraw3 methods ***/
+        #define IDirectDraw3_GetSurfaceFromDC(p,a,b)    (p)->lpVtbl->GetSurfaceFromDC(p,a,b)
+    #else
+        /*** IUnknown methods ***/
+        #define IDirectDraw3_QueryInterface(p,a,b) (p)->QueryInterface(a,b)
+        #define IDirectDraw3_AddRef(p)             (p)->AddRef()
+        #define IDirectDraw3_Release(p)            (p)->Release()
+        /*** IDirectDraw methods ***/
+        #define IDirectDraw3_Compact(p)                  (p)->Compact()
+        #define IDirectDraw3_CreateClipper(p,a,b,c)      (p)->CreateClipper(a,b,c)
+        #define IDirectDraw3_CreatePalette(p,a,b,c,d)    (p)->CreatePalette(a,b,c,d)
+        #define IDirectDraw3_CreateSurface(p,a,b,c)      (p)->CreateSurface(a,b,c)
+        #define IDirectDraw3_DuplicateSurface(p,a,b)     (p)->DuplicateSurface(a,b)
+        #define IDirectDraw3_EnumDisplayModes(p,a,b,c,d) (p)->EnumDisplayModes(a,b,c,d)
+        #define IDirectDraw3_EnumSurfaces(p,a,b,c,d)     (p)->EnumSurfaces(a,b,c,d)
+        #define IDirectDraw3_FlipToGDISurface(p)         (p)->FlipToGDISurface()
+        #define IDirectDraw3_GetCaps(p,a,b)              (p)->GetCaps(a,b)
+        #define IDirectDraw3_GetDisplayMode(p,a)         (p)->GetDisplayMode(a)
+        #define IDirectDraw3_GetFourCCCodes(p,a,b)       (p)->GetFourCCCodes(a,b)
+        #define IDirectDraw3_GetGDISurface(p,a)          (p)->GetGDISurface(a)
+        #define IDirectDraw3_GetMonitorFrequency(p,a)    (p)->GetMonitorFrequency(a)
+        #define IDirectDraw3_GetScanLine(p,a)            (p)->GetScanLine(a)
+        #define IDirectDraw3_GetVerticalBlankStatus(p,a) (p)->GetVerticalBlankStatus(a)
+        #define IDirectDraw3_Initialize(p,a)             (p)->Initialize(a)
+        #define IDirectDraw3_RestoreDisplayMode(p)       (p)->RestoreDisplayMode()
+        #define IDirectDraw3_SetCooperativeLevel(p,a,b)  (p)->SetCooperativeLevel(a,b)
+        #define IDirectDraw3_SetDisplayMode(p,a,b,c,d,e) (p)->SetDisplayMode(a,b,c,d,e)
+        #define IDirectDraw3_WaitForVerticalBlank(p,a,b) (p)->WaitForVerticalBlank(a,b)
+        /*** IDirectDraw2 methods ***/
+        #define IDirectDraw3_GetAvailableVidMem(p,a,b,c) (p)->GetAvailableVidMem(a,b,c)
+        /*** IDirectDraw3 methods ***/
+        #define IDirectDraw3_GetSurfaceFromDC(p,a,b)    (p)->GetSurfaceFromDC(a,b)
+    #endif
+#undef INTERFACE
+#endif
+
+#ifdef __cplusplus
+}
+#endif
index 030dcf0..a6a3cad 100644 (file)
 
 #include "config.h"
 #include "wine/port.h"
-#include "wine/debug.h"
 
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
+#include "ddraw_private.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
+
+/*****************************************************************************
+ * light_update
+ *
+ * Updates the Direct3DDevice7 lighting parameters
+ *
+ *****************************************************************************/
+static void light_update(IDirect3DLightImpl *light)
+{
+    IDirect3DDeviceImpl *device;
 
-#define COBJMACROS
+    TRACE("light %p.\n", light);
 
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
+    if (!light->active_viewport || !light->active_viewport->active_device) return;
+    device = light->active_viewport->active_device;
 
-#include "ddraw.h"
-#include "d3d.h"
+    IDirect3DDevice7_SetLight((IDirect3DDevice7 *)device, light->dwLightIndex, &light->light7);
+}
 
-#include "ddraw_private.h"
+/*****************************************************************************
+ * light_activate
+ *
+ * Uses the Direct3DDevice7::LightEnable method to active the light
+ *
+ *****************************************************************************/
+void light_activate(IDirect3DLightImpl *light)
+{
+    IDirect3DDeviceImpl *device;
+
+    TRACE("light %p.\n", light);
+
+    if (!light->active_viewport || !light->active_viewport->active_device) return;
+    device = light->active_viewport->active_device;
+
+    light_update(light);
+    if (!(light->light.dwFlags & D3DLIGHT_ACTIVE))
+    {
+        IDirect3DDevice7_LightEnable((IDirect3DDevice7 *)device, light->dwLightIndex, TRUE);
+        light->light.dwFlags |= D3DLIGHT_ACTIVE;
+    }
+}
+
+/*****************************************************************************
+ *
+ * light_deactivate
+ *
+ * Uses the Direct3DDevice7::LightEnable method to deactivate the light
+ *
+ *****************************************************************************/
+void light_deactivate(IDirect3DLightImpl *light)
+{
+    IDirect3DDeviceImpl *device;
 
-WINE_DEFAULT_DEBUG_CHANNEL(d3d7);
+    TRACE("light %p.\n", light);
+
+    if (!light->active_viewport || !light->active_viewport->active_device) return;
+    device = light->active_viewport->active_device;
+
+    /* If was not active, activate it */
+    if (light->light.dwFlags & D3DLIGHT_ACTIVE)
+    {
+        IDirect3DDevice7_LightEnable((IDirect3DDevice7 *)device, light->dwLightIndex, FALSE);
+        light->light.dwFlags &= ~D3DLIGHT_ACTIVE;
+    }
+}
 
 /*****************************************************************************
  * IUnknown Methods.
@@ -60,14 +108,11 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d7);
  * Returns:
  *  E_NOINTERFACE, because it's a stub
  *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DLightImpl_QueryInterface(IDirect3DLight *iface,
-                                  REFIID riid,
-                                  void **obp)
+static HRESULT WINAPI IDirect3DLightImpl_QueryInterface(IDirect3DLight *iface, REFIID riid, void **object)
 {
-    IDirect3DLightImpl *This = (IDirect3DLightImpl *)iface;
-    FIXME("(%p)->(%s,%p): stub!\n", This, debugstr_guid(riid), obp);
-    *obp = NULL;
+    FIXME("iface %p, riid %s, object %p stub!\n", iface, debugstr_guid(riid), object);
+
+    *object = NULL;
     return E_NOINTERFACE;
 }
 
@@ -86,7 +131,7 @@ IDirect3DLightImpl_AddRef(IDirect3DLight *iface)
     IDirect3DLightImpl *This = (IDirect3DLightImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    TRACE("(%p)->() incrementing from %u.\n", This, ref - 1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -107,11 +152,11 @@ IDirect3DLightImpl_Release(IDirect3DLight *iface)
     IDirect3DLightImpl *This = (IDirect3DLightImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
 
-    TRACE("(%p)->() decrementing from %u.\n", This, ref + 1);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (!ref) {
         HeapFree(GetProcessHeap(), 0, This);
-       return 0;
+        return 0;
     }
     return ref;
 }
@@ -133,13 +178,10 @@ IDirect3DLightImpl_Release(IDirect3DLight *iface)
  *  D3D_OK
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DLightImpl_Initialize(IDirect3DLight *iface,
-                              IDirect3D *lpDirect3D)
+static HRESULT WINAPI IDirect3DLightImpl_Initialize(IDirect3DLight *iface, IDirect3D *d3d)
 {
-    IDirect3DLightImpl *This = (IDirect3DLightImpl *)iface;
-    IDirectDrawImpl *d3d = lpDirect3D ? ddraw_from_d3d1(lpDirect3D) : NULL;
-    TRACE("(%p)->(%p) no-op...\n", This, d3d);
+    TRACE("iface %p, d3d %p.\n", iface, d3d);
+
     return D3D_OK;
 }
 
@@ -171,10 +213,13 @@ IDirect3DLightImpl_SetLight(IDirect3DLight *iface,
 {
     IDirect3DLightImpl *This = (IDirect3DLightImpl *)iface;
     LPD3DLIGHT7 light7 = &(This->light7);
-    TRACE("(%p)->(%p)\n", This, lpLight);
-    if (TRACE_ON(d3d7)) {
+
+    TRACE("iface %p, light %p.\n", iface, lpLight);
+
+    if (TRACE_ON(ddraw))
+    {
         TRACE("  Light definition :\n");
-       dump_light((LPD3DLIGHT2) lpLight);
+        dump_light((LPD3DLIGHT2) lpLight);
     }
 
     if ( (lpLight->dltType == 0) || (lpLight->dltType > D3DLIGHT_PARALLELPOINT) )
@@ -203,9 +248,8 @@ IDirect3DLightImpl_SetLight(IDirect3DLight *iface,
 
     EnterCriticalSection(&ddraw_cs);
     memcpy(&This->light, lpLight, lpLight->dwSize);
-    if ((This->light.dwFlags & D3DLIGHT_ACTIVE) != 0) {
-        This->update(This);
-    }
+    if (This->light.dwFlags & D3DLIGHT_ACTIVE)
+        light_update(This);
     LeaveCriticalSection(&ddraw_cs);
     return D3D_OK;
 }
@@ -227,10 +271,13 @@ IDirect3DLightImpl_GetLight(IDirect3DLight *iface,
                             D3DLIGHT *lpLight)
 {
     IDirect3DLightImpl *This = (IDirect3DLightImpl *)iface;
-    TRACE("(%p/%p)->(%p)\n", This, iface, lpLight);
-    if (TRACE_ON(d3d7)) {
+
+    TRACE("iface %p, light %p.\n", iface, lpLight);
+
+    if (TRACE_ON(ddraw))
+    {
         TRACE("  Returning light definition :\n");
-       dump_light(&This->light);
+        dump_light(&This->light);
     }
 
     EnterCriticalSection(&ddraw_cs);
@@ -240,74 +287,7 @@ IDirect3DLightImpl_GetLight(IDirect3DLight *iface,
     return DD_OK;
 }
 
-/*****************************************************************************
- * light_update
- *
- * Updates the Direct3DDevice7 lighting parameters
- *
- *****************************************************************************/
-void light_update(IDirect3DLightImpl* This)
-{
-    IDirect3DDeviceImpl* device;
-
-    TRACE("(%p)\n", This);
-
-    if (!This->active_viewport || !This->active_viewport->active_device)
-        return;
-    device =  This->active_viewport->active_device;
-
-    IDirect3DDevice7_SetLight((IDirect3DDevice7 *)device, This->dwLightIndex, &(This->light7));
-}
-
-/*****************************************************************************
- * light_activate
- *
- * Uses the Direct3DDevice7::LightEnable method to active the light
- *
- *****************************************************************************/
-void light_activate(IDirect3DLightImpl* This)
-{
-    IDirect3DDeviceImpl* device;
-
-    TRACE("(%p)\n", This);
-
-    if (!This->active_viewport || !This->active_viewport->active_device)
-        return;
-    device =  This->active_viewport->active_device;
-
-    light_update(This);
-    /* If was not active, activate it */
-    if ((This->light.dwFlags & D3DLIGHT_ACTIVE) == 0) {
-        IDirect3DDevice7_LightEnable((IDirect3DDevice7 *)device, This->dwLightIndex, TRUE);
-       This->light.dwFlags |= D3DLIGHT_ACTIVE;
-    }
-}
-
-/*****************************************************************************
- *
- * light_desactivate
- *
- * Uses the Direct3DDevice7::LightEnable method to deactivate the light
- *
- *****************************************************************************/
-void light_desactivate(IDirect3DLightImpl* This)
-{
-    IDirect3DDeviceImpl* device;
-
-    TRACE("(%p)\n", This);
-
-    if (!This->active_viewport || !This->active_viewport->active_device)
-        return;
-    device =  This->active_viewport->active_device;
-
-    /* If was not active, activate it */
-    if ((This->light.dwFlags & D3DLIGHT_ACTIVE) != 0) {
-        IDirect3DDevice7_LightEnable((IDirect3DDevice7 *)device, This->dwLightIndex, FALSE);
-       This->light.dwFlags &= ~D3DLIGHT_ACTIVE;
-    }
-}
-
-const IDirect3DLightVtbl IDirect3DLight_Vtbl =
+static const struct IDirect3DLightVtbl d3d_light_vtbl =
 {
     /*** IUnknown Methods ***/
     IDirect3DLightImpl_QueryInterface,
@@ -318,3 +298,10 @@ const IDirect3DLightVtbl IDirect3DLight_Vtbl =
     IDirect3DLightImpl_SetLight,
     IDirect3DLightImpl_GetLight
 };
+
+void d3d_light_init(IDirect3DLightImpl *light, IDirectDrawImpl *ddraw)
+{
+    light->lpVtbl = &d3d_light_vtbl;
+    light->ref = 1;
+    light->ddraw = ddraw;
+}
index 72426cd..217a2cb 100644 (file)
 
 #include "config.h"
 #include "wine/port.h"
-#include "wine/debug.h"
-
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-#include "winreg.h"
-
-#include "ddraw.h"
-#include "d3d.h"
 
 #define DDRAW_INIT_GUID
 #include "ddraw_private.h"
 
-static typeof(WineDirect3DCreate) *pWineDirect3DCreate;
+#include "wine/exception.h"
+#include "winreg.h"
 
 WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
 /* The configured default surface */
 WINED3DSURFTYPE DefaultSurfaceType = SURFACE_UNKNOWN;
 
+typeof(WineDirect3DCreateClipper) *pWineDirect3DCreateClipper DECLSPEC_HIDDEN;
+typeof(WineDirect3DCreate) *pWineDirect3DCreate DECLSPEC_HIDDEN;
+
 /* DDraw list and critical section */
 static struct list global_ddraw_list = LIST_INIT(global_ddraw_list);
 
@@ -70,6 +56,117 @@ CRITICAL_SECTION ddraw_cs = { &ddraw_cs_debug, -1, 0, 0, 0, 0 };
 /* value of ForceRefreshRate */
 DWORD force_refresh_rate = 0;
 
+/* Handle table functions */
+BOOL ddraw_handle_table_init(struct ddraw_handle_table *t, UINT initial_size)
+{
+    t->entries = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, initial_size * sizeof(*t->entries));
+    if (!t->entries)
+    {
+        ERR("Failed to allocate handle table memory.\n");
+        return FALSE;
+    }
+    t->free_entries = NULL;
+    t->table_size = initial_size;
+    t->entry_count = 0;
+
+    return TRUE;
+}
+
+void ddraw_handle_table_destroy(struct ddraw_handle_table *t)
+{
+    HeapFree(GetProcessHeap(), 0, t->entries);
+    memset(t, 0, sizeof(*t));
+}
+
+DWORD ddraw_allocate_handle(struct ddraw_handle_table *t, void *object, enum ddraw_handle_type type)
+{
+    struct ddraw_handle_entry *entry;
+
+    if (t->free_entries)
+    {
+        DWORD idx = t->free_entries - t->entries;
+        /* Use a free handle */
+        entry = t->free_entries;
+        if (entry->type != DDRAW_HANDLE_FREE)
+        {
+            ERR("Handle %#x (%p) is in the free list, but has type %#x.\n", idx, entry->object, entry->type);
+            return DDRAW_INVALID_HANDLE;
+        }
+        t->free_entries = entry->object;
+        entry->object = object;
+        entry->type = type;
+
+        return idx;
+    }
+
+    if (!(t->entry_count < t->table_size))
+    {
+        /* Grow the table */
+        UINT new_size = t->table_size + (t->table_size >> 1);
+        struct ddraw_handle_entry *new_entries = HeapReAlloc(GetProcessHeap(),
+                0, t->entries, new_size * sizeof(*t->entries));
+        if (!new_entries)
+        {
+            ERR("Failed to grow the handle table.\n");
+            return DDRAW_INVALID_HANDLE;
+        }
+        t->entries = new_entries;
+        t->table_size = new_size;
+    }
+
+    entry = &t->entries[t->entry_count];
+    entry->object = object;
+    entry->type = type;
+
+    return t->entry_count++;
+}
+
+void *ddraw_free_handle(struct ddraw_handle_table *t, DWORD handle, enum ddraw_handle_type type)
+{
+    struct ddraw_handle_entry *entry;
+    void *object;
+
+    if (handle == DDRAW_INVALID_HANDLE || handle >= t->entry_count)
+    {
+        WARN("Invalid handle %#x passed.\n", handle);
+        return NULL;
+    }
+
+    entry = &t->entries[handle];
+    if (entry->type != type)
+    {
+        WARN("Handle %#x (%p) is not of type %#x.\n", handle, entry->object, type);
+        return NULL;
+    }
+
+    object = entry->object;
+    entry->object = t->free_entries;
+    entry->type = DDRAW_HANDLE_FREE;
+    t->free_entries = entry;
+
+    return object;
+}
+
+void *ddraw_get_object(struct ddraw_handle_table *t, DWORD handle, enum ddraw_handle_type type)
+{
+    struct ddraw_handle_entry *entry;
+
+    if (handle == DDRAW_INVALID_HANDLE || handle >= t->entry_count)
+    {
+        WARN("Invalid handle %#x passed.\n", handle);
+        return NULL;
+    }
+
+    entry = &t->entries[handle];
+    if (entry->type != type)
+    {
+        WARN("Handle %#x (%p) is not of type %#x.\n", handle, entry->object, type);
+        return NULL;
+    }
+
+    return entry->object;
+}
+
 /*
  * Helper Function for DDRAW_Create and DirectDrawCreateClipper for
  * lazy loading of the Wine D3D driver.
@@ -124,14 +221,12 @@ DDRAW_Create(const GUID *guid,
              IUnknown *UnkOuter,
              REFIID iid)
 {
-    IDirectDrawImpl *This = NULL;
-    HRESULT hr;
-    IWineD3D *wineD3D = NULL;
-    IWineD3DDevice *wineD3DDevice = NULL;
-    HDC hDC;
     WINED3DDEVTYPE devicetype;
+    IDirectDrawImpl *This;
+    HRESULT hr;
 
-    TRACE("(%s,%p,%p)\n", debugstr_guid(guid), DD, UnkOuter);
+    TRACE("driver_guid %s, ddraw %p, outer_unknown %p, interface_iid %s.\n",
+            debugstr_guid(guid), DD, UnkOuter, debugstr_guid(iid));
 
     *DD = NULL;
 
@@ -167,129 +262,19 @@ DDRAW_Create(const GUID *guid,
         return E_OUTOFMEMORY;
     }
 
-    /* The interfaces:
-     * IDirectDraw and IDirect3D are the same object,
-     * QueryInterface is used to get other interfaces.
-     */
-    This->lpVtbl = &IDirectDraw7_Vtbl;
-    This->IDirectDraw_vtbl = &IDirectDraw1_Vtbl;
-    This->IDirectDraw2_vtbl = &IDirectDraw2_Vtbl;
-    This->IDirectDraw4_vtbl = &IDirectDraw4_Vtbl;
-    This->IDirect3D_vtbl = &IDirect3D1_Vtbl;
-    This->IDirect3D2_vtbl = &IDirect3D2_Vtbl;
-    This->IDirect3D3_vtbl = &IDirect3D3_Vtbl;
-    This->IDirect3D7_vtbl = &IDirect3D7_Vtbl;
-    This->device_parent_vtbl = &ddraw_wined3d_device_parent_vtbl;
-
-    /* See comments in IDirectDrawImpl_CreateNewSurface for a description
-     * of this member.
-     * Read from a registry key, should add a winecfg option later
-     */
-    This->ImplType = DefaultSurfaceType;
-
-    /* Get the current screen settings */
-    hDC = GetDC(0);
-    This->orig_bpp = GetDeviceCaps(hDC, BITSPIXEL) * GetDeviceCaps(hDC, PLANES);
-    ReleaseDC(0, hDC);
-    This->orig_width = GetSystemMetrics(SM_CXSCREEN);
-    This->orig_height = GetSystemMetrics(SM_CYSCREEN);
-
-    if (!LoadWineD3D())
-    {
-        ERR("Couldn't load WineD3D - OpenGL libs not present?\n");
-        hr = DDERR_NODIRECTDRAWSUPPORT;
-        goto err_out;
-    }
-
-    /* Initialize WineD3D
-     *
-     * All Rendering (2D and 3D) is relayed to WineD3D,
-     * but DirectDraw specific management, like DDSURFACEDESC and DDPIXELFORMAT
-     * structure handling is handled in this lib.
-     */
-    wineD3D = pWineDirect3DCreate(7 /* DXVersion */, (IUnknown *) This /* Parent */);
-    if(!wineD3D)
-    {
-        ERR("Failed to initialise WineD3D\n");
-        hr = E_OUTOFMEMORY;
-        goto err_out;
-    }
-    This->wineD3D = wineD3D;
-    TRACE("WineD3D created at %p\n", wineD3D);
-
-    /* Initialized member...
-     *
-     * It is set to false at creation time, and set to true in
-     * IDirectDraw7::Initialize. Its sole purpose is to return DD_OK on
-     * initialize only once
-     */
-    This->initialized = FALSE;
-
-    /* Initialize WineD3DDevice
-     *
-     * It is used for screen setup, surface and palette creation
-     * When a Direct3DDevice7 is created, the D3D capabilities of WineD3D are
-     * initialized
-     */
-    hr = IWineD3D_CreateDevice(wineD3D, 0 /* D3D_ADAPTER_DEFAULT */, devicetype, NULL /* FocusWindow, don't know yet */,
-            0 /* BehaviorFlags */, (IUnknown *)This, (IWineD3DDeviceParent *)&This->device_parent_vtbl, &wineD3DDevice);
-    if(FAILED(hr))
-    {
-        ERR("Failed to create a wineD3DDevice, result = %x\n", hr);
-        goto err_out;
-    }
-    This->wineD3DDevice = wineD3DDevice;
-    TRACE("wineD3DDevice created at %p\n", This->wineD3DDevice);
-
-    /* Register the window class
-     *
-     * It is used to create a hidden window for D3D
-     * rendering, if the application didn't pass one.
-     * It can also be used for Creating a device window
-     * from SetCooperativeLevel
-     *
-     * The name: DDRAW_<address>. The classname is
-     * 32 bit long, so a 64 bit address will fit nicely
-     * (Will this be compiled for 64 bit anyway?)
-     *
-     */
-    sprintf(This->classname, "DDRAW_%p", This);
-
-    memset(&This->wnd_class, 0, sizeof(This->wnd_class));
-    This->wnd_class.style = CS_HREDRAW | CS_VREDRAW;
-    This->wnd_class.lpfnWndProc = DefWindowProcA;
-    This->wnd_class.cbClsExtra = 0;
-    This->wnd_class.cbWndExtra = 0;
-    This->wnd_class.hInstance = GetModuleHandleA(0);
-    This->wnd_class.hIcon = 0;
-    This->wnd_class.hCursor = 0;
-    This->wnd_class.hbrBackground = GetStockObject(BLACK_BRUSH);
-    This->wnd_class.lpszMenuName = NULL;
-    This->wnd_class.lpszClassName = This->classname;
-    if(!RegisterClassA(&This->wnd_class))
+    hr = ddraw_init(This, devicetype);
+    if (FAILED(hr))
     {
-        ERR("RegisterClassA failed!\n");
-        goto err_out;
+        WARN("Failed to initialize ddraw object, hr %#x.\n", hr);
+        HeapFree(GetProcessHeap(), 0, This);
+        return hr;
     }
 
-    /* Get the amount of video memory */
-    This->total_vidmem = IWineD3DDevice_GetAvailableTextureMem(This->wineD3DDevice);
-
-    list_init(&This->surface_list);
-    list_add_head(&global_ddraw_list, &This->ddraw_list_entry);
-
-    /* Call QueryInterface to get the pointer to the requested interface. This also initializes
-     * The required refcount
-     */
     hr = IDirectDraw7_QueryInterface((IDirectDraw7 *)This, iid, DD);
-    if(SUCCEEDED(hr)) return DD_OK;
-
-err_out:
-    /* Let's hope we never need this ;) */
-    if(wineD3DDevice) IWineD3DDevice_Release(wineD3DDevice);
-    if(wineD3D) IWineD3D_Release(wineD3D);
-    HeapFree(GetProcessHeap(), 0, This->decls);
-    HeapFree(GetProcessHeap(), 0, This);
+    IDirectDraw7_Release((IDirectDraw7 *)This);
+    if (SUCCEEDED(hr)) list_add_head(&global_ddraw_list, &This->ddraw_list_entry);
+    else WARN("Failed to query interface %s from ddraw object %p.\n", debugstr_guid(iid), This);
+
     return hr;
 }
 
@@ -308,7 +293,9 @@ DirectDrawCreate(GUID *GUID,
                  IUnknown *UnkOuter)
 {
     HRESULT hr;
-    TRACE("(%s,%p,%p)\n", debugstr_guid(GUID), DD, UnkOuter);
+
+    TRACE("driver_guid %s, ddraw %p, outer_unknown %p.\n",
+            debugstr_guid(GUID), DD, UnkOuter);
 
     EnterCriticalSection(&ddraw_cs);
     hr = DDRAW_Create(GUID, (void **) DD, UnkOuter, &IID_IDirectDraw);
@@ -332,7 +319,9 @@ DirectDrawCreateEx(GUID *GUID,
                    IUnknown *UnkOuter)
 {
     HRESULT hr;
-    TRACE("(%s,%p,%s,%p)\n", debugstr_guid(GUID), DD, debugstr_guid(iid), UnkOuter);
+
+    TRACE("driver_guid %s, ddraw %p, interface_iid %s, outer_unknown %p.\n",
+            debugstr_guid(GUID), DD, debugstr_guid(iid), UnkOuter);
 
     if (!IsEqualGUID(iid, &IID_IDirectDraw7))
         return DDERR_INVALIDPARAMS;
@@ -363,11 +352,9 @@ DirectDrawCreateEx(GUID *GUID,
  *
  *
  ***********************************************************************/
-HRESULT WINAPI
-DirectDrawEnumerateA(LPDDENUMCALLBACKA Callback,
-                     LPVOID Context)
+HRESULT WINAPI DirectDrawEnumerateA(LPDDENUMCALLBACKA Callback, void *Context)
 {
-    TRACE("(%p, %p)\n", Callback, Context);
+    TRACE("callback %p, context %p.\n", Callback, Context);
 
     TRACE(" Enumerating default DirectDraw HAL interface\n");
     /* We only have one driver */
@@ -397,12 +384,9 @@ DirectDrawEnumerateA(LPDDENUMCALLBACKA Callback,
  * The Flag member is not supported right now.
  *
  ***********************************************************************/
-HRESULT WINAPI
-DirectDrawEnumerateExA(LPDDENUMCALLBACKEXA Callback,
-                       LPVOID Context,
-                       DWORD Flags)
+HRESULT WINAPI DirectDrawEnumerateExA(LPDDENUMCALLBACKEXA Callback, void *Context, DWORD Flags)
 {
-    TRACE("(%p, %p, 0x%08x)\n", Callback, Context, Flags);
+    TRACE("callback %p, context %p, flags %#x.\n", Callback, Context, Flags);
 
     if (Flags & ~(DDENUM_ATTACHEDSECONDARYDEVICES |
                   DDENUM_DETACHEDSECONDARYDEVICES |
@@ -440,13 +424,11 @@ DirectDrawEnumerateExA(LPDDENUMCALLBACKEXA Callback,
  * This function is not implemented on Windows.
  *
  ***********************************************************************/
-HRESULT WINAPI
-DirectDrawEnumerateW(LPDDENUMCALLBACKW Callback,
-                     LPVOID Context)
+HRESULT WINAPI DirectDrawEnumerateW(LPDDENUMCALLBACKW callback, void *context)
 {
-    TRACE("(%p, %p)\n", Callback, Context);
+    TRACE("callback %p, context %p.\n", callback, context);
 
-    if (!Callback)
+    if (!callback)
         return DDERR_INVALIDPARAMS;
     else
         return DDERR_UNSUPPORTED;
@@ -459,12 +441,9 @@ DirectDrawEnumerateW(LPDDENUMCALLBACKW Callback,
  * This function is not implemented on Windows.
  *
  ***********************************************************************/
-HRESULT WINAPI
-DirectDrawEnumerateExW(LPDDENUMCALLBACKEXW Callback,
-                       LPVOID Context,
-                       DWORD Flags)
+HRESULT WINAPI DirectDrawEnumerateExW(LPDDENUMCALLBACKEXW callback, void *context, DWORD flags)
 {
-    TRACE("(%p, %p, 0x%x)\n", Callback, Context, Flags);
+    TRACE("callback %p, context %p, flags %#x.\n", callback, context, flags);
 
     return DDERR_UNSUPPORTED;
 }
@@ -493,7 +472,7 @@ CF_CreateDirectDraw(IUnknown* UnkOuter, REFIID iid,
 {
     HRESULT hr;
 
-    TRACE("(%p,%s,%p)\n", UnkOuter, debugstr_guid(iid), obj);
+    TRACE("outer_unknown %p, riid %s, object %p.\n", UnkOuter, debugstr_guid(iid), obj);
 
     EnterCriticalSection(&ddraw_cs);
     hr = DDRAW_Create(NULL, obj, UnkOuter, iid);
@@ -522,6 +501,8 @@ CF_CreateDirectDrawClipper(IUnknown* UnkOuter, REFIID riid,
     HRESULT hr;
     IDirectDrawClipper *Clip;
 
+    TRACE("outer_unknown %p, riid %s, object %p.\n", UnkOuter, debugstr_guid(riid), obj);
+
     EnterCriticalSection(&ddraw_cs);
     hr = DirectDrawCreateClipper(0, &Clip, UnkOuter);
     if (hr != DD_OK)
@@ -565,7 +546,7 @@ IDirectDrawClassFactoryImpl_QueryInterface(IClassFactory *iface,
 {
     IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
 
-    TRACE("(%p)->(%s,%p)\n", This, debugstr_guid(riid), obj);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obj);
 
     if (IsEqualGUID(riid, &IID_IUnknown)
         || IsEqualGUID(riid, &IID_IClassFactory))
@@ -594,7 +575,7 @@ IDirectDrawClassFactoryImpl_AddRef(IClassFactory *iface)
     IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    TRACE("(%p)->() incrementing from %d.\n", This, ref - 1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -614,7 +595,8 @@ IDirectDrawClassFactoryImpl_Release(IClassFactory *iface)
 {
     IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
-    TRACE("(%p)->() decrementing from %d.\n", This, ref+1);
+
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (ref == 0)
         HeapFree(GetProcessHeap(), 0, This);
@@ -643,7 +625,8 @@ IDirectDrawClassFactoryImpl_CreateInstance(IClassFactory *iface,
 {
     IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
 
-    TRACE("(%p)->(%p,%s,%p)\n",This,UnkOuter,debugstr_guid(riid),obj);
+    TRACE("iface %p, outer_unknown %p, riid %s, object %p.\n",
+            iface, UnkOuter, debugstr_guid(riid), obj);
 
     return This->pfnCreateInstance(UnkOuter, riid, obj);
 }
@@ -660,11 +643,10 @@ IDirectDrawClassFactoryImpl_CreateInstance(IClassFactory *iface,
  *  S_OK, because it's a stub
  *
  *******************************************************************************/
-static HRESULT WINAPI
-IDirectDrawClassFactoryImpl_LockServer(IClassFactory *iface,BOOL dolock)
+static HRESULT WINAPI IDirectDrawClassFactoryImpl_LockServer(IClassFactory *iface, BOOL dolock)
 {
-    IClassFactoryImpl *This = (IClassFactoryImpl *)iface;
-    FIXME("(%p)->(%d),stub!\n",This,dolock);
+    FIXME("iface %p, dolock %#x stub!\n", iface, dolock);
+
     return S_OK;
 }
 
@@ -702,22 +684,23 @@ HRESULT WINAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID *ppv)
     unsigned int i;
     IClassFactoryImpl *factory;
 
-    TRACE("(%s,%s,%p)\n", debugstr_guid(rclsid), debugstr_guid(riid), ppv);
+    TRACE("rclsid %s, riid %s, object %p.\n",
+            debugstr_guid(rclsid), debugstr_guid(riid), ppv);
 
-    if ( !IsEqualGUID( &IID_IClassFactory, riid )
-        && ! IsEqualGUID( &IID_IUnknown, riid) )
-       return E_NOINTERFACE;
+    if (!IsEqualGUID(&IID_IClassFactory, riid)
+            && !IsEqualGUID(&IID_IUnknown, riid))
+        return E_NOINTERFACE;
 
     for (i=0; i < sizeof(object_creation)/sizeof(object_creation[0]); i++)
     {
-       if (IsEqualGUID(object_creation[i].clsid, rclsid))
-           break;
+        if (IsEqualGUID(object_creation[i].clsid, rclsid))
+            break;
     }
 
     if (i == sizeof(object_creation)/sizeof(object_creation[0]))
     {
-       FIXME("%s: no class found.\n", debugstr_guid(rclsid));
-       return CLASS_E_CLASSNOTAVAILABLE;
+        FIXME("%s: no class found.\n", debugstr_guid(rclsid));
+        return CLASS_E_CLASSNOTAVAILABLE;
     }
 
     factory = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*factory));
@@ -742,6 +725,8 @@ HRESULT WINAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID *ppv)
  */
 HRESULT WINAPI DllCanUnloadNow(void)
 {
+    TRACE("\n");
+
     return S_FALSE;
 }
 
@@ -816,8 +801,28 @@ DllMain(HINSTANCE hInstDLL,
         DWORD size = sizeof(buffer);
         HKEY hkey = 0;
         HKEY appkey = 0;
+        WNDCLASSA wc;
         DWORD len;
 
+        /* Register the window class. This is used to create a hidden window
+         * for D3D rendering, if the application didn't pass one. It can also
+         * be used for creating a device window from SetCooperativeLevel(). */
+        wc.style = CS_HREDRAW | CS_VREDRAW;
+        wc.lpfnWndProc = DefWindowProcA;
+        wc.cbClsExtra = 0;
+        wc.cbWndExtra = 0;
+        wc.hInstance = hInstDLL;
+        wc.hIcon = 0;
+        wc.hCursor = 0;
+        wc.hbrBackground = GetStockObject(BLACK_BRUSH);
+        wc.lpszMenuName = NULL;
+        wc.lpszClassName = DDRAW_WINDOW_CLASS_NAME;
+        if (!RegisterClassA(&wc))
+        {
+            ERR("Failed to register ddraw window class, last error %#x.\n", GetLastError());
+            return FALSE;
+        }
+
        /* @@ Wine registry key: HKCU\Software\Wine\Direct3D */
        if ( RegOpenKeyA( HKEY_CURRENT_USER, "Software\\Wine\\Direct3D", &hkey ) ) hkey = 0;
 
@@ -913,6 +918,7 @@ DllMain(HINSTANCE hInstDLL,
                 /* Add references to each interface to avoid freeing them unexpectedly */
                 IDirectDraw_AddRef((IDirectDraw *)&ddraw->IDirectDraw_vtbl);
                 IDirectDraw2_AddRef((IDirectDraw2 *)&ddraw->IDirectDraw2_vtbl);
+                IDirectDraw3_AddRef((IDirectDraw3 *)&ddraw->IDirectDraw3_vtbl);
                 IDirectDraw4_AddRef((IDirectDraw4 *)&ddraw->IDirectDraw4_vtbl);
                 IDirectDraw7_AddRef((IDirectDraw7 *)ddraw);
 
@@ -948,10 +954,14 @@ DllMain(HINSTANCE hInstDLL,
                     */
                 while(IDirectDraw_Release((IDirectDraw *)&ddraw->IDirectDraw_vtbl));
                 while(IDirectDraw2_Release((IDirectDraw2 *)&ddraw->IDirectDraw2_vtbl));
+                while(IDirectDraw3_Release((IDirectDraw3 *)&ddraw->IDirectDraw3_vtbl));
                 while(IDirectDraw4_Release((IDirectDraw4 *)&ddraw->IDirectDraw4_vtbl));
                 while(IDirectDraw7_Release((IDirectDraw7 *)ddraw));
             }
         }
+
+        /* Unregister the window class. */
+        UnregisterClassA(DDRAW_WINDOW_CLASS_NAME, hInstDLL);
     }
 
     return TRUE;
index d75501e..42d5edc 100644 (file)
 #include "config.h"
 #include "wine/port.h"
 
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-#define NONAMELESSUNION
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
 #include "ddraw_private.h"
-#include "wine/debug.h"
 
-WINE_DEFAULT_DEBUG_CHANNEL(d3d7);
-WINE_DECLARE_DEBUG_CHANNEL(ddraw_thunk);
+WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
 static void dump_material(const D3DMATERIAL *mat)
 {
@@ -85,33 +66,34 @@ IDirect3DMaterialImpl_QueryInterface(IDirect3DMaterial3 *iface,
                                      LPVOID* obp)
 {
     IDirect3DMaterialImpl *This = (IDirect3DMaterialImpl *)iface;
-    TRACE("(%p)->(%s,%p)\n", This, debugstr_guid(riid), obp);
+
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obp);
 
     *obp = NULL;
 
     if ( IsEqualGUID( &IID_IUnknown,  riid ) ) {
         IUnknown_AddRef(iface);
-       *obp = iface;
-       TRACE("  Creating IUnknown interface at %p.\n", *obp);
-       return S_OK;
+        *obp = iface;
+        TRACE("  Creating IUnknown interface at %p.\n", *obp);
+        return S_OK;
     }
     if ( IsEqualGUID( &IID_IDirect3DMaterial, riid ) ) {
         IDirect3DMaterial_AddRef((IDirect3DMaterial *)&This->IDirect3DMaterial_vtbl);
         *obp = &This->IDirect3DMaterial_vtbl;
-       TRACE("  Creating IDirect3DMaterial interface %p\n", *obp);
-       return S_OK;
+        TRACE("  Creating IDirect3DMaterial interface %p\n", *obp);
+        return S_OK;
     }
     if ( IsEqualGUID( &IID_IDirect3DMaterial2, riid ) ) {
         IDirect3DMaterial_AddRef((IDirect3DMaterial2 *)&This->IDirect3DMaterial2_vtbl);
         *obp = &This->IDirect3DMaterial2_vtbl;
-       TRACE("  Creating IDirect3DMaterial2 interface %p\n", *obp);
-       return S_OK;
+        TRACE("  Creating IDirect3DMaterial2 interface %p\n", *obp);
+        return S_OK;
     }
     if ( IsEqualGUID( &IID_IDirect3DMaterial3, riid ) ) {
         IDirect3DMaterial3_AddRef((IDirect3DMaterial3 *)This);
         *obp = This;
-       TRACE("  Creating IDirect3DMaterial3 interface %p\n", *obp);
-       return S_OK;
+        TRACE("  Creating IDirect3DMaterial3 interface %p\n", *obp);
+        return S_OK;
     }
     FIXME("(%p): interface for IID %s NOT found!\n", This, debugstr_guid(riid));
     return E_NOINTERFACE;
@@ -132,7 +114,7 @@ IDirect3DMaterialImpl_AddRef(IDirect3DMaterial3 *iface)
     IDirect3DMaterialImpl *This = (IDirect3DMaterialImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    TRACE("(%p)->() incrementing from %u.\n", This, ref - 1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -153,15 +135,14 @@ IDirect3DMaterialImpl_Release(IDirect3DMaterial3 *iface)
     IDirect3DMaterialImpl *This = (IDirect3DMaterialImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
 
-    TRACE("(%p)->() decrementing from %u.\n", This, ref + 1);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (!ref)
     {
         if(This->Handle)
         {
             EnterCriticalSection(&ddraw_cs);
-            This->ddraw->d3ddevice->Handles[This->Handle - 1].ptr = NULL;
-            This->ddraw->d3ddevice->Handles[This->Handle - 1].type = DDrawHandle_Unknown;
+            ddraw_free_handle(&This->ddraw->d3ddevice->handle_table, This->Handle - 1, DDRAW_HANDLE_MATERIAL);
             LeaveCriticalSection(&ddraw_cs);
         }
 
@@ -191,9 +172,7 @@ static HRESULT WINAPI
 IDirect3DMaterialImpl_Initialize(IDirect3DMaterial *iface,
                                   IDirect3D *Direct3D)
 {
-    IDirect3DMaterialImpl *This = material_from_material1(iface);
-
-    TRACE("(%p)->(%p) no-op...!\n", This, Direct3D);
+    TRACE("iface %p, d3d %p.\n", iface, Direct3D);
 
     return D3D_OK;
 }
@@ -211,8 +190,7 @@ IDirect3DMaterialImpl_Initialize(IDirect3DMaterial *iface,
 static HRESULT WINAPI
 IDirect3DMaterialImpl_Reserve(IDirect3DMaterial *iface)
 {
-    IDirect3DMaterialImpl *This = material_from_material1(iface);
-    TRACE("(%p)->() not implemented\n", This);
+    TRACE("iface %p.\n", iface);
 
     return DDERR_UNSUPPORTED;
 }
@@ -229,8 +207,7 @@ IDirect3DMaterialImpl_Reserve(IDirect3DMaterial *iface)
 static HRESULT WINAPI
 IDirect3DMaterialImpl_Unreserve(IDirect3DMaterial *iface)
 {
-    IDirect3DMaterialImpl *This = material_from_material1(iface);
-    TRACE("(%p)->() not implemented.\n", This);
+    TRACE("iface %p.\n", iface);
 
     return DDERR_UNSUPPORTED;
 }
@@ -253,8 +230,9 @@ IDirect3DMaterialImpl_SetMaterial(IDirect3DMaterial3 *iface,
                                   D3DMATERIAL *lpMat)
 {
     IDirect3DMaterialImpl *This = (IDirect3DMaterialImpl *)iface;
-    TRACE("(%p)->(%p)\n", This, lpMat);
-    if (TRACE_ON(d3d7))
+
+    TRACE("iface %p, material %p.\n", iface, lpMat);
+    if (TRACE_ON(ddraw))
         dump_material(lpMat);
 
     /* Stores the material */
@@ -285,8 +263,10 @@ IDirect3DMaterialImpl_GetMaterial(IDirect3DMaterial3 *iface,
 {
     IDirect3DMaterialImpl *This = (IDirect3DMaterialImpl *)iface;
     DWORD dwSize;
-    TRACE("(%p)->(%p)\n", This, lpMat);
-    if (TRACE_ON(d3d7)) {
+
+    TRACE("iface %p, material %p.\n", iface, lpMat);
+    if (TRACE_ON(ddraw))
+    {
         TRACE("  Returning material : ");
         dump_material(&This->mat);
     }
@@ -322,21 +302,22 @@ IDirect3DMaterialImpl_GetHandle(IDirect3DMaterial3 *iface,
 {
     IDirect3DMaterialImpl *This = (IDirect3DMaterialImpl *)iface;
     IDirect3DDeviceImpl *device = device_from_device3(lpDirect3DDevice3);
-    TRACE("(%p/%p)->(%p,%p)\n", This, iface, device, lpHandle);
+
+    TRACE("iface %p, device %p, handle %p.\n", iface, lpDirect3DDevice3, lpHandle);
 
     EnterCriticalSection(&ddraw_cs);
     This->active_device = device;
     if(!This->Handle)
     {
-        This->Handle = IDirect3DDeviceImpl_CreateHandle(device);
-        if(!This->Handle)
+        DWORD h = ddraw_allocate_handle(&device->handle_table, This, DDRAW_HANDLE_MATERIAL);
+        if (h == DDRAW_INVALID_HANDLE)
         {
-            ERR("Error creating a handle\n");
+            ERR("Failed to allocate a material handle.\n");
             LeaveCriticalSection(&ddraw_cs);
             return DDERR_INVALIDPARAMS;   /* Unchecked */
         }
-        device->Handles[This->Handle - 1].ptr = This;
-        device->Handles[This->Handle - 1].type = DDrawHandle_Material;
+
+        This->Handle = h + 1;
     }
     *lpHandle = This->Handle;
     TRACE(" returning handle %08x.\n", *lpHandle);
@@ -345,22 +326,20 @@ IDirect3DMaterialImpl_GetHandle(IDirect3DMaterial3 *iface,
     return D3D_OK;
 }
 
-static HRESULT WINAPI
-Thunk_IDirect3DMaterialImpl_2_GetHandle(LPDIRECT3DMATERIAL2 iface,
-                                       LPDIRECT3DDEVICE2 lpDirect3DDevice2,
-                                       LPD3DMATERIALHANDLE lpHandle)
+static HRESULT WINAPI Thunk_IDirect3DMaterialImpl_2_GetHandle(IDirect3DMaterial2 *iface,
+        IDirect3DDevice2 *lpDirect3DDevice2, D3DMATERIALHANDLE *lpHandle)
 {
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p) thunking to IDirect3DMaterial3 interface.\n", iface, lpDirect3DDevice2, lpHandle);
+    TRACE("iface %p, device %p, handle %p.\n", iface, lpDirect3DDevice2, lpHandle);
+
     return IDirect3DMaterial3_GetHandle((IDirect3DMaterial3 *)material_from_material2(iface), lpDirect3DDevice2 ?
             (IDirect3DDevice3 *)&device_from_device2(lpDirect3DDevice2)->IDirect3DDevice3_vtbl : NULL, lpHandle);
 }
 
-static HRESULT WINAPI
-Thunk_IDirect3DMaterialImpl_1_GetHandle(LPDIRECT3DMATERIAL iface,
-                                       LPDIRECT3DDEVICE lpDirect3DDevice,
-                                       LPD3DMATERIALHANDLE lpHandle)
+static HRESULT WINAPI Thunk_IDirect3DMaterialImpl_1_GetHandle(IDirect3DMaterial *iface,
+        IDirect3DDevice *lpDirect3DDevice, D3DMATERIALHANDLE *lpHandle)
 {
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p) thunking to IDirect3DMaterial3 interface.\n", iface, lpDirect3DDevice, lpHandle);
+    TRACE("iface %p, device %p, handle %p.\n", iface, lpDirect3DDevice, lpHandle);
+
     return IDirect3DMaterial3_GetHandle((IDirect3DMaterial3 *)material_from_material1(iface), lpDirect3DDevice ?
             (IDirect3DDevice3 *)&device_from_device1(lpDirect3DDevice)->IDirect3DDevice3_vtbl : NULL, lpHandle);
 }
@@ -370,7 +349,8 @@ Thunk_IDirect3DMaterialImpl_2_QueryInterface(LPDIRECT3DMATERIAL2 iface,
                                              REFIID riid,
                                              LPVOID* obp)
 {
-    TRACE_(ddraw_thunk)("(%p)->(%s,%p) thunking to IDirect3DMaterial3 interface.\n", iface, debugstr_guid(riid), obp);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obp);
+
     return IDirect3DMaterial3_QueryInterface((IDirect3DMaterial3 *)material_from_material2(iface), riid, obp);
 }
 
@@ -379,35 +359,40 @@ Thunk_IDirect3DMaterialImpl_1_QueryInterface(LPDIRECT3DMATERIAL iface,
                                              REFIID riid,
                                              LPVOID* obp)
 {
-    TRACE_(ddraw_thunk)("(%p)->(%s,%p) thunking to IDirect3DMaterial3 interface.\n", iface, debugstr_guid(riid), obp);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obp);
+
     return IDirect3DMaterial3_QueryInterface((IDirect3DMaterial3 *)material_from_material1(iface), riid, obp);
 }
 
 static ULONG WINAPI
 Thunk_IDirect3DMaterialImpl_2_AddRef(LPDIRECT3DMATERIAL2 iface)
 {
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DMaterial3 interface.\n", iface);
+    TRACE("iface %p.\n", iface);
+
     return IDirect3DMaterial3_AddRef((IDirect3DMaterial3 *)material_from_material2(iface));
 }
 
 static ULONG WINAPI
 Thunk_IDirect3DMaterialImpl_1_AddRef(LPDIRECT3DMATERIAL iface)
 {
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DMaterial3 interface.\n", iface);
+    TRACE("iface %p.\n", iface);
+
     return IDirect3DMaterial3_AddRef((IDirect3DMaterial3 *)material_from_material1(iface));
 }
 
 static ULONG WINAPI
 Thunk_IDirect3DMaterialImpl_2_Release(LPDIRECT3DMATERIAL2 iface)
 {
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DMaterial3 interface.\n", iface);
+    TRACE("iface %p.\n", iface);
+
     return IDirect3DMaterial3_Release((IDirect3DMaterial3 *)material_from_material2(iface));
 }
 
 static ULONG WINAPI
 Thunk_IDirect3DMaterialImpl_1_Release(LPDIRECT3DMATERIAL iface)
 {
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DMaterial3 interface.\n", iface);
+    TRACE("iface %p.\n", iface);
+
     return IDirect3DMaterial3_Release((IDirect3DMaterial3 *)material_from_material1(iface));
 }
 
@@ -415,7 +400,8 @@ static HRESULT WINAPI
 Thunk_IDirect3DMaterialImpl_2_SetMaterial(LPDIRECT3DMATERIAL2 iface,
                                           LPD3DMATERIAL lpMat)
 {
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DMaterial3 interface.\n", iface, lpMat);
+    TRACE("iface %p, material %p.\n", iface, lpMat);
+
     return IDirect3DMaterial3_SetMaterial((IDirect3DMaterial3 *)material_from_material2(iface), lpMat);
 }
 
@@ -423,7 +409,8 @@ static HRESULT WINAPI
 Thunk_IDirect3DMaterialImpl_1_SetMaterial(LPDIRECT3DMATERIAL iface,
                                           LPD3DMATERIAL lpMat)
 {
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DMaterial3 interface.\n", iface, lpMat);
+    TRACE("iface %p, material %p.\n", iface, lpMat);
+
     return IDirect3DMaterial3_SetMaterial((IDirect3DMaterial3 *)material_from_material1(iface), lpMat);
 }
 
@@ -431,7 +418,8 @@ static HRESULT WINAPI
 Thunk_IDirect3DMaterialImpl_2_GetMaterial(LPDIRECT3DMATERIAL2 iface,
                                           LPD3DMATERIAL lpMat)
 {
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DMaterial3 interface.\n", iface, lpMat);
+    TRACE("iface %p, material %p.\n", iface, lpMat);
+
     return IDirect3DMaterial3_GetMaterial((IDirect3DMaterial3 *)material_from_material2(iface), lpMat);
 }
 
@@ -439,7 +427,8 @@ static HRESULT WINAPI
 Thunk_IDirect3DMaterialImpl_1_GetMaterial(LPDIRECT3DMATERIAL iface,
                                           LPD3DMATERIAL lpMat)
 {
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DMaterial3 interface.\n", iface, lpMat);
+    TRACE("iface %p, material %p.\n", iface, lpMat);
+
     return IDirect3DMaterial3_GetMaterial((IDirect3DMaterial3 *)material_from_material1(iface), lpMat);
 }
 
@@ -467,7 +456,7 @@ void material_activate(IDirect3DMaterialImpl* This)
     IDirect3DDevice7_SetMaterial((IDirect3DDevice7 *)This->active_device, &d3d7mat);
 }
 
-const IDirect3DMaterial3Vtbl IDirect3DMaterial3_Vtbl =
+static const struct IDirect3DMaterial3Vtbl d3d_material3_vtbl =
 {
     /*** IUnknown Methods ***/
     IDirect3DMaterialImpl_QueryInterface,
@@ -479,7 +468,7 @@ const IDirect3DMaterial3Vtbl IDirect3DMaterial3_Vtbl =
     IDirect3DMaterialImpl_GetHandle,
 };
 
-const IDirect3DMaterial2Vtbl IDirect3DMaterial2_Vtbl =
+static const struct IDirect3DMaterial2Vtbl d3d_material2_vtbl =
 {
     /*** IUnknown Methods ***/
     Thunk_IDirect3DMaterialImpl_2_QueryInterface,
@@ -491,7 +480,7 @@ const IDirect3DMaterial2Vtbl IDirect3DMaterial2_Vtbl =
     Thunk_IDirect3DMaterialImpl_2_GetHandle,
 };
 
-const IDirect3DMaterialVtbl IDirect3DMaterial_Vtbl =
+static const struct IDirect3DMaterialVtbl d3d_material1_vtbl =
 {
     /*** IUnknown Methods ***/
     Thunk_IDirect3DMaterialImpl_1_QueryInterface,
@@ -505,3 +494,12 @@ const IDirect3DMaterialVtbl IDirect3DMaterial_Vtbl =
     IDirect3DMaterialImpl_Reserve,
     IDirect3DMaterialImpl_Unreserve
 };
+
+void d3d_material_init(IDirect3DMaterialImpl *material, IDirectDrawImpl *ddraw)
+{
+    material->lpVtbl = &d3d_material3_vtbl;
+    material->IDirect3DMaterial2_vtbl = &d3d_material2_vtbl;
+    material->IDirect3DMaterial_vtbl = &d3d_material1_vtbl;
+    material->ref = 1;
+    material->ddraw = ddraw;
+}
index 9ef0a7c..7064ba0 100644 (file)
@@ -1,5 +1,4 @@
-/*             DirectDraw - IDirectPalette base interface
- *
+/*
  * Copyright 2006 Stefan Dösinger
  *
  * This library is free software; you can redistribute it and/or
  */
 
 #include "config.h"
-#include "winerror.h"
-#include "wine/debug.h"
-
-#define COBJMACROS
-
-#include <assert.h>
-#include <string.h>
+#include "wine/port.h"
 
 #include "ddraw_private.h"
 
@@ -49,8 +42,7 @@ IDirectDrawPaletteImpl_QueryInterface(IDirectDrawPalette *iface,
                                       REFIID refiid,
                                       void **obj)
 {
-    IDirectDrawPaletteImpl *This = (IDirectDrawPaletteImpl *)iface;
-    TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(refiid),obj);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(refiid), obj);
 
     if (IsEqualGUID(refiid, &IID_IUnknown)
         || IsEqualGUID(refiid, &IID_IDirectDrawPalette))
@@ -81,7 +73,7 @@ IDirectDrawPaletteImpl_AddRef(IDirectDrawPalette *iface)
     IDirectDrawPaletteImpl *This = (IDirectDrawPaletteImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    TRACE("(%p)->() incrementing from %u.\n", This, ref - 1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -101,7 +93,7 @@ IDirectDrawPaletteImpl_Release(IDirectDrawPalette *iface)
     IDirectDrawPaletteImpl *This = (IDirectDrawPaletteImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
 
-    TRACE("(%p)->() decrementing from %u.\n", This, ref + 1);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (ref == 0)
     {
@@ -139,7 +131,9 @@ IDirectDrawPaletteImpl_Initialize(IDirectDrawPalette *iface,
                                   DWORD Flags,
                                   PALETTEENTRY *ColorTable)
 {
-    TRACE("(%p)->(%p,%x,%p)\n", iface, DD, Flags, ColorTable);
+    TRACE("iface %p, ddraw %p, flags %#x, entries %p.\n",
+            iface, DD, Flags, ColorTable);
+
     return DDERR_ALREADYINITIALIZED;
 }
 
@@ -163,7 +157,8 @@ IDirectDrawPaletteImpl_GetCaps(IDirectDrawPalette *iface,
 {
     IDirectDrawPaletteImpl *This = (IDirectDrawPaletteImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p): Relay\n", This, Caps);
+
+    TRACE("iface %p, caps %p.\n", iface, Caps);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DPalette_GetCaps(This->wineD3DPalette, Caps);
@@ -198,7 +193,9 @@ IDirectDrawPaletteImpl_SetEntries(IDirectDrawPalette *iface,
 {
     IDirectDrawPaletteImpl *This = (IDirectDrawPaletteImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%x,%d,%d,%p): Relay\n", This, Flags, Start, Count, PalEnt);
+
+    TRACE("iface %p, flags %#x, start %u, count %u, entries %p.\n",
+            iface, Flags, Start, Count, PalEnt);
 
     if(!PalEnt)
         return DDERR_INVALIDPARAMS;
@@ -235,7 +232,9 @@ IDirectDrawPaletteImpl_GetEntries(IDirectDrawPalette *iface,
 {
     IDirectDrawPaletteImpl *This = (IDirectDrawPaletteImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%x,%d,%d,%p): Relay\n", This, Flags, Start, Count, PalEnt);
+
+    TRACE("iface %p, flags %#x, start %u, count %u, entries %p.\n",
+            iface, Flags, Start, Count, PalEnt);
 
     if(!PalEnt)
         return DDERR_INVALIDPARAMS;
@@ -246,7 +245,7 @@ IDirectDrawPaletteImpl_GetEntries(IDirectDrawPalette *iface,
     return hr;
 }
 
-const IDirectDrawPaletteVtbl IDirectDrawPalette_Vtbl =
+static const struct IDirectDrawPaletteVtbl ddraw_palette_vtbl =
 {
     /*** IUnknown ***/
     IDirectDrawPaletteImpl_QueryInterface,
@@ -258,3 +257,25 @@ const IDirectDrawPaletteVtbl IDirectDrawPalette_Vtbl =
     IDirectDrawPaletteImpl_Initialize,
     IDirectDrawPaletteImpl_SetEntries
 };
+
+HRESULT ddraw_palette_init(IDirectDrawPaletteImpl *palette,
+        IDirectDrawImpl *ddraw, DWORD flags, PALETTEENTRY *entries)
+{
+    HRESULT hr;
+
+    palette->lpVtbl = &ddraw_palette_vtbl;
+    palette->ref = 1;
+
+    hr = IWineD3DDevice_CreatePalette(ddraw->wineD3DDevice, flags,
+            entries, palette, &palette->wineD3DPalette);
+    if (FAILED(hr))
+    {
+        WARN("Failed to create wined3d palette, hr %#x.\n", hr);
+        return hr;
+    }
+
+    palette->ifaceToRelease = (IUnknown *)ddraw;
+    IUnknown_AddRef(palette->ifaceToRelease);
+
+    return DD_OK;
+}
index 473152e..871f066 100644 (file)
 
 #include "config.h"
 #include "wine/port.h"
-#include "wine/debug.h"
-
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
 
 #include "ddraw_private.h"
 
@@ -68,7 +51,7 @@ IParentImpl_QueryInterface(IParent *iface,
                            REFIID riid,
                            void **obj)
 {
-    TRACE("(%p)->(%s,%p)\n", iface, debugstr_guid(riid), obj);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obj);
 
     *obj = NULL;
     if ( IsEqualGUID( &IID_IUnknown, riid ) ||
@@ -98,7 +81,7 @@ IParentImpl_AddRef(IParent *iface)
     IParentImpl *This = (IParentImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    TRACE("(%p) : AddRef from %d\n", This, ref - 1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -122,7 +105,7 @@ static ULONG WINAPI IParentImpl_Release(IParent *iface)
     IParentImpl *This = (IParentImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
 
-    TRACE("(%p) : ReleaseRef to %d\n", This, ref);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (ref == 0)
     {
@@ -138,9 +121,15 @@ static ULONG WINAPI IParentImpl_Release(IParent *iface)
 /*****************************************************************************
  * The VTable
  *****************************************************************************/
-const IParentVtbl IParent_Vtbl =
+static const struct IParentVtbl ddraw_parent_vtbl =
 {
      IParentImpl_QueryInterface,
      IParentImpl_AddRef,
      IParentImpl_Release,
 };
+
+void ddraw_parent_init(IParentImpl *parent)
+{
+    parent->lpVtbl = &ddraw_parent_vtbl;
+    parent->ref = 1;
+}
index 6ab75d1..52a6fb7 100644 (file)
  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
  */
 
-#include <stdarg.h>
-#include <string.h>
+#include "config.h"
+#include "wine/port.h"
 
-#include "windef.h"
-#include "winbase.h"
-#include "winreg.h"
-#include "wingdi.h"
-#include "winuser.h"
-#include "winerror.h"
-
-#include "ddraw.h"
-
-#include "wine/debug.h"
+#include "ddraw_private.h"
 #include "wine/unicode.h"
+#include "winreg.h"
 
 WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
index 44be26c..cff2f95 100644 (file)
 #include "config.h"
 #include "wine/port.h"
 
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-#define NONAMELESSUNION
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
 #include "ddraw_private.h"
-#include "wine/debug.h"
 
 WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
+static inline IDirectDrawSurfaceImpl *surface_from_gamma_control(IDirectDrawGammaControl *iface)
+{
+    return (IDirectDrawSurfaceImpl *)((char*)iface
+            - FIELD_OFFSET(IDirectDrawSurfaceImpl, IDirectDrawGammaControl_vtbl));
+}
+
 /*****************************************************************************
  * IUnknown parts follow
  *****************************************************************************/
@@ -70,20 +58,18 @@ WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
  *  E_NOINTERFACE if the requested interface wasn't found
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_QueryInterface(IDirectDrawSurface7 *iface,
-                                      REFIID riid,
-                                      void **obj)
+static HRESULT WINAPI ddraw_surface7_QueryInterface(IDirectDrawSurface7 *iface, REFIID riid, void **obj)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
 
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obj);
+
     /* According to COM docs, if the QueryInterface fails, obj should be set to NULL */
     *obj = NULL;
 
     if(!riid)
         return DDERR_INVALIDPARAMS;
 
-    TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(riid),obj);
     if (IsEqualGUID(riid, &IID_IUnknown)
      || IsEqualGUID(riid, &IID_IDirectDrawSurface7)
      || IsEqualGUID(riid, &IID_IDirectDrawSurface4) )
@@ -118,10 +104,15 @@ IDirectDrawSurfaceImpl_QueryInterface(IDirectDrawSurface7 *iface,
         /* Call into IDirect3D7 for creation */
         IDirect3D7_CreateDevice((IDirect3D7 *)&This->ddraw->IDirect3D7_vtbl, riid, (IDirectDrawSurface7 *)This, &d3d);
 
-        *obj = d3d ? (IDirect3DDevice *)&((IDirect3DDeviceImpl *)d3d)->IDirect3DDevice_vtbl : NULL;
-        TRACE("(%p) Returning IDirect3DDevice interface at %p\n", This, *obj);
+        if (d3d)
+        {
+            *obj = (IDirect3DDevice *)&((IDirect3DDeviceImpl *)d3d)->IDirect3DDevice_vtbl;
+            TRACE("(%p) Returning IDirect3DDevice interface at %p\n", This, *obj);
+            return S_OK;
+        }
 
-        return S_OK;
+        WARN("Unable to create a IDirect3DDevice instance, returning E_NOINTERFACE\n");
+        return E_NOINTERFACE;
     }
     else if (IsEqualGUID( &IID_IDirect3DTexture, riid ) ||
              IsEqualGUID( &IID_IDirect3DTexture2, riid ))
@@ -144,6 +135,34 @@ IDirectDrawSurfaceImpl_QueryInterface(IDirectDrawSurface7 *iface,
     return E_NOINTERFACE;
 }
 
+static HRESULT WINAPI ddraw_surface3_QueryInterface(IDirectDrawSurface3 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw_surface7_QueryInterface((IDirectDrawSurface7 *)surface_from_surface3(iface), riid, object);
+}
+
+static HRESULT WINAPI ddraw_gamma_control_QueryInterface(IDirectDrawGammaControl *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw_surface7_QueryInterface((IDirectDrawSurface7 *)surface_from_gamma_control(iface), riid, object);
+}
+
+static HRESULT WINAPI d3d_texture2_QueryInterface(IDirect3DTexture2 *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw_surface7_QueryInterface((IDirectDrawSurface7 *)surface_from_texture2(iface), riid, object);
+}
+
+static HRESULT WINAPI d3d_texture1_QueryInterface(IDirect3DTexture *iface, REFIID riid, void **object)
+{
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    return ddraw_surface7_QueryInterface((IDirectDrawSurface7 *)surface_from_texture1(iface), riid, object);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::AddRef
  *
@@ -153,12 +172,13 @@ IDirectDrawSurfaceImpl_QueryInterface(IDirectDrawSurface7 *iface,
  *  The new refcount
  *
  *****************************************************************************/
-static ULONG WINAPI
-IDirectDrawSurfaceImpl_AddRef(IDirectDrawSurface7 *iface)
+static ULONG WINAPI ddraw_surface7_AddRef(IDirectDrawSurface7 *iface)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     ULONG refCount = InterlockedIncrement(&This->ref);
 
+    TRACE("%p increasing refcount to %u.\n", This, refCount);
+
     if (refCount == 1 && This->WineD3DSurface)
     {
         EnterCriticalSection(&ddraw_cs);
@@ -166,12 +186,39 @@ IDirectDrawSurfaceImpl_AddRef(IDirectDrawSurface7 *iface)
         LeaveCriticalSection(&ddraw_cs);
     }
 
-    TRACE("(%p) : AddRef increasing from %d\n", This, refCount - 1);
     return refCount;
 }
 
+static ULONG WINAPI ddraw_surface3_AddRef(IDirectDrawSurface3 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_AddRef((IDirectDrawSurface7 *)surface_from_surface3(iface));
+}
+
+static ULONG WINAPI ddraw_gamma_control_AddRef(IDirectDrawGammaControl *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_AddRef((IDirectDrawSurface7 *)surface_from_gamma_control(iface));
+}
+
+static ULONG WINAPI d3d_texture2_AddRef(IDirect3DTexture2 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_AddRef((IDirectDrawSurface7 *)surface_from_texture2(iface));
+}
+
+static ULONG WINAPI d3d_texture1_AddRef(IDirect3DTexture *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_AddRef((IDirectDrawSurface7 *)surface_from_texture1(iface));
+}
+
 /*****************************************************************************
- * IDirectDrawSurfaceImpl_Destroy
+ * ddraw_surface_destroy
  *
  * A helper function for IDirectDrawSurface7::Release
  *
@@ -182,9 +229,9 @@ IDirectDrawSurfaceImpl_AddRef(IDirectDrawSurface7 *iface)
  *  This: Surface to free
  *
  *****************************************************************************/
-void IDirectDrawSurfaceImpl_Destroy(IDirectDrawSurfaceImpl *This)
+void ddraw_surface_destroy(IDirectDrawSurfaceImpl *This)
 {
-    TRACE("(%p)\n", This);
+    TRACE("surface %p.\n", This);
 
     /* Check the refcount and give a warning */
     if(This->ref > 1)
@@ -235,8 +282,7 @@ void IDirectDrawSurfaceImpl_Destroy(IDirectDrawSurfaceImpl *This)
     /* Having a texture handle set implies that the device still exists */
     if(This->Handle)
     {
-        This->ddraw->d3ddevice->Handles[This->Handle - 1].ptr = NULL;
-        This->ddraw->d3ddevice->Handles[This->Handle - 1].type = DDrawHandle_Unknown;
+        ddraw_free_handle(&This->ddraw->d3ddevice->handle_table, This->Handle - 1, DDRAW_HANDLE_SURFACE);
     }
 
     /* Reduce the ddraw surface count */
@@ -275,13 +321,12 @@ void IDirectDrawSurfaceImpl_Destroy(IDirectDrawSurfaceImpl *This)
  *  The new refcount
  *
  *****************************************************************************/
-static ULONG WINAPI
-IDirectDrawSurfaceImpl_Release(IDirectDrawSurface7 *iface)
+static ULONG WINAPI ddraw_surface7_Release(IDirectDrawSurface7 *iface)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    ULONG ref;
-    TRACE("(%p) : Releasing from %d\n", This, This->ref);
-    ref = InterlockedDecrement(&This->ref);
+    ULONG ref = InterlockedDecrement(&This->ref);
+
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (ref == 0)
     {
@@ -385,13 +430,12 @@ IDirectDrawSurfaceImpl_Release(IDirectDrawSurface7 *iface)
             {
                 IDirectDrawSurfaceImpl *destroy = surf;
                 surf = surf->complex_array[0];              /* Iterate through the "tree" */
-                IDirectDrawSurfaceImpl_Destroy(destroy);    /* Destroy it */
+                ddraw_surface_destroy(destroy);             /* Destroy it */
             }
         }
 
-        /* Destroy the root surface.
-         */
-        IDirectDrawSurfaceImpl_Destroy(This);
+        /* Destroy the root surface. */
+        ddraw_surface_destroy(This);
 
         /* Reduce the ddraw refcount */
         if(ifaceToRelease) IUnknown_Release(ifaceToRelease);
@@ -401,6 +445,34 @@ IDirectDrawSurfaceImpl_Release(IDirectDrawSurface7 *iface)
     return ref;
 }
 
+static ULONG WINAPI ddraw_surface3_Release(IDirectDrawSurface3 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_Release((IDirectDrawSurface7 *)surface_from_surface3(iface));
+}
+
+static ULONG WINAPI ddraw_gamma_control_Release(IDirectDrawGammaControl *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_Release((IDirectDrawSurface7 *)surface_from_gamma_control(iface));
+}
+
+static ULONG WINAPI d3d_texture2_Release(IDirect3DTexture2 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_Release((IDirectDrawSurface7 *)surface_from_texture2(iface));
+}
+
+static ULONG WINAPI d3d_texture1_Release(IDirect3DTexture *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_Release((IDirectDrawSurface7 *)surface_from_texture1(iface));
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetAttachedSurface
  *
@@ -428,17 +500,16 @@ IDirectDrawSurfaceImpl_Release(IDirectDrawSurface7 *iface)
  *  DDERR_NOTFOUND if no surface was found
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetAttachedSurface(IDirectDrawSurface7 *iface,
-                                          DDSCAPS2 *Caps,
-                                          IDirectDrawSurface7 **Surface)
+static HRESULT WINAPI ddraw_surface7_GetAttachedSurface(IDirectDrawSurface7 *iface,
+        DDSCAPS2 *Caps, IDirectDrawSurface7 **Surface)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawSurfaceImpl *surf;
     DDSCAPS2 our_caps;
     int i;
 
-    TRACE("(%p)->(%p,%p)\n", This, Caps, Surface);
+    TRACE("iface %p, caps %p, attachment %p.\n", iface, Caps, Surface);
+
     EnterCriticalSection(&ddraw_cs);
 
     if(This->version < 7)
@@ -482,7 +553,7 @@ IDirectDrawSurfaceImpl_GetAttachedSurface(IDirectDrawSurface7 *iface,
             TRACE("(%p): Returning surface %p\n", This, surf);
             TRACE("(%p): mipmapcount=%d\n", This, surf->mipmap_level);
             *Surface = (IDirectDrawSurface7 *)surf;
-            IDirectDrawSurface7_AddRef(*Surface);
+            ddraw_surface7_AddRef(*Surface);
             LeaveCriticalSection(&ddraw_cs);
             return DD_OK;
         }
@@ -507,7 +578,7 @@ IDirectDrawSurfaceImpl_GetAttachedSurface(IDirectDrawSurface7 *iface,
 
             TRACE("(%p): Returning surface %p\n", This, surf);
             *Surface = (IDirectDrawSurface7 *)surf;
-            IDirectDrawSurface7_AddRef(*Surface);
+            ddraw_surface7_AddRef(*Surface);
             LeaveCriticalSection(&ddraw_cs);
             return DD_OK;
         }
@@ -520,6 +591,29 @@ IDirectDrawSurfaceImpl_GetAttachedSurface(IDirectDrawSurface7 *iface,
     return DDERR_NOTFOUND;
 }
 
+static HRESULT WINAPI ddraw_surface3_GetAttachedSurface(IDirectDrawSurface3 *iface,
+        DDSCAPS *caps, IDirectDrawSurface3 **attachment)
+{
+    IDirectDrawSurface7 *attachment7;
+    DDSCAPS2 caps2;
+    HRESULT hr;
+
+    TRACE("iface %p, caps %p, attachment %p.\n", iface, caps, attachment);
+
+    caps2.dwCaps  = caps->dwCaps;
+    caps2.dwCaps2 = 0;
+    caps2.dwCaps3 = 0;
+    caps2.u1.dwCaps4 = 0;
+
+    hr = ddraw_surface7_GetAttachedSurface((IDirectDrawSurface7 *)surface_from_surface3(iface),
+            &caps2, &attachment7);
+    if (FAILED(hr)) *attachment = NULL;
+    else *attachment = attachment7 ?
+            (IDirectDrawSurface3 *)&((IDirectDrawSurfaceImpl *)attachment7)->IDirectDrawSurface3_vtbl : NULL;
+
+    return hr;
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::Lock
  *
@@ -537,17 +631,15 @@ IDirectDrawSurfaceImpl_GetAttachedSurface(IDirectDrawSurface7 *iface,
  *  For more details, see IWineD3DSurface::LockRect
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_Lock(IDirectDrawSurface7 *iface,
-                            RECT *Rect,
-                            DDSURFACEDESC2 *DDSD,
-                            DWORD Flags,
-                            HANDLE h)
+static HRESULT WINAPI ddraw_surface7_Lock(IDirectDrawSurface7 *iface,
+        RECT *Rect, DDSURFACEDESC2 *DDSD, DWORD Flags, HANDLE h)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     WINED3DLOCKED_RECT LockedRect;
     HRESULT hr;
-    TRACE("(%p)->(%p,%p,%x,%p)\n", This, Rect, DDSD, Flags, h);
+
+    TRACE("iface %p, rect %s, surface_desc %p, flags %#x, h %p.\n",
+            iface, wine_dbgstr_rect(Rect), DDSD, Flags, h);
 
     if(!DDSD)
         return DDERR_INVALIDPARAMS;
@@ -621,6 +713,16 @@ IDirectDrawSurfaceImpl_Lock(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_Lock(IDirectDrawSurface3 *iface, RECT *rect,
+        DDSURFACEDESC *surface_desc, DWORD flags, HANDLE h)
+{
+    TRACE("iface %p, rect %s, surface_desc %p, flags %#x, h %p.\n",
+            iface, wine_dbgstr_rect(rect), surface_desc, flags, h);
+
+    return ddraw_surface7_Lock((IDirectDrawSurface7 *)surface_from_surface3(iface),
+            rect, (DDSURFACEDESC2 *)surface_desc, flags, h);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::Unlock
  *
@@ -634,13 +736,12 @@ IDirectDrawSurfaceImpl_Lock(IDirectDrawSurface7 *iface,
  *  For more details, see IWineD3DSurface::UnlockRect
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_Unlock(IDirectDrawSurface7 *iface,
-                              RECT *pRect)
+static HRESULT WINAPI ddraw_surface7_Unlock(IDirectDrawSurface7 *iface, RECT *pRect)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p)\n", This, pRect);
+
+    TRACE("iface %p, rect %s.\n", iface, wine_dbgstr_rect(pRect));
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_UnlockRect(This->WineD3DSurface);
@@ -652,6 +753,14 @@ IDirectDrawSurfaceImpl_Unlock(IDirectDrawSurface7 *iface,
     return hr;
 }
 
+static HRESULT WINAPI ddraw_surface3_Unlock(IDirectDrawSurface3 *iface, void *data)
+{
+    TRACE("iface %p, data %p.\n", iface, data);
+
+    /* data might not be the LPRECT of later versions, so drop it. */
+    return ddraw_surface7_Unlock((IDirectDrawSurface7 *)surface_from_surface3(iface), NULL);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::Flip
  *
@@ -671,16 +780,14 @@ IDirectDrawSurfaceImpl_Unlock(IDirectDrawSurface7 *iface,
  *  For more details, see IWineD3DSurface::Flip
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_Flip(IDirectDrawSurface7 *iface,
-                            IDirectDrawSurface7 *DestOverride,
-                            DWORD Flags)
+static HRESULT WINAPI ddraw_surface7_Flip(IDirectDrawSurface7 *iface, IDirectDrawSurface7 *DestOverride, DWORD Flags)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawSurfaceImpl *Override = (IDirectDrawSurfaceImpl *)DestOverride;
     IDirectDrawSurface7 *Override7;
     HRESULT hr;
-    TRACE("(%p)->(%p,%x)\n", This, DestOverride, Flags);
+
+    TRACE("iface %p, dst %p, flags %#x.\n", iface, DestOverride, Flags);
 
     /* Flip has to be called from a front buffer
      * What about overlay surfaces, AFAIK they can flip too?
@@ -697,7 +804,7 @@ IDirectDrawSurfaceImpl_Flip(IDirectDrawSurface7 *iface,
 
         memset(&Caps, 0, sizeof(Caps));
         Caps.dwCaps |= DDSCAPS_BACKBUFFER;
-        hr = IDirectDrawSurface7_GetAttachedSurface(iface, &Caps, &Override7);
+        hr = ddraw_surface7_GetAttachedSurface(iface, &Caps, &Override7);
         if(hr != DD_OK)
         {
             ERR("Can't find a flip target\n");
@@ -707,7 +814,7 @@ IDirectDrawSurfaceImpl_Flip(IDirectDrawSurface7 *iface,
         Override = (IDirectDrawSurfaceImpl *)Override7;
 
         /* For the GetAttachedSurface */
-        IDirectDrawSurface7_Release(Override7);
+        ddraw_surface7_Release(Override7);
     }
 
     hr = IWineD3DSurface_Flip(This->WineD3DSurface,
@@ -717,6 +824,14 @@ IDirectDrawSurfaceImpl_Flip(IDirectDrawSurface7 *iface,
     return hr;
 }
 
+static HRESULT WINAPI ddraw_surface3_Flip(IDirectDrawSurface3 *iface, IDirectDrawSurface3 *dst, DWORD flags)
+{
+    TRACE("iface %p, dst %p, flags %#x.\n", iface, dst, flags);
+
+    return ddraw_surface7_Flip((IDirectDrawSurface7 *)surface_from_surface3(iface),
+            dst ? (IDirectDrawSurface7 *)surface_from_surface3(dst) : NULL, flags);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::Blt
  *
@@ -734,18 +849,15 @@ IDirectDrawSurfaceImpl_Flip(IDirectDrawSurface7 *iface,
  *  See IWineD3DSurface::Blt for more details
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_Blt(IDirectDrawSurface7 *iface,
-                           RECT *DestRect,
-                           IDirectDrawSurface7 *SrcSurface,
-                           RECT *SrcRect,
-                           DWORD Flags,
-                           DDBLTFX *DDBltFx)
+static HRESULT WINAPI ddraw_surface7_Blt(IDirectDrawSurface7 *iface, RECT *DestRect,
+        IDirectDrawSurface7 *SrcSurface, RECT *SrcRect, DWORD Flags, DDBLTFX *DDBltFx)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawSurfaceImpl *Src = (IDirectDrawSurfaceImpl *)SrcSurface;
     HRESULT hr;
-    TRACE("(%p)->(%p,%p,%p,%x,%p)\n", This, DestRect, Src, SrcRect, Flags, DDBltFx);
+
+    TRACE("iface %p, dst_rect %s, src_surface %p, src_rect %p, flags %#x, fx %p.\n",
+            iface, wine_dbgstr_rect(DestRect), SrcSurface, wine_dbgstr_rect(SrcRect), Flags, DDBltFx);
 
     /* Check for validity of the flags here. WineD3D Has the software-opengl selection path and would have
      * to check at 2 places, and sometimes do double checks. This also saves the call to wined3d :-)
@@ -812,6 +924,16 @@ IDirectDrawSurfaceImpl_Blt(IDirectDrawSurface7 *iface,
     }
 }
 
+static HRESULT WINAPI ddraw_surface3_Blt(IDirectDrawSurface3 *iface, RECT *dst_rect,
+        IDirectDrawSurface3 *src_surface, RECT *src_rect, DWORD flags, DDBLTFX *fx)
+{
+    TRACE("iface %p, dst_rect %s, src_surface %p, src_rect %p, flags %#x, fx %p.\n",
+            iface, wine_dbgstr_rect(dst_rect), src_surface, wine_dbgstr_rect(src_rect), flags, fx);
+
+    return ddraw_surface7_Blt((IDirectDrawSurface7 *)surface_from_surface3(iface), dst_rect,
+            src_surface ? (IDirectDrawSurface7 *)surface_from_surface3(src_surface) : NULL, src_rect, flags, fx);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::AddAttachedSurface
  *
@@ -843,8 +965,8 @@ IDirectDrawSurfaceImpl_Blt(IDirectDrawSurface7 *iface,
  * switching between that and double buffering is not yet implemented in
  * WineD3D, so for 3D it might have unexpected results.
  *
- * IDirectDrawSurfaceImpl_AddAttachedSurface is the real thing,
- * IDirectDrawSurface7Impl_AddAttachedSurface is a wrapper around it that
+ * ddraw_surface_attach_surface is the real thing,
+ * ddraw_surface7_AddAttachedSurface is a wrapper around it that
  * performs additional checks. Version 7 of this interface is much more restrictive
  * than its predecessors.
  *
@@ -856,11 +978,9 @@ IDirectDrawSurfaceImpl_Blt(IDirectDrawSurface7 *iface,
  *  DDERR_CANNOTATTACHSURFACE if the surface can't be attached for some reason
  *
  *****************************************************************************/
-HRESULT WINAPI
-IDirectDrawSurfaceImpl_AddAttachedSurface(IDirectDrawSurfaceImpl *This,
-                                          IDirectDrawSurfaceImpl *Surf)
+static HRESULT ddraw_surface_attach_surface(IDirectDrawSurfaceImpl *This, IDirectDrawSurfaceImpl *Surf)
 {
-    TRACE("(%p)->(%p)\n", This, Surf);
+    TRACE("surface %p, attachment %p.\n", This, Surf);
 
     if(Surf == This)
         return DDERR_CANNOTATTACHSURFACE; /* unchecked */
@@ -868,13 +988,14 @@ IDirectDrawSurfaceImpl_AddAttachedSurface(IDirectDrawSurfaceImpl *This,
     EnterCriticalSection(&ddraw_cs);
 
     /* Check if the surface is already attached somewhere */
-    if( (Surf->next_attached != NULL) ||
-        (Surf->first_attached != Surf) )
+    if (Surf->next_attached || Surf->first_attached != Surf)
     {
-        /* TODO: Test for the structure of the manual attachment. Is it a chain or a list?
-         * What happens if one surface is attached to 2 different surfaces?
-         */
-        FIXME("(%p) The Surface %p is already attached somewhere else: next_attached = %p, first_attached = %p, can't handle by now\n", This, Surf, Surf->next_attached, Surf->first_attached);
+        /* TODO: Test for the structure of the manual attachment. Is it a
+         * chain or a list? What happens if one surface is attached to 2
+         * different surfaces? */
+        WARN("Surface %p is already attached somewhere. next_attached %p, first_attached %p.\n",
+                Surf, Surf->next_attached, Surf->first_attached);
+
         LeaveCriticalSection(&ddraw_cs);
         return DDERR_SURFACEALREADYATTACHED;
     }
@@ -890,18 +1011,18 @@ IDirectDrawSurfaceImpl_AddAttachedSurface(IDirectDrawSurfaceImpl *This,
         IDirect3DDeviceImpl_UpdateDepthStencil(This->ddraw->d3ddevice);
     }
 
-    IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)Surf);
+    ddraw_surface7_AddRef((IDirectDrawSurface7 *)Surf);
     LeaveCriticalSection(&ddraw_cs);
     return DD_OK;
 }
 
-static HRESULT WINAPI
-IDirectDrawSurface7Impl_AddAttachedSurface(IDirectDrawSurface7 *iface,
-                                           IDirectDrawSurface7 *Attach)
+static HRESULT WINAPI ddraw_surface7_AddAttachedSurface(IDirectDrawSurface7 *iface, IDirectDrawSurface7 *Attach)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawSurfaceImpl *Surf = (IDirectDrawSurfaceImpl *)Attach;
 
+    TRACE("iface %p, attachment %p.\n", iface, Attach);
+
     /* Version 7 of this interface seems to refuse everything except z buffers, as per msdn */
     if(!(Surf->surface_desc.ddsCaps.dwCaps & DDSCAPS_ZBUFFER))
     {
@@ -911,9 +1032,47 @@ IDirectDrawSurface7Impl_AddAttachedSurface(IDirectDrawSurface7 *iface,
         return DDERR_CANNOTATTACHSURFACE;
     }
 
-    return IDirectDrawSurfaceImpl_AddAttachedSurface(This,
-                                                     Surf);
+    return ddraw_surface_attach_surface(This, Surf);
+}
+
+static HRESULT WINAPI ddraw_surface3_AddAttachedSurface(IDirectDrawSurface3 *iface, IDirectDrawSurface3 *attachment)
+{
+    IDirectDrawSurfaceImpl *surface = surface_from_surface3(iface);
+    IDirectDrawSurfaceImpl *attach_impl = surface_from_surface3(attachment);
+
+    TRACE("iface %p, attachment %p.\n", iface, attachment);
+
+    /* Tests suggest that
+     * -> offscreen plain surfaces can be attached to other offscreen plain surfaces
+     * -> offscreen plain surfaces can be attached to primaries
+     * -> primaries can be attached to offscreen plain surfaces
+     * -> z buffers can be attached to primaries */
+    if (surface->surface_desc.ddsCaps.dwCaps & (DDSCAPS_PRIMARYSURFACE | DDSCAPS_OFFSCREENPLAIN)
+            && attach_impl->surface_desc.ddsCaps.dwCaps & (DDSCAPS_PRIMARYSURFACE | DDSCAPS_OFFSCREENPLAIN))
+    {
+        /* Sizes have to match */
+        if (attach_impl->surface_desc.dwWidth != surface->surface_desc.dwWidth
+                || attach_impl->surface_desc.dwHeight != surface->surface_desc.dwHeight)
+        {
+            WARN("Surface sizes do not match.\n");
+            return DDERR_CANNOTATTACHSURFACE;
+        }
+        /* OK */
+    }
+    else if (surface->surface_desc.ddsCaps.dwCaps & (DDSCAPS_PRIMARYSURFACE | DDSCAPS_3DDEVICE)
+            && attach_impl->surface_desc.ddsCaps.dwCaps & (DDSCAPS_ZBUFFER))
+    {
+        /* OK */
+    }
+    else
+    {
+        WARN("Invalid attachment combination.\n");
+        return DDERR_CANNOTATTACHSURFACE;
+    }
+
+    return ddraw_surface_attach_surface(surface, attach_impl);
 }
+
 /*****************************************************************************
  * IDirectDrawSurface7::DeleteAttachedSurface
  *
@@ -929,15 +1088,14 @@ IDirectDrawSurface7Impl_AddAttachedSurface(IDirectDrawSurface7 *iface,
  *  DDERR_SURFACENOTATTACHED if the surface isn't attached to
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_DeleteAttachedSurface(IDirectDrawSurface7 *iface,
-                                             DWORD Flags,
-                                             IDirectDrawSurface7 *Attach)
+static HRESULT WINAPI ddraw_surface7_DeleteAttachedSurface(IDirectDrawSurface7 *iface,
+        DWORD Flags, IDirectDrawSurface7 *Attach)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawSurfaceImpl *Surf = (IDirectDrawSurfaceImpl *)Attach;
     IDirectDrawSurfaceImpl *Prev = This;
-    TRACE("(%p)->(%08x,%p)\n", This, Flags, Surf);
+
+    TRACE("iface %p, flags %#x, attachment %p.\n", iface, Flags, Attach);
 
     EnterCriticalSection(&ddraw_cs);
     if (!Surf || (Surf->first_attached != This) || (Surf == This) )
@@ -976,11 +1134,20 @@ IDirectDrawSurfaceImpl_DeleteAttachedSurface(IDirectDrawSurface7 *iface,
         IDirect3DDeviceImpl_UpdateDepthStencil(This->ddraw->d3ddevice);
     }
 
-    IDirectDrawSurface7_Release(Attach);
+    ddraw_surface7_Release(Attach);
     LeaveCriticalSection(&ddraw_cs);
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_DeleteAttachedSurface(IDirectDrawSurface3 *iface,
+        DWORD flags, IDirectDrawSurface3 *attachment)
+{
+    TRACE("iface %p, flags %#x, attachment %p.\n", iface, flags, attachment);
+
+    return ddraw_surface7_DeleteAttachedSurface((IDirectDrawSurface7 *)surface_from_surface3(iface), flags,
+            attachment ? (IDirectDrawSurface7 *)surface_from_surface3(attachment) : NULL);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::AddOverlayDirtyRect
  *
@@ -993,23 +1160,20 @@ IDirectDrawSurfaceImpl_DeleteAttachedSurface(IDirectDrawSurface7 *iface,
  *  DDERR_UNSUPPORTED
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_AddOverlayDirtyRect(IDirectDrawSurface7 *iface,
-                                           LPRECT Rect)
+static HRESULT WINAPI ddraw_surface7_AddOverlayDirtyRect(IDirectDrawSurface7 *iface, RECT *Rect)
 {
-    IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    TRACE("(%p)->(%p)\n",This,Rect);
+    TRACE("iface %p, rect %s.\n", iface, wine_dbgstr_rect(Rect));
 
-    /* MSDN says it's not implemented. I could forward it to WineD3D,
-     * then we'd implement it, but I don't think that's a good idea
-     * (Stefan Dösinger)
-     */
-#if 0
-    return IWineD3DSurface_AddOverlayDirtyRect(This->WineD3DSurface, pRect);
-#endif
     return DDERR_UNSUPPORTED; /* unchecked */
 }
 
+static HRESULT WINAPI ddraw_surface3_AddOverlayDirtyRect(IDirectDrawSurface3 *iface, RECT *rect)
+{
+    TRACE("iface %p, rect %s.\n", iface, wine_dbgstr_rect(rect));
+
+    return ddraw_surface7_AddOverlayDirtyRect((IDirectDrawSurface7 *)surface_from_surface3(iface), rect);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetDC
  *
@@ -1024,13 +1188,12 @@ IDirectDrawSurfaceImpl_AddOverlayDirtyRect(IDirectDrawSurface7 *iface,
  *  For details, see IWineD3DSurface::GetDC
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetDC(IDirectDrawSurface7 *iface,
-                             HDC *hdc)
+static HRESULT WINAPI ddraw_surface7_GetDC(IDirectDrawSurface7 *iface, HDC *hdc)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p): Relay\n", This, hdc);
+
+    TRACE("iface %p, dc %p.\n", iface, hdc);
 
     if(!hdc)
         return DDERR_INVALIDPARAMS;
@@ -1052,6 +1215,13 @@ IDirectDrawSurfaceImpl_GetDC(IDirectDrawSurface7 *iface,
     }
 }
 
+static HRESULT WINAPI ddraw_surface3_GetDC(IDirectDrawSurface3 *iface, HDC *dc)
+{
+    TRACE("iface %p, dc %p.\n", iface, dc);
+
+    return ddraw_surface7_GetDC((IDirectDrawSurface7 *)surface_from_surface3(iface), dc);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::ReleaseDC
  *
@@ -1065,13 +1235,12 @@ IDirectDrawSurfaceImpl_GetDC(IDirectDrawSurface7 *iface,
  *  For more details, see IWineD3DSurface::ReleaseDC
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_ReleaseDC(IDirectDrawSurface7 *iface,
-                                 HDC hdc)
+static HRESULT WINAPI ddraw_surface7_ReleaseDC(IDirectDrawSurface7 *iface, HDC hdc)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p): Relay\n", This, hdc);
+
+    TRACE("iface %p, dc %p.\n", iface, hdc);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_ReleaseDC(This->WineD3DSurface, hdc);
@@ -1079,6 +1248,13 @@ IDirectDrawSurfaceImpl_ReleaseDC(IDirectDrawSurface7 *iface,
     return hr;
 }
 
+static HRESULT WINAPI ddraw_surface3_ReleaseDC(IDirectDrawSurface3 *iface, HDC dc)
+{
+    TRACE("iface %p, dc %p.\n", iface, dc);
+
+    return ddraw_surface7_ReleaseDC((IDirectDrawSurface7 *)surface_from_surface3(iface), dc);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetCaps
  *
@@ -1092,12 +1268,11 @@ IDirectDrawSurfaceImpl_ReleaseDC(IDirectDrawSurface7 *iface,
  *  DDERR_INVALIDPARAMS if Caps is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetCaps(IDirectDrawSurface7 *iface,
-                               DDSCAPS2 *Caps)
+static HRESULT WINAPI ddraw_surface7_GetCaps(IDirectDrawSurface7 *iface, DDSCAPS2 *Caps)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    TRACE("(%p)->(%p)\n",This,Caps);
+
+    TRACE("iface %p, caps %p.\n", iface, Caps);
 
     if(!Caps)
         return DDERR_INVALIDPARAMS;
@@ -1106,6 +1281,20 @@ IDirectDrawSurfaceImpl_GetCaps(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_GetCaps(IDirectDrawSurface3 *iface, DDSCAPS *caps)
+{
+    DDSCAPS2 caps2;
+    HRESULT hr;
+
+    TRACE("iface %p, caps %p.\n", iface, caps);
+
+    hr = ddraw_surface7_GetCaps((IDirectDrawSurface7 *)surface_from_surface3(iface), &caps2);
+    if (FAILED(hr)) return hr;
+
+    caps->dwCaps = caps2.dwCaps;
+    return hr;
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::SetPriority
  *
@@ -1119,12 +1308,12 @@ IDirectDrawSurfaceImpl_GetCaps(IDirectDrawSurface7 *iface,
  *  For more details, see IWineD3DSurface::SetPriority
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_SetPriority(IDirectDrawSurface7 *iface, DWORD Priority)
+static HRESULT WINAPI ddraw_surface7_SetPriority(IDirectDrawSurface7 *iface, DWORD Priority)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%d): Relay!\n",This,Priority);
+
+    TRACE("iface %p, priority %u.\n", iface, Priority);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_SetPriority(This->WineD3DSurface, Priority);
@@ -1146,12 +1335,11 @@ IDirectDrawSurfaceImpl_SetPriority(IDirectDrawSurface7 *iface, DWORD Priority)
  *  For more details, see IWineD3DSurface::GetPriority
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetPriority(IDirectDrawSurface7 *iface,
-                                   DWORD *Priority)
+static HRESULT WINAPI ddraw_surface7_GetPriority(IDirectDrawSurface7 *iface, DWORD *Priority)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    TRACE("(%p)->(%p): Relay\n",This,Priority);
+
+    TRACE("iface %p, priority %p.\n", iface, Priority);
 
     if(!Priority)
     {
@@ -1181,16 +1369,14 @@ IDirectDrawSurfaceImpl_GetPriority(IDirectDrawSurface7 *iface,
  *  For more details, see IWineD3DSurface::SetPrivateData
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_SetPrivateData(IDirectDrawSurface7 *iface,
-                                      REFGUID tag,
-                                      void *Data,
-                                      DWORD Size,
-                                      DWORD Flags)
+static HRESULT WINAPI ddraw_surface7_SetPrivateData(IDirectDrawSurface7 *iface,
+        REFGUID tag, void *Data, DWORD Size, DWORD Flags)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%s,%p,%d,%x): Relay\n", This, debugstr_guid(tag), Data, Size, Flags);
+
+    TRACE("iface %p, tag %s, data %p, data_size %u, flags %#x.\n",
+            iface, debugstr_guid(tag), Data, Size, Flags);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_SetPrivateData(This->WineD3DSurface,
@@ -1222,15 +1408,13 @@ IDirectDrawSurfaceImpl_SetPrivateData(IDirectDrawSurface7 *iface,
  *  For more details, see IWineD3DSurface::GetPrivateData
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetPrivateData(IDirectDrawSurface7 *iface,
-                                      REFGUID tag,
-                                      void *Data,
-                                      DWORD *Size)
+static HRESULT WINAPI ddraw_surface7_GetPrivateData(IDirectDrawSurface7 *iface, REFGUID tag, void *Data, DWORD *Size)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%s,%p,%p): Relay\n", This, debugstr_guid(tag), Data, Size);
+
+    TRACE("iface %p, tag %s, data %p, data_size %p.\n",
+            iface, debugstr_guid(tag), Data, Size);
 
     if(!Data)
         return DDERR_INVALIDPARAMS;
@@ -1257,13 +1441,12 @@ IDirectDrawSurfaceImpl_GetPrivateData(IDirectDrawSurface7 *iface,
  *  For more details, see IWineD3DSurface::FreePrivateData
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_FreePrivateData(IDirectDrawSurface7 *iface,
-                                       REFGUID tag)
+static HRESULT WINAPI ddraw_surface7_FreePrivateData(IDirectDrawSurface7 *iface, REFGUID tag)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%s): Relay\n", This, debugstr_guid(tag));
+
+    TRACE("iface %p, tag %s.\n", iface, debugstr_guid(tag));
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_FreePrivateData(This->WineD3DSurface, tag);
@@ -1283,16 +1466,21 @@ IDirectDrawSurfaceImpl_FreePrivateData(IDirectDrawSurface7 *iface,
  *  DD_OK, because it's a stub
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_PageLock(IDirectDrawSurface7 *iface,
-                                DWORD Flags)
+static HRESULT WINAPI ddraw_surface7_PageLock(IDirectDrawSurface7 *iface, DWORD Flags)
 {
-    TRACE("(%p)->(%x)\n", iface, Flags);
+    TRACE("iface %p, flags %#x.\n", iface, Flags);
 
     /* This is Windows memory management related - we don't need this */
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_PageLock(IDirectDrawSurface3 *iface, DWORD flags)
+{
+    TRACE("iface %p, flags %#x.\n", iface, flags);
+
+    return ddraw_surface7_PageLock((IDirectDrawSurface7 *)surface_from_surface3(iface), flags);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::PageUnlock
  *
@@ -1305,15 +1493,20 @@ IDirectDrawSurfaceImpl_PageLock(IDirectDrawSurface7 *iface,
  *  DD_OK, because it's a stub
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_PageUnlock(IDirectDrawSurface7 *iface,
-                                  DWORD Flags)
+static HRESULT WINAPI ddraw_surface7_PageUnlock(IDirectDrawSurface7 *iface, DWORD Flags)
 {
-    TRACE("(%p)->(%x)\n", iface, Flags);
+    TRACE("iface %p, flags %#x.\n", iface, Flags);
 
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_PageUnlock(IDirectDrawSurface3 *iface, DWORD flags)
+{
+    TRACE("iface %p, flags %#x.\n", iface, flags);
+
+    return ddraw_surface7_PageUnlock((IDirectDrawSurface7 *)surface_from_surface3(iface), flags);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::BltBatch
  *
@@ -1326,14 +1519,21 @@ IDirectDrawSurfaceImpl_PageUnlock(IDirectDrawSurface7 *iface,
  *  DDERR_UNSUPPORTED
  *
  *****************************************************************************/
-static HRESULT WINAPI IDirectDrawSurfaceImpl_BltBatch(IDirectDrawSurface7 *iface, DDBLTBATCH *Batch, DWORD Count, DWORD Flags)
+static HRESULT WINAPI ddraw_surface7_BltBatch(IDirectDrawSurface7 *iface, DDBLTBATCH *Batch, DWORD Count, DWORD Flags)
 {
-    TRACE("(%p)->(%p,%d,%08x)\n",iface,Batch,Count,Flags);
+    TRACE("iface %p, batch %p, count %u, flags %#x.\n", iface, Batch, Count, Flags);
 
     /* MSDN: "not currently implemented" */
     return DDERR_UNSUPPORTED;
 }
 
+static HRESULT WINAPI ddraw_surface3_BltBatch(IDirectDrawSurface3 *iface, DDBLTBATCH *batch, DWORD count, DWORD flags)
+{
+    TRACE("iface %p, batch %p, count %u, flags %#x.\n", iface, batch, count, flags);
+
+    return ddraw_surface7_BltBatch((IDirectDrawSurface7 *)surface_from_surface3(iface), batch, count, flags);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::EnumAttachedSurfaces
  *
@@ -1348,10 +1548,8 @@ static HRESULT WINAPI IDirectDrawSurfaceImpl_BltBatch(IDirectDrawSurface7 *iface
  *  DDERR_INVALIDPARAMS if cb is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_EnumAttachedSurfaces(IDirectDrawSurface7 *iface,
-                                            void *context,
-                                            LPDDENUMSURFACESCALLBACK7 cb)
+static HRESULT WINAPI ddraw_surface7_EnumAttachedSurfaces(IDirectDrawSurface7 *iface,
+        void *context, LPDDENUMSURFACESCALLBACK7 cb)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawSurfaceImpl *surf;
@@ -1359,7 +1557,7 @@ IDirectDrawSurfaceImpl_EnumAttachedSurfaces(IDirectDrawSurface7 *iface,
     int i;
 
     /* Attached surfaces aren't handled in WineD3D */
-    TRACE("(%p)->(%p,%p)\n",This,context,cb);
+    TRACE("iface %p, context %p, callback %p.\n", iface, context, cb);
 
     if(!cb)
         return DDERR_INVALIDPARAMS;
@@ -1370,7 +1568,7 @@ IDirectDrawSurfaceImpl_EnumAttachedSurfaces(IDirectDrawSurface7 *iface,
         surf = This->complex_array[i];
         if(!surf) break;
 
-        IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)surf);
+        ddraw_surface7_AddRef((IDirectDrawSurface7 *)surf);
         desc = surf->surface_desc;
         /* check: != DDENUMRET_OK or == DDENUMRET_CANCEL? */
         if (cb((IDirectDrawSurface7 *)surf, &desc, context) == DDENUMRET_CANCEL)
@@ -1382,7 +1580,7 @@ IDirectDrawSurfaceImpl_EnumAttachedSurfaces(IDirectDrawSurface7 *iface,
 
     for (surf = This->next_attached; surf != NULL; surf = surf->next_attached)
     {
-        IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)surf);
+        ddraw_surface7_AddRef((IDirectDrawSurface7 *)surf);
         desc = surf->surface_desc;
         /* check: != DDENUMRET_OK or == DDENUMRET_CANCEL? */
         if (cb((IDirectDrawSurface7 *)surf, &desc, context) == DDENUMRET_CANCEL)
@@ -1398,6 +1596,34 @@ IDirectDrawSurfaceImpl_EnumAttachedSurfaces(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+struct callback_info
+{
+    LPDDENUMSURFACESCALLBACK callback;
+    void *context;
+};
+
+static HRESULT CALLBACK EnumCallback(IDirectDrawSurface7 *surface, DDSURFACEDESC2 *surface_desc, void *context)
+{
+    const struct callback_info *info = context;
+
+    return info->callback((IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)surface)->IDirectDrawSurface3_vtbl,
+            (DDSURFACEDESC *)surface_desc, info->context);
+}
+
+static HRESULT WINAPI ddraw_surface3_EnumAttachedSurfaces(IDirectDrawSurface3 *iface,
+        void *context, LPDDENUMSURFACESCALLBACK callback)
+{
+    struct callback_info info;
+
+    TRACE("iface %p, context %p, callback %p.\n", iface, context, callback);
+
+    info.callback = callback;
+    info.context  = context;
+
+    return ddraw_surface7_EnumAttachedSurfaces((IDirectDrawSurface7 *)surface_from_surface3(iface),
+            &info, EnumCallback);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::EnumOverlayZOrders
  *
@@ -1412,17 +1638,28 @@ IDirectDrawSurfaceImpl_EnumAttachedSurfaces(IDirectDrawSurface7 *iface,
  *  DD_OK, because it's a stub
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_EnumOverlayZOrders(IDirectDrawSurface7 *iface,
-                                          DWORD Flags,
-                                          void *context,
-                                          LPDDENUMSURFACESCALLBACK7 cb)
+static HRESULT WINAPI ddraw_surface7_EnumOverlayZOrders(IDirectDrawSurface7 *iface,
+        DWORD Flags, void *context, LPDDENUMSURFACESCALLBACK7 cb)
 {
-     FIXME("(%p)->(%x,%p,%p): Stub!\n", iface, Flags, context, cb);
+    FIXME("iface %p, flags %#x, context %p, callback %p stub!\n", iface, Flags, context, cb);
 
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_EnumOverlayZOrders(IDirectDrawSurface3 *iface,
+        DWORD flags, void *context, LPDDENUMSURFACESCALLBACK callback)
+{
+    struct callback_info info;
+
+    TRACE("iface %p, flags %#x, context %p, callback %p.\n", iface, flags, context, callback);
+
+    info.callback = callback;
+    info.context  = context;
+
+    return ddraw_surface7_EnumOverlayZOrders((IDirectDrawSurface7 *)surface_from_surface3(iface),
+            flags, &info, EnumCallback);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetBltStatus
  *
@@ -1435,13 +1672,12 @@ IDirectDrawSurfaceImpl_EnumOverlayZOrders(IDirectDrawSurface7 *iface,
  *  See IWineD3DSurface::Blt
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetBltStatus(IDirectDrawSurface7 *iface,
-                                    DWORD Flags)
+static HRESULT WINAPI ddraw_surface7_GetBltStatus(IDirectDrawSurface7 *iface, DWORD Flags)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%x): Relay\n", This, Flags);
+
+    TRACE("iface %p, flags %#x.\n", iface, Flags);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_GetBltStatus(This->WineD3DSurface, Flags);
@@ -1453,6 +1689,13 @@ IDirectDrawSurfaceImpl_GetBltStatus(IDirectDrawSurface7 *iface,
     }
 }
 
+static HRESULT WINAPI ddraw_surface3_GetBltStatus(IDirectDrawSurface3 *iface, DWORD flags)
+{
+    TRACE("iface %p, flags %#x.\n", iface, flags);
+
+    return ddraw_surface7_GetBltStatus((IDirectDrawSurface7 *)surface_from_surface3(iface), flags);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetColorKey
  *
@@ -1467,13 +1710,11 @@ IDirectDrawSurfaceImpl_GetBltStatus(IDirectDrawSurface7 *iface,
  *  DDERR_INVALIDPARAMS if CKey is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetColorKey(IDirectDrawSurface7 *iface,
-                                   DWORD Flags,
-                                   DDCOLORKEY *CKey)
+static HRESULT WINAPI ddraw_surface7_GetColorKey(IDirectDrawSurface7 *iface, DWORD Flags, DDCOLORKEY *CKey)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    TRACE("(%p)->(%08x,%p)\n", This, Flags, CKey);
+
+    TRACE("iface %p, flags %#x, color_key %p.\n", iface, Flags, CKey);
 
     if(!CKey)
         return DDERR_INVALIDPARAMS;
@@ -1527,6 +1768,13 @@ IDirectDrawSurfaceImpl_GetColorKey(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_GetColorKey(IDirectDrawSurface3 *iface, DWORD flags, DDCOLORKEY *color_key)
+{
+    TRACE("iface %p, flags %#x, color_key %p.\n", iface, flags, color_key);
+
+    return ddraw_surface7_GetColorKey((IDirectDrawSurface7 *)surface_from_surface3(iface), flags, color_key);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetFlipStatus
  *
@@ -1539,13 +1787,12 @@ IDirectDrawSurfaceImpl_GetColorKey(IDirectDrawSurface7 *iface,
  *  See IWineD3DSurface::GetFlipStatus
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetFlipStatus(IDirectDrawSurface7 *iface,
-                                     DWORD Flags)
+static HRESULT WINAPI ddraw_surface7_GetFlipStatus(IDirectDrawSurface7 *iface, DWORD Flags)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%x): Relay\n", This, Flags);
+
+    TRACE("iface %p, flags %#x.\n", iface, Flags);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_GetFlipStatus(This->WineD3DSurface, Flags);
@@ -1557,6 +1804,13 @@ IDirectDrawSurfaceImpl_GetFlipStatus(IDirectDrawSurface7 *iface,
     }
 }
 
+static HRESULT WINAPI ddraw_surface3_GetFlipStatus(IDirectDrawSurface3 *iface, DWORD flags)
+{
+    TRACE("iface %p, flags %#x.\n", iface, flags);
+
+    return ddraw_surface7_GetFlipStatus((IDirectDrawSurface7 *)surface_from_surface3(iface), flags);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetOverlayPosition
  *
@@ -1569,13 +1823,12 @@ IDirectDrawSurfaceImpl_GetFlipStatus(IDirectDrawSurface7 *iface,
  * Returns:
  *  DDERR_NOTAOVERLAYSURFACE, because it's a stub
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetOverlayPosition(IDirectDrawSurface7 *iface,
-                                          LONG *X,
-                                          LONG *Y) {
+static HRESULT WINAPI ddraw_surface7_GetOverlayPosition(IDirectDrawSurface7 *iface, LONG *X, LONG *Y)
+{
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%p,%p): Relay\n", This, X, Y);
+
+    TRACE("iface %p, x %p, y %p.\n", iface, X, Y);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_GetOverlayPosition(This->WineD3DSurface,
@@ -1585,6 +1838,13 @@ IDirectDrawSurfaceImpl_GetOverlayPosition(IDirectDrawSurface7 *iface,
     return hr;
 }
 
+static HRESULT WINAPI ddraw_surface3_GetOverlayPosition(IDirectDrawSurface3 *iface, LONG *x, LONG *y)
+{
+    TRACE("iface %p, x %p, y %p.\n", iface, x, y);
+
+    return ddraw_surface7_GetOverlayPosition((IDirectDrawSurface7 *)surface_from_surface3(iface), x, y);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetPixelFormat
  *
@@ -1599,13 +1859,12 @@ IDirectDrawSurfaceImpl_GetOverlayPosition(IDirectDrawSurface7 *iface,
  *  DDERR_INVALIDPARAMS if PixelFormat is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetPixelFormat(IDirectDrawSurface7 *iface,
-                                      DDPIXELFORMAT *PixelFormat)
+static HRESULT WINAPI ddraw_surface7_GetPixelFormat(IDirectDrawSurface7 *iface, DDPIXELFORMAT *PixelFormat)
 {
     /* What is DDERR_INVALIDSURFACETYPE for here? */
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    TRACE("(%p)->(%p)\n",This,PixelFormat);
+
+    TRACE("iface %p, pixel_format %p.\n", iface, PixelFormat);
 
     if(!PixelFormat)
         return DDERR_INVALIDPARAMS;
@@ -1617,6 +1876,12 @@ IDirectDrawSurfaceImpl_GetPixelFormat(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_GetPixelFormat(IDirectDrawSurface3 *iface, DDPIXELFORMAT *pixel_format)
+{
+    TRACE("iface %p, pixel_format %p.\n", iface, pixel_format);
+
+    return ddraw_surface7_GetPixelFormat((IDirectDrawSurface7 *)surface_from_surface3(iface), pixel_format);
+}
 
 /*****************************************************************************
  * IDirectDrawSurface7::GetSurfaceDesc
@@ -1632,13 +1897,11 @@ IDirectDrawSurfaceImpl_GetPixelFormat(IDirectDrawSurface7 *iface,
  *  DDERR_INVALIDPARAMS if DDSD is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetSurfaceDesc(IDirectDrawSurface7 *iface,
-                                      DDSURFACEDESC2 *DDSD)
+static HRESULT WINAPI ddraw_surface7_GetSurfaceDesc(IDirectDrawSurface7 *iface, DDSURFACEDESC2 *DDSD)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
 
-    TRACE("(%p)->(%p)\n",This,DDSD);
+    TRACE("iface %p, surface_desc %p.\n", iface, DDSD);
 
     if(!DDSD)
         return DDERR_INVALIDPARAMS;
@@ -1658,6 +1921,33 @@ IDirectDrawSurfaceImpl_GetSurfaceDesc(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_GetSurfaceDesc(IDirectDrawSurface3 *iface, DDSURFACEDESC *surface_desc)
+{
+    IDirectDrawSurfaceImpl *surface = surface_from_surface3(iface);
+
+    TRACE("iface %p, surface_desc %p.\n", iface, surface_desc);
+
+    if (!surface_desc) return DDERR_INVALIDPARAMS;
+
+    if (surface_desc->dwSize != sizeof(DDSURFACEDESC))
+    {
+        WARN("Incorrect structure size %u, returning DDERR_INVALIDPARAMS.\n", surface_desc->dwSize);
+        return DDERR_INVALIDPARAMS;
+    }
+
+    EnterCriticalSection(&ddraw_cs);
+    DD_STRUCT_COPY_BYSIZE(surface_desc, (DDSURFACEDESC *)&surface->surface_desc);
+    TRACE("Returning surface desc:\n");
+    if (TRACE_ON(ddraw))
+    {
+        /* DDRAW_dump_surface_desc handles the smaller size */
+        DDRAW_dump_surface_desc((DDSURFACEDESC2 *)surface_desc);
+    }
+
+    LeaveCriticalSection(&ddraw_cs);
+    return DD_OK;
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::Initialize
  *
@@ -1671,35 +1961,60 @@ IDirectDrawSurfaceImpl_GetSurfaceDesc(IDirectDrawSurface7 *iface,
  *  DDERR_ALREADYINITIALIZED
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_Initialize(IDirectDrawSurface7 *iface,
-                                  IDirectDraw *DD,
-                                  DDSURFACEDESC2 *DDSD)
+static HRESULT WINAPI ddraw_surface7_Initialize(IDirectDrawSurface7 *iface,
+        IDirectDraw *ddraw, DDSURFACEDESC2 *surface_desc)
 {
-    IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    IDirectDrawImpl *ddimpl = DD ? ddraw_from_ddraw1(DD) : NULL;
-    TRACE("(%p)->(%p,%p)\n",This,ddimpl,DDSD);
+    TRACE("iface %p, ddraw %p, surface_desc %p.\n", iface, ddraw, surface_desc);
 
     return DDERR_ALREADYINITIALIZED;
 }
 
+static HRESULT WINAPI ddraw_surface3_Initialize(IDirectDrawSurface3 *iface,
+        IDirectDraw *ddraw, DDSURFACEDESC *surface_desc)
+{
+    TRACE("iface %p, ddraw %p, surface_desc %p.\n", iface, ddraw, surface_desc);
+
+    return ddraw_surface7_Initialize((IDirectDrawSurface7 *)surface_from_surface3(iface),
+            ddraw, (DDSURFACEDESC2 *)surface_desc);
+}
+
 /*****************************************************************************
- * IDirectDrawSurface7::IsLost
+ * IDirect3DTexture1::Initialize
  *
- * Checks if the surface is lost
+ * The sdk says it's not implemented
  *
- * Returns:
- *  DD_OK, if the surface is usable
- *  DDERR_ISLOST if the surface is lost
- *  See IWineD3DSurface::IsLost for more details
+ * Params:
+ *  ?
+ *
+ * Returns
+ *  DDERR_UNSUPPORTED
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_IsLost(IDirectDrawSurface7 *iface)
+static HRESULT WINAPI d3d_texture1_Initialize(IDirect3DTexture *iface,
+        IDirect3DDevice *device, IDirectDrawSurface *surface)
+{
+    TRACE("iface %p, device %p, surface %p.\n", iface, device, surface);
+
+    return DDERR_UNSUPPORTED; /* Unchecked */
+}
+
+/*****************************************************************************
+ * IDirectDrawSurface7::IsLost
+ *
+ * Checks if the surface is lost
+ *
+ * Returns:
+ *  DD_OK, if the surface is usable
+ *  DDERR_ISLOST if the surface is lost
+ *  See IWineD3DSurface::IsLost for more details
+ *
+ *****************************************************************************/
+static HRESULT WINAPI ddraw_surface7_IsLost(IDirectDrawSurface7 *iface)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)\n", This);
+
+    TRACE("iface %p.\n", iface);
 
     EnterCriticalSection(&ddraw_cs);
     /* We lose the surface if the implementation was changed */
@@ -1726,6 +2041,13 @@ IDirectDrawSurfaceImpl_IsLost(IDirectDrawSurface7 *iface)
     }
 }
 
+static HRESULT WINAPI ddraw_surface3_IsLost(IDirectDrawSurface3 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_IsLost((IDirectDrawSurface7 *)surface_from_surface3(iface));
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::Restore
  *
@@ -1737,27 +2059,32 @@ IDirectDrawSurfaceImpl_IsLost(IDirectDrawSurface7 *iface)
  *  See IWineD3DSurface::Restore for more details
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_Restore(IDirectDrawSurface7 *iface)
+static HRESULT WINAPI ddraw_surface7_Restore(IDirectDrawSurface7 *iface)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)\n", This);
+
+    TRACE("iface %p.\n", iface);
 
     EnterCriticalSection(&ddraw_cs);
     if(This->ImplType != This->ddraw->ImplType)
     {
         /* Call the recreation callback. Make sure to AddRef first */
         IDirectDrawSurface_AddRef(iface);
-        IDirectDrawImpl_RecreateSurfacesCallback(iface,
-                                                 &This->surface_desc,
-                                                 NULL /* Not needed */);
+        ddraw_recreate_surfaces_cb(iface, &This->surface_desc, NULL /* Not needed */);
     }
     hr = IWineD3DSurface_Restore(This->WineD3DSurface);
     LeaveCriticalSection(&ddraw_cs);
     return hr;
 }
 
+static HRESULT WINAPI ddraw_surface3_Restore(IDirectDrawSurface3 *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ddraw_surface7_Restore((IDirectDrawSurface7 *)surface_from_surface3(iface));
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::SetOverlayPosition
  *
@@ -1770,14 +2097,12 @@ IDirectDrawSurfaceImpl_Restore(IDirectDrawSurface7 *iface)
  * Returns:
  *   DDERR_NOTAOVERLAYSURFACE, because we don't support overlays right now
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_SetOverlayPosition(IDirectDrawSurface7 *iface,
-                                          LONG X,
-                                          LONG Y)
+static HRESULT WINAPI ddraw_surface7_SetOverlayPosition(IDirectDrawSurface7 *iface, LONG X, LONG Y)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%d,%d): Relay\n", This, X, Y);
+
+    TRACE("iface %p, x %d, y %d.\n", iface, X, Y);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_SetOverlayPosition(This->WineD3DSurface,
@@ -1787,6 +2112,13 @@ IDirectDrawSurfaceImpl_SetOverlayPosition(IDirectDrawSurface7 *iface,
     return hr;
 }
 
+static HRESULT WINAPI ddraw_surface3_SetOverlayPosition(IDirectDrawSurface3 *iface, LONG x, LONG y)
+{
+    TRACE("iface %p, x %d, y %d.\n", iface, x, y);
+
+    return ddraw_surface7_SetOverlayPosition((IDirectDrawSurface7 *)surface_from_surface3(iface), x, y);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::UpdateOverlay
  *
@@ -1802,18 +2134,15 @@ IDirectDrawSurfaceImpl_SetOverlayPosition(IDirectDrawSurface7 *iface,
  *  DDERR_UNSUPPORTED, because we don't support overlays
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_UpdateOverlay(IDirectDrawSurface7 *iface,
-                                     LPRECT SrcRect,
-                                     IDirectDrawSurface7 *DstSurface,
-                                     LPRECT DstRect,
-                                     DWORD Flags,
-                                     LPDDOVERLAYFX FX)
+static HRESULT WINAPI ddraw_surface7_UpdateOverlay(IDirectDrawSurface7 *iface, RECT *SrcRect,
+        IDirectDrawSurface7 *DstSurface, RECT *DstRect, DWORD Flags, DDOVERLAYFX *FX)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawSurfaceImpl *Dst = (IDirectDrawSurfaceImpl *)DstSurface;
     HRESULT hr;
-    TRACE("(%p)->(%p,%p,%p,%x,%p): Relay\n", This, SrcRect, Dst, DstRect, Flags, FX);
+
+    TRACE("iface %p, src_rect %s, dst_surface %p, dst_rect %s, flags %#x, fx %p.\n",
+            iface, wine_dbgstr_rect(SrcRect), DstSurface, wine_dbgstr_rect(DstRect), Flags, FX);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DSurface_UpdateOverlay(This->WineD3DSurface,
@@ -1832,6 +2161,16 @@ IDirectDrawSurfaceImpl_UpdateOverlay(IDirectDrawSurface7 *iface,
     }
 }
 
+static HRESULT WINAPI ddraw_surface3_UpdateOverlay(IDirectDrawSurface3 *iface, RECT *src_rect,
+        IDirectDrawSurface3 *dst_surface, RECT *dst_rect, DWORD flags, DDOVERLAYFX *fx)
+{
+    TRACE("iface %p, src_rect %s, dst_surface %p, dst_rect %s, flags %#x, fx %p.\n",
+            iface, wine_dbgstr_rect(src_rect), dst_surface, wine_dbgstr_rect(dst_rect), flags, fx);
+
+    return ddraw_surface7_UpdateOverlay((IDirectDrawSurface7 *)surface_from_surface3(iface), src_rect,
+            dst_surface ? (IDirectDrawSurface7 *)surface_from_surface3(dst_surface) : NULL, dst_rect, flags, fx);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::UpdateOverlayDisplay
  *
@@ -1843,15 +2182,20 @@ IDirectDrawSurfaceImpl_UpdateOverlay(IDirectDrawSurface7 *iface,
  * Returns: DDERR_UNSUPPORTED, because we don't support overlays
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_UpdateOverlayDisplay(IDirectDrawSurface7 *iface,
-                                            DWORD Flags)
+static HRESULT WINAPI ddraw_surface7_UpdateOverlayDisplay(IDirectDrawSurface7 *iface, DWORD Flags)
 {
-    IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    TRACE("(%p)->(%x)\n", This, Flags);
+    TRACE("iface %p, flags %#x.\n", iface, Flags);
+
     return DDERR_UNSUPPORTED;
 }
 
+static HRESULT WINAPI ddraw_surface3_UpdateOverlayDisplay(IDirectDrawSurface3 *iface, DWORD flags)
+{
+    TRACE("iface %p, flags %#x.\n", iface, flags);
+
+    return ddraw_surface7_UpdateOverlayDisplay((IDirectDrawSurface7 *)surface_from_surface3(iface), flags);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::UpdateOverlayZOrder
  *
@@ -1865,16 +2209,15 @@ IDirectDrawSurfaceImpl_UpdateOverlayDisplay(IDirectDrawSurface7 *iface,
  *  DDERR_NOTOVERLAYSURFACE, because we don't support overlays
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_UpdateOverlayZOrder(IDirectDrawSurface7 *iface,
-                                           DWORD Flags,
-                                           IDirectDrawSurface7 *DDSRef)
+static HRESULT WINAPI ddraw_surface7_UpdateOverlayZOrder(IDirectDrawSurface7 *iface,
+        DWORD Flags, IDirectDrawSurface7 *DDSRef)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawSurfaceImpl *Ref = (IDirectDrawSurfaceImpl *)DDSRef;
     HRESULT hr;
 
-    TRACE("(%p)->(%x,%p): Relay\n", This, Flags, Ref);
+    TRACE("iface %p, flags %#x, reference %p.\n", iface, Flags, DDSRef);
+
     EnterCriticalSection(&ddraw_cs);
     hr =  IWineD3DSurface_UpdateOverlayZOrder(This->WineD3DSurface,
                                               Flags,
@@ -1883,6 +2226,15 @@ IDirectDrawSurfaceImpl_UpdateOverlayZOrder(IDirectDrawSurface7 *iface,
     return hr;
 }
 
+static HRESULT WINAPI ddraw_surface3_UpdateOverlayZOrder(IDirectDrawSurface3 *iface,
+        DWORD flags, IDirectDrawSurface3 *reference)
+{
+    TRACE("iface %p, flags %#x, reference %p.\n", iface, flags, reference);
+
+    return ddraw_surface7_UpdateOverlayZOrder((IDirectDrawSurface7 *)surface_from_surface3(iface), flags,
+            reference ? (IDirectDrawSurface7 *)surface_from_surface3(reference) : NULL);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetDDInterface
  *
@@ -1897,13 +2249,11 @@ IDirectDrawSurfaceImpl_UpdateOverlayZOrder(IDirectDrawSurface7 *iface,
  *  DDERR_INVALIDPARAMS if DD is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetDDInterface(IDirectDrawSurface7 *iface,
-                                      void **DD)
+static HRESULT WINAPI ddraw_surface7_GetDDInterface(IDirectDrawSurface7 *iface, void **DD)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
 
-    TRACE("(%p)->(%p)\n",This,DD);
+    TRACE("iface %p, ddraw %p.\n", iface, DD);
 
     if(!DD)
         return DDERR_INVALIDPARAMS;
@@ -1932,13 +2282,21 @@ IDirectDrawSurfaceImpl_GetDDInterface(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_GetDDInterface(IDirectDrawSurface3 *iface, void **ddraw)
+{
+    TRACE("iface %p, ddraw %p.\n", iface, ddraw);
+
+    return ddraw_surface7_GetDDInterface((IDirectDrawSurface7 *)surface_from_surface3(iface), ddraw);
+}
+
 /* This seems also windows implementation specific - I don't think WineD3D needs this */
-static HRESULT WINAPI IDirectDrawSurfaceImpl_ChangeUniquenessValue(IDirectDrawSurface7 *iface)
+static HRESULT WINAPI ddraw_surface7_ChangeUniquenessValue(IDirectDrawSurface7 *iface)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     volatile IDirectDrawSurfaceImpl* vThis = This;
 
-    TRACE("(%p)\n",This);
+    TRACE("iface %p.\n", iface);
+
     EnterCriticalSection(&ddraw_cs);
     /* A uniqueness value of 0 is apparently special.
      * This needs to be checked.
@@ -1962,11 +2320,12 @@ static HRESULT WINAPI IDirectDrawSurfaceImpl_ChangeUniquenessValue(IDirectDrawSu
     return DD_OK;
 }
 
-static HRESULT WINAPI IDirectDrawSurfaceImpl_GetUniquenessValue(IDirectDrawSurface7 *iface, LPDWORD pValue)
+static HRESULT WINAPI ddraw_surface7_GetUniquenessValue(IDirectDrawSurface7 *iface, DWORD *pValue)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
 
-    TRACE("(%p)->(%p)\n",This,pValue);
+    TRACE("iface %p, value %p.\n", iface, pValue);
+
     EnterCriticalSection(&ddraw_cs);
     *pValue = This->uniqueness_value;
     LeaveCriticalSection(&ddraw_cs);
@@ -1986,13 +2345,12 @@ static HRESULT WINAPI IDirectDrawSurfaceImpl_GetUniquenessValue(IDirectDrawSurfa
  *  DDERR_INVALIDOBJECT if the surface is invalid for this method
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_SetLOD(IDirectDrawSurface7 *iface,
-                              DWORD MaxLOD)
+static HRESULT WINAPI ddraw_surface7_SetLOD(IDirectDrawSurface7 *iface, DWORD MaxLOD)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->(%d)\n", This, MaxLOD);
+
+    TRACE("iface %p, lod %u.\n", iface, MaxLOD);
 
     EnterCriticalSection(&ddraw_cs);
     if (!(This->surface_desc.ddsCaps.dwCaps2 & DDSCAPS2_TEXTUREMANAGE))
@@ -2028,12 +2386,11 @@ IDirectDrawSurfaceImpl_SetLOD(IDirectDrawSurface7 *iface,
  *  DDERR_INVALIDOBJECT if the surface is invalid for this method
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetLOD(IDirectDrawSurface7 *iface,
-                              DWORD *MaxLOD)
+static HRESULT WINAPI ddraw_surface7_GetLOD(IDirectDrawSurface7 *iface, DWORD *MaxLOD)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    TRACE("(%p)->(%p)\n", This, MaxLOD);
+
+    TRACE("iface %p, lod %p.\n", iface, MaxLOD);
 
     if(!MaxLOD)
         return DDERR_INVALIDPARAMS;
@@ -2067,18 +2424,19 @@ IDirectDrawSurfaceImpl_GetLOD(IDirectDrawSurface7 *iface,
  *  For more details, see IWineD3DSurface::BltFast
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_BltFast(IDirectDrawSurface7 *iface,
-                               DWORD dstx,
-                               DWORD dsty,
-                               IDirectDrawSurface7 *Source,
-                               RECT *rsrc,
-                               DWORD trans)
+static HRESULT WINAPI ddraw_surface7_BltFast(IDirectDrawSurface7 *iface, DWORD dstx, DWORD dsty,
+        IDirectDrawSurface7 *Source, RECT *rsrc, DWORD trans)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawSurfaceImpl *src = (IDirectDrawSurfaceImpl *)Source;
+    DWORD src_w, src_h, dst_w, dst_h;
     HRESULT hr;
-    TRACE("(%p)->(%d,%d,%p,%p,%d): Relay\n", This, dstx, dsty, Source, rsrc, trans);
+
+    TRACE("iface %p, dst_x %u, dst_y %u, src_surface %p, src_rect %s, flags %#x.\n",
+            iface, dstx, dsty, Source, wine_dbgstr_rect(rsrc), trans);
+
+    dst_w = This->surface_desc.dwWidth;
+    dst_h = This->surface_desc.dwHeight;
 
     /* Source must be != NULL, This is not checked by windows. Windows happily throws a 0xc0000005
      * in that case
@@ -2092,21 +2450,21 @@ IDirectDrawSurfaceImpl_BltFast(IDirectDrawSurface7 *iface,
             WARN("Source rectangle is invalid, returning DDERR_INVALIDRECT\n");
             return DDERR_INVALIDRECT;
         }
-        if(dstx + rsrc->right - rsrc->left > This->surface_desc.dwWidth ||
-           dsty + rsrc->bottom - rsrc->top > This->surface_desc.dwHeight)
-        {
-            WARN("Destination area out of bounds, returning DDERR_INVALIDRECT\n");
-            return DDERR_INVALIDRECT;
-        }
+
+        src_w = rsrc->right - rsrc->left;
+        src_h = rsrc->bottom - rsrc->top;
     }
     else
     {
-        if(dstx + src->surface_desc.dwWidth > This->surface_desc.dwWidth ||
-           dsty + src->surface_desc.dwHeight > This->surface_desc.dwHeight)
-        {
-            WARN("Destination area out of bounds, returning DDERR_INVALIDRECT\n");
-            return DDERR_INVALIDRECT;
-        }
+        src_w = src->surface_desc.dwWidth;
+        src_h = src->surface_desc.dwHeight;
+    }
+
+    if (src_w > dst_w || dstx > dst_w - src_w
+            || src_h > dst_h || dsty > dst_h - src_h)
+    {
+        WARN("Destination area out of bounds, returning DDERR_INVALIDRECT.\n");
+        return DDERR_INVALIDRECT;
     }
 
     EnterCriticalSection(&ddraw_cs);
@@ -2124,6 +2482,16 @@ IDirectDrawSurfaceImpl_BltFast(IDirectDrawSurface7 *iface,
     }
 }
 
+static HRESULT WINAPI ddraw_surface3_BltFast(IDirectDrawSurface3 *iface, DWORD dst_x, DWORD dst_y,
+        IDirectDrawSurface3 *src_surface, RECT *src_rect, DWORD flags)
+{
+    TRACE("iface %p, dst_x %u, dst_y %u, src_surface %p, src_rect %s, flags %#x.\n",
+            iface, dst_x, dst_y, src_surface, wine_dbgstr_rect(src_rect), flags);
+
+    return ddraw_surface7_BltFast((IDirectDrawSurface7 *)surface_from_surface3(iface), dst_x, dst_y,
+            src_surface ? (IDirectDrawSurface7 *)surface_from_surface3(src_surface) : NULL, src_rect, flags);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetClipper
  *
@@ -2139,12 +2507,11 @@ IDirectDrawSurfaceImpl_BltFast(IDirectDrawSurface7 *iface,
  *  DDERR_NOCLIPPERATTACHED if there's no clipper attached
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetClipper(IDirectDrawSurface7 *iface,
-                                  IDirectDrawClipper **Clipper)
+static HRESULT WINAPI ddraw_surface7_GetClipper(IDirectDrawSurface7 *iface, IDirectDrawClipper **Clipper)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    TRACE("(%p)->(%p)\n", This, Clipper);
+
+    TRACE("iface %p, clipper %p.\n", iface, Clipper);
 
     if(!Clipper)
     {
@@ -2165,6 +2532,13 @@ IDirectDrawSurfaceImpl_GetClipper(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_GetClipper(IDirectDrawSurface3 *iface, IDirectDrawClipper **clipper)
+{
+    TRACE("iface %p, clipper %p.\n", iface, clipper);
+
+    return ddraw_surface7_GetClipper((IDirectDrawSurface7 *)surface_from_surface3(iface), clipper);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::SetClipper
  *
@@ -2177,15 +2551,14 @@ IDirectDrawSurfaceImpl_GetClipper(IDirectDrawSurface7 *iface,
  *  DD_OK on success
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_SetClipper(IDirectDrawSurface7 *iface,
-                                  IDirectDrawClipper *Clipper)
+static HRESULT WINAPI ddraw_surface7_SetClipper(IDirectDrawSurface7 *iface, IDirectDrawClipper *Clipper)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawClipperImpl *oldClipper = This->clipper;
     HWND clipWindow;
     HRESULT hr;
-    TRACE("(%p)->(%p)\n",This,Clipper);
+
+    TRACE("iface %p, clipper %p.\n", iface, Clipper);
 
     EnterCriticalSection(&ddraw_cs);
     if ((IDirectDrawClipperImpl *)Clipper == This->clipper)
@@ -2222,6 +2595,13 @@ IDirectDrawSurfaceImpl_SetClipper(IDirectDrawSurface7 *iface,
     return hr;
 }
 
+static HRESULT WINAPI ddraw_surface3_SetClipper(IDirectDrawSurface3 *iface, IDirectDrawClipper *clipper)
+{
+    TRACE("iface %p, clipper %p.\n", iface, clipper);
+
+    return ddraw_surface7_SetClipper((IDirectDrawSurface7 *)surface_from_surface3(iface), clipper);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::SetSurfaceDesc
  *
@@ -2238,15 +2618,13 @@ IDirectDrawSurfaceImpl_SetClipper(IDirectDrawSurface7 *iface,
  *  DDERR_INVALIDPARAMS if DDSD is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_SetSurfaceDesc(IDirectDrawSurface7 *iface,
-                                      DDSURFACEDESC2 *DDSD,
-                                      DWORD Flags)
+static HRESULT WINAPI ddraw_surface7_SetSurfaceDesc(IDirectDrawSurface7 *iface, DDSURFACEDESC2 *DDSD, DWORD Flags)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
-    WINED3DFORMAT newFormat = WINED3DFMT_UNKNOWN;
+    enum wined3d_format_id newFormat = WINED3DFMT_UNKNOWN;
     HRESULT hr;
-    TRACE("(%p)->(%p,%x)\n", This, DDSD, Flags);
+
+    TRACE("iface %p, surface_desc %p, flags %#x.\n", iface, DDSD, Flags);
 
     if(!DDSD)
         return DDERR_INVALIDPARAMS;
@@ -2320,6 +2698,15 @@ IDirectDrawSurfaceImpl_SetSurfaceDesc(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_SetSurfaceDesc(IDirectDrawSurface3 *iface,
+        DDSURFACEDESC *surface_desc, DWORD flags)
+{
+    TRACE("iface %p, surface_desc %p, flags %#x.\n", iface, surface_desc, flags);
+
+    return ddraw_surface7_SetSurfaceDesc((IDirectDrawSurface7 *)surface_from_surface3(iface),
+            (DDSURFACEDESC2 *)surface_desc, flags);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::GetPalette
  *
@@ -2334,14 +2721,13 @@ IDirectDrawSurfaceImpl_SetSurfaceDesc(IDirectDrawSurface7 *iface,
  *  DDERR_INVALIDPARAMS if Pal is NULL
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_GetPalette(IDirectDrawSurface7 *iface,
-                                  IDirectDrawPalette **Pal)
+static HRESULT WINAPI ddraw_surface7_GetPalette(IDirectDrawSurface7 *iface, IDirectDrawPalette **Pal)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IWineD3DPalette *wPal;
     HRESULT hr;
-    TRACE("(%p)->(%p): Relay\n", This, Pal);
+
+    TRACE("iface %p, palette %p.\n", iface, Pal);
 
     if(!Pal)
         return DDERR_INVALIDPARAMS;
@@ -2356,7 +2742,8 @@ IDirectDrawSurfaceImpl_GetPalette(IDirectDrawSurface7 *iface,
 
     if(wPal)
     {
-        hr = IWineD3DPalette_GetParent(wPal, (IUnknown **) Pal);
+        *Pal = IWineD3DPalette_GetParent(wPal);
+        IDirectDrawPalette_AddRef(*Pal);
     }
     else
     {
@@ -2368,6 +2755,13 @@ IDirectDrawSurfaceImpl_GetPalette(IDirectDrawSurface7 *iface,
     return hr;
 }
 
+static HRESULT WINAPI ddraw_surface3_GetPalette(IDirectDrawSurface3 *iface, IDirectDrawPalette **palette)
+{
+    TRACE("iface %p, palette %p.\n", iface, palette);
+
+    return ddraw_surface7_GetPalette((IDirectDrawSurface7 *)surface_from_surface3(iface), palette);
+}
+
 /*****************************************************************************
  * SetColorKeyEnum
  *
@@ -2400,10 +2794,9 @@ SetColorKeyEnum(IDirectDrawSurface7 *surface,
         ctx->ret = hr;
     }
 
-    IDirectDrawSurface7_EnumAttachedSurfaces(surface,
-                                             context,
-                                             SetColorKeyEnum);
-    IDirectDrawSurface7_Release(surface);
+    ddraw_surface7_EnumAttachedSurfaces(surface, context, SetColorKeyEnum);
+    ddraw_surface7_Release(surface);
+
     return DDENUMRET_OK;
 }
 
@@ -2423,15 +2816,13 @@ SetColorKeyEnum(IDirectDrawSurface7 *surface,
  *  See IWineD3DSurface::SetColorKey for details
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_SetColorKey(IDirectDrawSurface7 *iface,
-                                   DWORD Flags,
-                                   DDCOLORKEY *CKey)
+static HRESULT WINAPI ddraw_surface7_SetColorKey(IDirectDrawSurface7 *iface, DWORD Flags, DDCOLORKEY *CKey)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     DDCOLORKEY FixedCKey;
     struct SCKContext ctx = { DD_OK, (WINEDDCOLORKEY *) (CKey ? &FixedCKey : NULL), Flags };
-    TRACE("(%p)->(%x,%p)\n", This, Flags, CKey);
+
+    TRACE("iface %p, flags %#x, color_key %p.\n", iface, Flags, CKey);
 
     EnterCriticalSection(&ddraw_cs);
     if (CKey)
@@ -2493,12 +2884,8 @@ IDirectDrawSurfaceImpl_SetColorKey(IDirectDrawSurface7 *iface,
             return DDERR_INVALIDPARAMS;
         }
     }
-    ctx.ret = IWineD3DSurface_SetColorKey(This->WineD3DSurface,
-                                          Flags,
-                                          ctx.CKey);
-    IDirectDrawSurface7_EnumAttachedSurfaces(iface,
-                                             &ctx,
-                                             SetColorKeyEnum);
+    ctx.ret = IWineD3DSurface_SetColorKey(This->WineD3DSurface, Flags, ctx.CKey);
+    ddraw_surface7_EnumAttachedSurfaces(iface, &ctx, SetColorKeyEnum);
     LeaveCriticalSection(&ddraw_cs);
     switch(ctx.ret)
     {
@@ -2507,6 +2894,13 @@ IDirectDrawSurfaceImpl_SetColorKey(IDirectDrawSurface7 *iface,
     }
 }
 
+static HRESULT WINAPI ddraw_surface3_SetColorKey(IDirectDrawSurface3 *iface, DWORD flags, DDCOLORKEY *color_key)
+{
+    TRACE("iface %p, flags %#x, color_key %p.\n", iface, flags, color_key);
+
+    return ddraw_surface7_SetColorKey((IDirectDrawSurface7 *)surface_from_surface3(iface), flags, color_key);
+}
+
 /*****************************************************************************
  * IDirectDrawSurface7::SetPalette
  *
@@ -2519,16 +2913,15 @@ IDirectDrawSurfaceImpl_SetColorKey(IDirectDrawSurface7 *iface,
  *  DD_OK on success
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirectDrawSurfaceImpl_SetPalette(IDirectDrawSurface7 *iface,
-                                  IDirectDrawPalette *Pal)
+static HRESULT WINAPI ddraw_surface7_SetPalette(IDirectDrawSurface7 *iface, IDirectDrawPalette *Pal)
 {
     IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)iface;
     IDirectDrawPalette *oldPal;
     IDirectDrawSurfaceImpl *surf;
     IDirectDrawPaletteImpl *PalImpl = (IDirectDrawPaletteImpl *)Pal;
     HRESULT hr;
-    TRACE("(%p)->(%p)\n", This, Pal);
+
+    TRACE("iface %p, palette %p.\n", iface, Pal);
 
     if (!(This->surface_desc.u4.ddpfPixelFormat.dwFlags & (DDPF_PALETTEINDEXED1 | DDPF_PALETTEINDEXED2 |
             DDPF_PALETTEINDEXED4 | DDPF_PALETTEINDEXED8 | DDPF_PALETTEINDEXEDTO8))) {
@@ -2567,17 +2960,16 @@ IDirectDrawSurfaceImpl_SetPalette(IDirectDrawSurface7 *iface,
         {
             IDirectDrawSurface7 *attach;
             HRESULT hr;
-            hr = IDirectDrawSurface7_GetAttachedSurface((IDirectDrawSurface7 *)surf, &caps2, &attach);
+            hr = ddraw_surface7_GetAttachedSurface((IDirectDrawSurface7 *)surf, &caps2, &attach);
             if(hr != DD_OK)
             {
                 break;
             }
 
             TRACE("Setting palette on %p\n", attach);
-            IDirectDrawSurface7_SetPalette(attach,
-                                           Pal);
+            ddraw_surface7_SetPalette(attach, Pal);
             surf = (IDirectDrawSurfaceImpl *)attach;
-            IDirectDrawSurface7_Release(attach);
+            ddraw_surface7_Release(attach);
         }
     }
 
@@ -2585,65 +2977,677 @@ IDirectDrawSurfaceImpl_SetPalette(IDirectDrawSurface7 *iface,
     return DD_OK;
 }
 
+static HRESULT WINAPI ddraw_surface3_SetPalette(IDirectDrawSurface3 *iface, IDirectDrawPalette *palette)
+{
+    TRACE("iface %p, palette %p.\n", iface, palette);
+
+    return ddraw_surface7_SetPalette((IDirectDrawSurface7 *)surface_from_surface3(iface), palette);
+}
+
+/**********************************************************
+ * IDirectDrawGammaControl::GetGammaRamp
+ *
+ * Returns the current gamma ramp for a surface
+ *
+ * Params:
+ *  flags: Ignored
+ *  gamma_ramp: Address to write the ramp to
+ *
+ * Returns:
+ *  DD_OK on success
+ *  DDERR_INVALIDPARAMS if gamma_ramp is NULL
+ *
+ **********************************************************/
+static HRESULT WINAPI ddraw_gamma_control_GetGammaRamp(IDirectDrawGammaControl *iface,
+        DWORD flags, DDGAMMARAMP *gamma_ramp)
+{
+    IDirectDrawSurfaceImpl *surface = surface_from_gamma_control(iface);
+
+    TRACE("iface %p, flags %#x, gamma_ramp %p.\n", iface, flags, gamma_ramp);
+
+    if (!gamma_ramp)
+    {
+        WARN("Invalid gamma_ramp passed.\n");
+        return DDERR_INVALIDPARAMS;
+    }
+
+    EnterCriticalSection(&ddraw_cs);
+    if (surface->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE)
+    {
+        /* Note: DDGAMMARAMP is compatible with WINED3DGAMMARAMP. */
+        IWineD3DDevice_GetGammaRamp(surface->ddraw->wineD3DDevice, 0, (WINED3DGAMMARAMP *)gamma_ramp);
+    }
+    else
+    {
+        ERR("Not implemented for non-primary surfaces.\n");
+    }
+    LeaveCriticalSection(&ddraw_cs);
+
+    return DD_OK;
+}
+
+/**********************************************************
+ * IDirectDrawGammaControl::SetGammaRamp
+ *
+ * Sets the red, green and blue gamma ramps for
+ *
+ * Params:
+ *  flags: Can be DDSGR_CALIBRATE to request calibration
+ *  gamma_ramp: Structure containing the new gamma ramp
+ *
+ * Returns:
+ *  DD_OK on success
+ *  DDERR_INVALIDPARAMS if gamma_ramp is NULL
+ *
+ **********************************************************/
+static HRESULT WINAPI ddraw_gamma_control_SetGammaRamp(IDirectDrawGammaControl *iface,
+        DWORD flags, DDGAMMARAMP *gamma_ramp)
+{
+    IDirectDrawSurfaceImpl *surface = surface_from_gamma_control(iface);
+
+    TRACE("iface %p, flags %#x, gamma_ramp %p.\n", iface, flags, gamma_ramp);
+
+    if (!gamma_ramp)
+    {
+        WARN("Invalid gamma_ramp passed.\n");
+        return DDERR_INVALIDPARAMS;
+    }
+
+    EnterCriticalSection(&ddraw_cs);
+    if (surface->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE)
+    {
+        /* Note: DDGAMMARAMP is compatible with WINED3DGAMMARAMP */
+        IWineD3DDevice_SetGammaRamp(surface->ddraw->wineD3DDevice, 0, flags, (WINED3DGAMMARAMP *)gamma_ramp);
+    }
+    else
+    {
+        ERR("Not implemented for non-primary surfaces.\n");
+    }
+    LeaveCriticalSection(&ddraw_cs);
+
+    return DD_OK;
+}
+
+/*****************************************************************************
+ * IDirect3DTexture2::PaletteChanged
+ *
+ * Informs the texture about a palette change
+ *
+ * Params:
+ *  start: Start index of the change
+ *  count: The number of changed entries
+ *
+ * Returns
+ *  D3D_OK, because it's a stub
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d_texture2_PaletteChanged(IDirect3DTexture2 *iface, DWORD start, DWORD count)
+{
+    FIXME("iface %p, start %u, count %u stub!\n", iface, start, count);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d_texture1_PaletteChanged(IDirect3DTexture *iface, DWORD start, DWORD count)
+{
+    IDirectDrawSurfaceImpl *surface = surface_from_texture1(iface);
+
+    TRACE("iface %p, start %u, count %u.\n", iface, start, count);
+
+    return d3d_texture2_PaletteChanged((IDirect3DTexture2 *)&surface->IDirect3DTexture2_vtbl, start, count);
+}
+
+/*****************************************************************************
+ * IDirect3DTexture::Unload
+ *
+ * DX5 SDK: "The IDirect3DTexture2::Unload method is not implemented
+ *
+ *
+ * Returns:
+ *  DDERR_UNSUPPORTED
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d_texture1_Unload(IDirect3DTexture *iface)
+{
+    WARN("iface %p. Not implemented.\n", iface);
+
+    return DDERR_UNSUPPORTED;
+}
+
+/*****************************************************************************
+ * IDirect3DTexture2::GetHandle
+ *
+ * Returns handle for the texture. At the moment, the interface
+ * to the IWineD3DTexture is used.
+ *
+ * Params:
+ *  device: Device this handle is assigned to
+ *  handle: Address to store the handle at.
+ *
+ * Returns:
+ *  D3D_OK
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d_texture2_GetHandle(IDirect3DTexture2 *iface,
+        IDirect3DDevice2 *device, D3DTEXTUREHANDLE *handle)
+{
+    IDirectDrawSurfaceImpl *surface = surface_from_texture2(iface);
+
+    TRACE("iface %p, device %p, handle %p.\n", iface, device, handle);
+
+    EnterCriticalSection(&ddraw_cs);
+
+    if (!surface->Handle)
+    {
+        DWORD h = ddraw_allocate_handle(&device_from_device2(device)->handle_table, surface, DDRAW_HANDLE_SURFACE);
+        if (h == DDRAW_INVALID_HANDLE)
+        {
+            ERR("Failed to allocate a texture handle.\n");
+            LeaveCriticalSection(&ddraw_cs);
+            return DDERR_OUTOFMEMORY;
+        }
+
+        surface->Handle = h + 1;
+    }
+
+    TRACE("Returning handle %08x.\n", surface->Handle);
+    *handle = surface->Handle;
+
+    LeaveCriticalSection(&ddraw_cs);
+
+    return D3D_OK;
+}
+
+static HRESULT WINAPI d3d_texture1_GetHandle(IDirect3DTexture *iface,
+        IDirect3DDevice *device, D3DTEXTUREHANDLE *handle)
+{
+    IDirect3DTexture2 *texture2 = (IDirect3DTexture2 *)&surface_from_texture1(iface)->IDirect3DTexture2_vtbl;
+    IDirect3DDevice2 *device2 = (IDirect3DDevice2 *)&device_from_device1(device)->IDirect3DDevice2_vtbl;
+
+    TRACE("iface %p, device %p, handle %p.\n", iface, device, handle);
+
+    return d3d_texture2_GetHandle(texture2, device2, handle);
+}
+
+/*****************************************************************************
+ * get_sub_mimaplevel
+ *
+ * Helper function that returns the next mipmap level
+ *
+ * tex_ptr: Surface of which to return the next level
+ *
+ *****************************************************************************/
+static IDirectDrawSurfaceImpl *get_sub_mimaplevel(IDirectDrawSurfaceImpl *surface)
+{
+    /* Now go down the mipmap chain to the next surface */
+    static DDSCAPS2 mipmap_caps = { DDSCAPS_MIPMAP | DDSCAPS_TEXTURE, 0, 0, {0} };
+    IDirectDrawSurface7 *next_level;
+    HRESULT hr;
+
+    hr = ddraw_surface7_GetAttachedSurface((IDirectDrawSurface7 *)surface, &mipmap_caps, &next_level);
+    if (FAILED(hr)) return NULL;
+
+    ddraw_surface7_Release(next_level);
+
+    return (IDirectDrawSurfaceImpl *)next_level;
+}
+
+/*****************************************************************************
+ * IDirect3DTexture2::Load
+ *
+ * Loads a texture created with the DDSCAPS_ALLOCONLOAD
+ *
+ * This function isn't relayed to WineD3D because the whole interface is
+ * implemented in DDraw only. For speed improvements a implementation which
+ * takes OpenGL more into account could be placed into WineD3D.
+ *
+ * Params:
+ *  src_texture: Address of the texture to load
+ *
+ * Returns:
+ *  D3D_OK on success
+ *  D3DERR_TEXTURE_LOAD_FAILED.
+ *
+ *****************************************************************************/
+static HRESULT WINAPI d3d_texture2_Load(IDirect3DTexture2 *iface, IDirect3DTexture2 *src_texture)
+{
+    IDirectDrawSurfaceImpl *dst_surface = surface_from_texture2(iface);
+    IDirectDrawSurfaceImpl *src_surface = surface_from_texture2(src_texture);
+    HRESULT hr;
+
+    TRACE("iface %p, src_texture %p.\n", iface, src_texture);
+
+    if (src_surface == dst_surface)
+    {
+        TRACE("copying surface %p to surface %p, why?\n", src_surface, dst_surface);
+        return D3D_OK;
+    }
+
+    EnterCriticalSection(&ddraw_cs);
+
+    if (((src_surface->surface_desc.ddsCaps.dwCaps & DDSCAPS_MIPMAP)
+            != (dst_surface->surface_desc.ddsCaps.dwCaps & DDSCAPS_MIPMAP))
+            || (src_surface->surface_desc.u2.dwMipMapCount != dst_surface->surface_desc.u2.dwMipMapCount))
+    {
+        ERR("Trying to load surfaces with different mip-map counts.\n");
+    }
+
+    for (;;)
+    {
+        IWineD3DPalette *wined3d_dst_pal, *wined3d_src_pal;
+        IDirectDrawPalette *dst_pal = NULL, *src_pal = NULL;
+        DDSURFACEDESC *src_desc, *dst_desc;
+
+        TRACE("Copying surface %p to surface %p (mipmap level %d).\n",
+                src_surface, dst_surface, src_surface->mipmap_level);
+
+        /* Suppress the ALLOCONLOAD flag */
+        dst_surface->surface_desc.ddsCaps.dwCaps &= ~DDSCAPS_ALLOCONLOAD;
+
+        /* Get the palettes */
+        hr = IWineD3DSurface_GetPalette(dst_surface->WineD3DSurface, &wined3d_dst_pal);
+        if (FAILED(hr))
+        {
+            ERR("Failed to get destination palette, hr %#x.\n", hr);
+            LeaveCriticalSection(&ddraw_cs);
+            return D3DERR_TEXTURE_LOAD_FAILED;
+        }
+        if (wined3d_dst_pal) dst_pal = IWineD3DPalette_GetParent(wined3d_dst_pal);
+
+        hr = IWineD3DSurface_GetPalette(src_surface->WineD3DSurface, &wined3d_src_pal);
+        if (FAILED(hr))
+        {
+            ERR("Failed to get source palette, hr %#x.\n", hr);
+            LeaveCriticalSection(&ddraw_cs);
+            return D3DERR_TEXTURE_LOAD_FAILED;
+        }
+        if (wined3d_src_pal) src_pal = IWineD3DPalette_GetParent(wined3d_src_pal);
+
+        if (src_pal)
+        {
+            PALETTEENTRY palent[256];
+
+            if (!dst_pal)
+            {
+                LeaveCriticalSection(&ddraw_cs);
+                return DDERR_NOPALETTEATTACHED;
+            }
+            IDirectDrawPalette_GetEntries(src_pal, 0, 0, 256, palent);
+            IDirectDrawPalette_SetEntries(dst_pal, 0, 0, 256, palent);
+        }
+
+        /* Copy one surface on the other */
+        dst_desc = (DDSURFACEDESC *)&(dst_surface->surface_desc);
+        src_desc = (DDSURFACEDESC *)&(src_surface->surface_desc);
+
+        if ((src_desc->dwWidth != dst_desc->dwWidth) || (src_desc->dwHeight != dst_desc->dwHeight))
+        {
+            /* Should also check for same pixel format, u1.lPitch, ... */
+            ERR("Error in surface sizes.\n");
+            LeaveCriticalSection(&ddraw_cs);
+            return D3DERR_TEXTURE_LOAD_FAILED;
+        }
+        else
+        {
+            WINED3DLOCKED_RECT src_rect, dst_rect;
+
+            /* Copy also the ColorKeying stuff */
+            if (src_desc->dwFlags & DDSD_CKSRCBLT)
+            {
+                dst_desc->dwFlags |= DDSD_CKSRCBLT;
+                dst_desc->ddckCKSrcBlt.dwColorSpaceLowValue = src_desc->ddckCKSrcBlt.dwColorSpaceLowValue;
+                dst_desc->ddckCKSrcBlt.dwColorSpaceHighValue = src_desc->ddckCKSrcBlt.dwColorSpaceHighValue;
+            }
+
+            /* Copy the main memory texture into the surface that corresponds
+             * to the OpenGL texture object. */
+
+            hr = IWineD3DSurface_LockRect(src_surface->WineD3DSurface, &src_rect, NULL, 0);
+            if (FAILED(hr))
+            {
+                ERR("Failed to lock source surface, hr %#x.\n", hr);
+                LeaveCriticalSection(&ddraw_cs);
+                return D3DERR_TEXTURE_LOAD_FAILED;
+            }
+
+            hr = IWineD3DSurface_LockRect(dst_surface->WineD3DSurface, &dst_rect, NULL, 0);
+            if (FAILED(hr))
+            {
+                ERR("Failed to lock destination surface, hr %#x.\n", hr);
+                IWineD3DSurface_UnlockRect(src_surface->WineD3DSurface);
+                LeaveCriticalSection(&ddraw_cs);
+                return D3DERR_TEXTURE_LOAD_FAILED;
+            }
+
+            if (dst_surface->surface_desc.u4.ddpfPixelFormat.dwFlags & DDPF_FOURCC)
+                memcpy(dst_rect.pBits, src_rect.pBits, src_surface->surface_desc.u1.dwLinearSize);
+            else
+                memcpy(dst_rect.pBits, src_rect.pBits, src_rect.Pitch * src_desc->dwHeight);
+
+            IWineD3DSurface_UnlockRect(src_surface->WineD3DSurface);
+            IWineD3DSurface_UnlockRect(dst_surface->WineD3DSurface);
+        }
+
+        if (src_surface->surface_desc.ddsCaps.dwCaps & DDSCAPS_MIPMAP)
+            src_surface = get_sub_mimaplevel(src_surface);
+        else
+            src_surface = NULL;
+
+        if (dst_surface->surface_desc.ddsCaps.dwCaps & DDSCAPS_MIPMAP)
+            dst_surface = get_sub_mimaplevel(dst_surface);
+        else
+            dst_surface = NULL;
+
+        if (!src_surface || !dst_surface)
+        {
+            if (src_surface != dst_surface)
+                ERR("Loading surface with different mipmap structure.\n");
+            break;
+        }
+    }
+
+    LeaveCriticalSection(&ddraw_cs);
+
+    return hr;
+}
+
+static HRESULT WINAPI d3d_texture1_Load(IDirect3DTexture *iface, IDirect3DTexture *src_texture)
+{
+    TRACE("iface %p, src_texture %p.\n", iface, src_texture);
+
+    return d3d_texture2_Load((IDirect3DTexture2 *)&surface_from_texture1(iface)->IDirect3DTexture2_vtbl,
+            src_texture ? (IDirect3DTexture2 *)&surface_from_texture1(src_texture)->IDirect3DTexture2_vtbl : NULL);
+}
+
 /*****************************************************************************
  * The VTable
  *****************************************************************************/
 
-const IDirectDrawSurface7Vtbl IDirectDrawSurface7_Vtbl =
-{
-    /*** IUnknown ***/
-    IDirectDrawSurfaceImpl_QueryInterface,
-    IDirectDrawSurfaceImpl_AddRef,
-    IDirectDrawSurfaceImpl_Release,
-    /*** IDirectDrawSurface ***/
-    IDirectDrawSurface7Impl_AddAttachedSurface,
-    IDirectDrawSurfaceImpl_AddOverlayDirtyRect,
-    IDirectDrawSurfaceImpl_Blt,
-    IDirectDrawSurfaceImpl_BltBatch,
-    IDirectDrawSurfaceImpl_BltFast,
-    IDirectDrawSurfaceImpl_DeleteAttachedSurface,
-    IDirectDrawSurfaceImpl_EnumAttachedSurfaces,
-    IDirectDrawSurfaceImpl_EnumOverlayZOrders,
-    IDirectDrawSurfaceImpl_Flip,
-    IDirectDrawSurfaceImpl_GetAttachedSurface,
-    IDirectDrawSurfaceImpl_GetBltStatus,
-    IDirectDrawSurfaceImpl_GetCaps,
-    IDirectDrawSurfaceImpl_GetClipper,
-    IDirectDrawSurfaceImpl_GetColorKey,
-    IDirectDrawSurfaceImpl_GetDC,
-    IDirectDrawSurfaceImpl_GetFlipStatus,
-    IDirectDrawSurfaceImpl_GetOverlayPosition,
-    IDirectDrawSurfaceImpl_GetPalette,
-    IDirectDrawSurfaceImpl_GetPixelFormat,
-    IDirectDrawSurfaceImpl_GetSurfaceDesc,
-    IDirectDrawSurfaceImpl_Initialize,
-    IDirectDrawSurfaceImpl_IsLost,
-    IDirectDrawSurfaceImpl_Lock,
-    IDirectDrawSurfaceImpl_ReleaseDC,
-    IDirectDrawSurfaceImpl_Restore,
-    IDirectDrawSurfaceImpl_SetClipper,
-    IDirectDrawSurfaceImpl_SetColorKey,
-    IDirectDrawSurfaceImpl_SetOverlayPosition,
-    IDirectDrawSurfaceImpl_SetPalette,
-    IDirectDrawSurfaceImpl_Unlock,
-    IDirectDrawSurfaceImpl_UpdateOverlay,
-    IDirectDrawSurfaceImpl_UpdateOverlayDisplay,
-    IDirectDrawSurfaceImpl_UpdateOverlayZOrder,
-    /*** IDirectDrawSurface2 ***/
-    IDirectDrawSurfaceImpl_GetDDInterface,
-    IDirectDrawSurfaceImpl_PageLock,
-    IDirectDrawSurfaceImpl_PageUnlock,
-    /*** IDirectDrawSurface3 ***/
-    IDirectDrawSurfaceImpl_SetSurfaceDesc,
-    /*** IDirectDrawSurface4 ***/
-    IDirectDrawSurfaceImpl_SetPrivateData,
-    IDirectDrawSurfaceImpl_GetPrivateData,
-    IDirectDrawSurfaceImpl_FreePrivateData,
-    IDirectDrawSurfaceImpl_GetUniquenessValue,
-    IDirectDrawSurfaceImpl_ChangeUniquenessValue,
-    /*** IDirectDrawSurface7 ***/
-    IDirectDrawSurfaceImpl_SetPriority,
-    IDirectDrawSurfaceImpl_GetPriority,
-    IDirectDrawSurfaceImpl_SetLOD,
-    IDirectDrawSurfaceImpl_GetLOD
+static const struct IDirectDrawSurface7Vtbl ddraw_surface7_vtbl =
+{
+    /* IUnknown */
+    ddraw_surface7_QueryInterface,
+    ddraw_surface7_AddRef,
+    ddraw_surface7_Release,
+    /* IDirectDrawSurface */
+    ddraw_surface7_AddAttachedSurface,
+    ddraw_surface7_AddOverlayDirtyRect,
+    ddraw_surface7_Blt,
+    ddraw_surface7_BltBatch,
+    ddraw_surface7_BltFast,
+    ddraw_surface7_DeleteAttachedSurface,
+    ddraw_surface7_EnumAttachedSurfaces,
+    ddraw_surface7_EnumOverlayZOrders,
+    ddraw_surface7_Flip,
+    ddraw_surface7_GetAttachedSurface,
+    ddraw_surface7_GetBltStatus,
+    ddraw_surface7_GetCaps,
+    ddraw_surface7_GetClipper,
+    ddraw_surface7_GetColorKey,
+    ddraw_surface7_GetDC,
+    ddraw_surface7_GetFlipStatus,
+    ddraw_surface7_GetOverlayPosition,
+    ddraw_surface7_GetPalette,
+    ddraw_surface7_GetPixelFormat,
+    ddraw_surface7_GetSurfaceDesc,
+    ddraw_surface7_Initialize,
+    ddraw_surface7_IsLost,
+    ddraw_surface7_Lock,
+    ddraw_surface7_ReleaseDC,
+    ddraw_surface7_Restore,
+    ddraw_surface7_SetClipper,
+    ddraw_surface7_SetColorKey,
+    ddraw_surface7_SetOverlayPosition,
+    ddraw_surface7_SetPalette,
+    ddraw_surface7_Unlock,
+    ddraw_surface7_UpdateOverlay,
+    ddraw_surface7_UpdateOverlayDisplay,
+    ddraw_surface7_UpdateOverlayZOrder,
+    /* IDirectDrawSurface2 */
+    ddraw_surface7_GetDDInterface,
+    ddraw_surface7_PageLock,
+    ddraw_surface7_PageUnlock,
+    /* IDirectDrawSurface3 */
+    ddraw_surface7_SetSurfaceDesc,
+    /* IDirectDrawSurface4 */
+    ddraw_surface7_SetPrivateData,
+    ddraw_surface7_GetPrivateData,
+    ddraw_surface7_FreePrivateData,
+    ddraw_surface7_GetUniquenessValue,
+    ddraw_surface7_ChangeUniquenessValue,
+    /* IDirectDrawSurface7 */
+    ddraw_surface7_SetPriority,
+    ddraw_surface7_GetPriority,
+    ddraw_surface7_SetLOD,
+    ddraw_surface7_GetLOD,
+};
+
+static const struct IDirectDrawSurface3Vtbl ddraw_surface3_vtbl =
+{
+    /* IUnknown */
+    ddraw_surface3_QueryInterface,
+    ddraw_surface3_AddRef,
+    ddraw_surface3_Release,
+    /* IDirectDrawSurface */
+    ddraw_surface3_AddAttachedSurface,
+    ddraw_surface3_AddOverlayDirtyRect,
+    ddraw_surface3_Blt,
+    ddraw_surface3_BltBatch,
+    ddraw_surface3_BltFast,
+    ddraw_surface3_DeleteAttachedSurface,
+    ddraw_surface3_EnumAttachedSurfaces,
+    ddraw_surface3_EnumOverlayZOrders,
+    ddraw_surface3_Flip,
+    ddraw_surface3_GetAttachedSurface,
+    ddraw_surface3_GetBltStatus,
+    ddraw_surface3_GetCaps,
+    ddraw_surface3_GetClipper,
+    ddraw_surface3_GetColorKey,
+    ddraw_surface3_GetDC,
+    ddraw_surface3_GetFlipStatus,
+    ddraw_surface3_GetOverlayPosition,
+    ddraw_surface3_GetPalette,
+    ddraw_surface3_GetPixelFormat,
+    ddraw_surface3_GetSurfaceDesc,
+    ddraw_surface3_Initialize,
+    ddraw_surface3_IsLost,
+    ddraw_surface3_Lock,
+    ddraw_surface3_ReleaseDC,
+    ddraw_surface3_Restore,
+    ddraw_surface3_SetClipper,
+    ddraw_surface3_SetColorKey,
+    ddraw_surface3_SetOverlayPosition,
+    ddraw_surface3_SetPalette,
+    ddraw_surface3_Unlock,
+    ddraw_surface3_UpdateOverlay,
+    ddraw_surface3_UpdateOverlayDisplay,
+    ddraw_surface3_UpdateOverlayZOrder,
+    /* IDirectDrawSurface2 */
+    ddraw_surface3_GetDDInterface,
+    ddraw_surface3_PageLock,
+    ddraw_surface3_PageUnlock,
+    /* IDirectDrawSurface3 */
+    ddraw_surface3_SetSurfaceDesc,
+};
+
+static const struct IDirectDrawGammaControlVtbl ddraw_gamma_control_vtbl =
+{
+    ddraw_gamma_control_QueryInterface,
+    ddraw_gamma_control_AddRef,
+    ddraw_gamma_control_Release,
+    ddraw_gamma_control_GetGammaRamp,
+    ddraw_gamma_control_SetGammaRamp,
+};
+
+static const struct IDirect3DTexture2Vtbl d3d_texture2_vtbl =
+{
+    d3d_texture2_QueryInterface,
+    d3d_texture2_AddRef,
+    d3d_texture2_Release,
+    d3d_texture2_GetHandle,
+    d3d_texture2_PaletteChanged,
+    d3d_texture2_Load,
 };
+
+static const struct IDirect3DTextureVtbl d3d_texture1_vtbl =
+{
+    d3d_texture1_QueryInterface,
+    d3d_texture1_AddRef,
+    d3d_texture1_Release,
+    d3d_texture1_Initialize,
+    d3d_texture1_GetHandle,
+    d3d_texture1_PaletteChanged,
+    d3d_texture1_Load,
+    d3d_texture1_Unload,
+};
+
+HRESULT ddraw_surface_init(IDirectDrawSurfaceImpl *surface, IDirectDrawImpl *ddraw,
+        DDSURFACEDESC2 *desc, UINT mip_level, WINED3DSURFTYPE surface_type)
+{
+    WINED3DPOOL pool = WINED3DPOOL_DEFAULT;
+    WINED3DSURFACE_DESC wined3d_desc;
+    enum wined3d_format_id format;
+    DWORD usage = 0;
+    HRESULT hr;
+
+    if (!(desc->ddsCaps.dwCaps & (DDSCAPS_VIDEOMEMORY | DDSCAPS_SYSTEMMEMORY))
+            && !((desc->ddsCaps.dwCaps & DDSCAPS_TEXTURE)
+            && (desc->ddsCaps.dwCaps2 & DDSCAPS2_TEXTUREMANAGE)))
+    {
+        /* Tests show surfaces without memory flags get these flags added
+         * right after creation. */
+        desc->ddsCaps.dwCaps |= DDSCAPS_LOCALVIDMEM | DDSCAPS_VIDEOMEMORY;
+    }
+
+    if (desc->ddsCaps.dwCaps & (DDSCAPS_PRIMARYSURFACE | DDSCAPS_3DDEVICE))
+    {
+        usage |= WINED3DUSAGE_RENDERTARGET;
+        desc->ddsCaps.dwCaps |= DDSCAPS_VISIBLE;
+    }
+
+    if (desc->ddsCaps.dwCaps & (DDSCAPS_OVERLAY))
+    {
+        usage |= WINED3DUSAGE_OVERLAY;
+    }
+
+    if (ddraw->depthstencil || (desc->ddsCaps.dwCaps & DDSCAPS_ZBUFFER))
+    {
+        /* The depth stencil creation callback sets this flag. Set the
+         * wined3d usage to let it know it's a depth/stencil surface. */
+        usage |= WINED3DUSAGE_DEPTHSTENCIL;
+    }
+
+    if (desc->ddsCaps.dwCaps & DDSCAPS_SYSTEMMEMORY)
+    {
+        pool = WINED3DPOOL_SYSTEMMEM;
+    }
+    else if (desc->ddsCaps.dwCaps2 & DDSCAPS2_TEXTUREMANAGE)
+    {
+        pool = WINED3DPOOL_MANAGED;
+        /* Managed textures have the system memory flag set. */
+        desc->ddsCaps.dwCaps |= DDSCAPS_SYSTEMMEMORY;
+    }
+    else if (desc->ddsCaps.dwCaps & DDSCAPS_VIDEOMEMORY)
+    {
+        /* Videomemory adds localvidmem. This is mutually exclusive with
+         * systemmemory and texturemanage. */
+        desc->ddsCaps.dwCaps |= DDSCAPS_LOCALVIDMEM;
+    }
+
+    format = PixelFormat_DD2WineD3D(&desc->u4.ddpfPixelFormat);
+    if (format == WINED3DFMT_UNKNOWN)
+    {
+        WARN("Unsupported / unknown pixelformat.\n");
+        return DDERR_INVALIDPIXELFORMAT;
+    }
+
+    surface->lpVtbl = &ddraw_surface7_vtbl;
+    surface->IDirectDrawSurface3_vtbl = &ddraw_surface3_vtbl;
+    surface->IDirectDrawGammaControl_vtbl = &ddraw_gamma_control_vtbl;
+    surface->IDirect3DTexture2_vtbl = &d3d_texture2_vtbl;
+    surface->IDirect3DTexture_vtbl = &d3d_texture1_vtbl;
+    surface->ref = 1;
+    surface->version = 7;
+    surface->ddraw = ddraw;
+
+    surface->surface_desc.dwSize = sizeof(DDSURFACEDESC2);
+    surface->surface_desc.u4.ddpfPixelFormat.dwSize = sizeof(DDPIXELFORMAT);
+    DD_STRUCT_COPY_BYSIZE(&surface->surface_desc, desc);
+
+    surface->first_attached = surface;
+    surface->ImplType = surface_type;
+
+    hr = IWineD3DDevice_CreateSurface(ddraw->wineD3DDevice, desc->dwWidth, desc->dwHeight, format,
+            TRUE /* Lockable */, FALSE /* Discard */, mip_level, usage, pool,
+            WINED3DMULTISAMPLE_NONE, 0 /* MultiSampleQuality */, surface_type, surface,
+            &ddraw_null_wined3d_parent_ops, &surface->WineD3DSurface);
+    if (FAILED(hr))
+    {
+        WARN("Failed to create wined3d surface, hr %#x.\n", hr);
+        return hr;
+    }
+
+    surface->surface_desc.dwFlags |= DDSD_PIXELFORMAT;
+    IWineD3DSurface_GetDesc(surface->WineD3DSurface, &wined3d_desc);
+
+    format = wined3d_desc.format;
+    if (format == WINED3DFMT_UNKNOWN)
+    {
+        FIXME("IWineD3DSurface::GetDesc returned WINED3DFMT_UNKNOWN.\n");
+    }
+    PixelFormat_WineD3DtoDD(&surface->surface_desc.u4.ddpfPixelFormat, format);
+
+    /* Anno 1602 stores the pitch right after surface creation, so make sure
+     * it's there. TODO: Test other fourcc formats. */
+    if (format == WINED3DFMT_DXT1 || format == WINED3DFMT_DXT2 || format == WINED3DFMT_DXT3
+            || format == WINED3DFMT_DXT4 || format == WINED3DFMT_DXT5)
+    {
+        surface->surface_desc.dwFlags |= DDSD_LINEARSIZE;
+        if (format == WINED3DFMT_DXT1)
+        {
+            surface->surface_desc.u1.dwLinearSize = max(4, wined3d_desc.width) * max(4, wined3d_desc.height) / 2;
+        }
+        else
+        {
+            surface->surface_desc.u1.dwLinearSize = max(4, wined3d_desc.width) * max(4, wined3d_desc.height);
+        }
+    }
+    else
+    {
+        surface->surface_desc.dwFlags |= DDSD_PITCH;
+        surface->surface_desc.u1.lPitch = IWineD3DSurface_GetPitch(surface->WineD3DSurface);
+    }
+
+    if (desc->dwFlags & DDSD_CKDESTOVERLAY)
+    {
+        IWineD3DSurface_SetColorKey(surface->WineD3DSurface,
+                DDCKEY_DESTOVERLAY, (WINEDDCOLORKEY *)&desc->u3.ddckCKDestOverlay);
+    }
+    if (desc->dwFlags & DDSD_CKDESTBLT)
+    {
+        IWineD3DSurface_SetColorKey(surface->WineD3DSurface,
+                DDCKEY_DESTBLT, (WINEDDCOLORKEY *)&desc->ddckCKDestBlt);
+    }
+    if (desc->dwFlags & DDSD_CKSRCOVERLAY)
+    {
+        IWineD3DSurface_SetColorKey(surface->WineD3DSurface,
+                DDCKEY_SRCOVERLAY, (WINEDDCOLORKEY *)&desc->ddckCKSrcOverlay);
+    }
+    if (desc->dwFlags & DDSD_CKSRCBLT)
+    {
+        IWineD3DSurface_SetColorKey(surface->WineD3DSurface,
+                DDCKEY_SRCBLT, (WINEDDCOLORKEY *)&desc->ddckCKSrcBlt);
+    }
+    if (desc->dwFlags & DDSD_LPSURFACE)
+    {
+        hr = IWineD3DSurface_SetMem(surface->WineD3DSurface, desc->lpSurface);
+        if (FAILED(hr))
+        {
+            ERR("Failed to set surface memory, hr %#x.\n", hr);
+            IWineD3DSurface_Release(surface->WineD3DSurface);
+            return hr;
+        }
+    }
+
+    return DD_OK;
+}
diff --git a/reactos/dll/directx/wine/ddraw/surface_thunks.c b/reactos/dll/directx/wine/ddraw/surface_thunks.c
deleted file mode 100644 (file)
index d235ff9..0000000
+++ /dev/null
@@ -1,484 +0,0 @@
-/* IDirectDrawSurface3 -> IDirectDrawSurface7 thunks
- * Copyright 2000 TransGaming Technologies Inc.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "wine/port.h"
-#include "wine/debug.h"
-#include <stdarg.h>
-#include <assert.h>
-
-#include "windef.h"
-#include "winbase.h"
-#include "wingdi.h"
-#include "ddraw.h"
-#include "winerror.h"
-
-#include "ddraw_private.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(ddraw_thunk);
-WINE_DECLARE_DEBUG_CHANNEL(ddraw);
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_QueryInterface(LPDIRECTDRAWSURFACE3 This, REFIID iid,
-                                      LPVOID *ppObj)
-{
-    return IDirectDrawSurface7_QueryInterface((IDirectDrawSurface7 *)surface_from_surface3(This), iid, ppObj);
-}
-
-static ULONG WINAPI
-IDirectDrawSurface3Impl_AddRef(LPDIRECTDRAWSURFACE3 This)
-{
-    return IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)surface_from_surface3(This));
-}
-
-static ULONG WINAPI
-IDirectDrawSurface3Impl_Release(LPDIRECTDRAWSURFACE3 iface)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_surface3(iface);
-    TRACE("(%p)\n", This);
-    return IDirectDrawSurface7_Release((IDirectDrawSurface7 *)surface_from_surface3(iface));
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_AddAttachedSurface(LPDIRECTDRAWSURFACE3 iface,
-                                          LPDIRECTDRAWSURFACE3 pAttach)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_surface3(iface);
-    IDirectDrawSurfaceImpl *Surf = surface_from_surface3(pAttach);
-    TRACE("(%p)->(%p)\n", This, Surf);
-
-    /* Tests suggest that
-     * -> offscreen plain surfaces can be attached to other offscreen plain surfaces
-     * -> offscreen plain surfaces can be attached to primaries
-     * -> primaries can be attached to offscreen plain surfaces
-     * -> z buffers can be attached to primaries
-     *
-     */
-    if(This->surface_desc.ddsCaps.dwCaps & (DDSCAPS_PRIMARYSURFACE | DDSCAPS_OFFSCREENPLAIN) &&
-       Surf->surface_desc.ddsCaps.dwCaps & (DDSCAPS_PRIMARYSURFACE | DDSCAPS_OFFSCREENPLAIN))
-    {
-        /* Sizes have to match */
-        if(Surf->surface_desc.dwWidth != This->surface_desc.dwWidth ||
-        Surf->surface_desc.dwHeight != This->surface_desc.dwHeight)
-        {
-            WARN("Surface sizes do not match\n");
-            return DDERR_CANNOTATTACHSURFACE;
-        }
-        /* OK */
-    }
-    else if(This->surface_desc.ddsCaps.dwCaps & (DDSCAPS_PRIMARYSURFACE | DDSCAPS_3DDEVICE) &&
-            Surf->surface_desc.ddsCaps.dwCaps & (DDSCAPS_ZBUFFER))
-    {
-        /* OK */
-    }
-    else
-    {
-        WARN("Invalid attachment combination\n");
-        return DDERR_CANNOTATTACHSURFACE;
-    }
-
-    return IDirectDrawSurfaceImpl_AddAttachedSurface(This,
-                                                     Surf);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_AddOverlayDirtyRect(LPDIRECTDRAWSURFACE3 This,
-                                           LPRECT pRect)
-{
-    return IDirectDrawSurface7_AddOverlayDirtyRect((IDirectDrawSurface7 *)surface_from_surface3(This), pRect);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_Blt(LPDIRECTDRAWSURFACE3 This, LPRECT prcDst,
-                           LPDIRECTDRAWSURFACE3 pSrcSurf, LPRECT prcSrc,
-                           DWORD dwFlags, LPDDBLTFX pFX)
-{
-    return IDirectDrawSurface7_Blt((IDirectDrawSurface7 *)surface_from_surface3(This), prcDst,
-            pSrcSurf ? (IDirectDrawSurface7 *)surface_from_surface3(pSrcSurf) : NULL, prcSrc, dwFlags, pFX);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_BltBatch(LPDIRECTDRAWSURFACE3 This,
-                                LPDDBLTBATCH pBatch, DWORD dwCount,
-                                DWORD dwFlags)
-{
-    return IDirectDrawSurface7_BltBatch((IDirectDrawSurface7 *)surface_from_surface3(This), pBatch, dwCount, dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_BltFast(LPDIRECTDRAWSURFACE3 This, DWORD x, DWORD y,
-                               LPDIRECTDRAWSURFACE3 pSrcSurf, LPRECT prcSrc,
-                               DWORD dwTrans)
-{
-    return IDirectDrawSurface7_BltFast((IDirectDrawSurface7 *)surface_from_surface3(This), x, y,
-            pSrcSurf ? (IDirectDrawSurface7 *)surface_from_surface3(pSrcSurf) : NULL, prcSrc, dwTrans);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_DeleteAttachedSurface(LPDIRECTDRAWSURFACE3 This,
-                                             DWORD dwFlags,
-                                             LPDIRECTDRAWSURFACE3 pAttached)
-{
-    return IDirectDrawSurface7_DeleteAttachedSurface((IDirectDrawSurface7 *)surface_from_surface3(This), dwFlags,
-            pAttached ? (IDirectDrawSurface7 *)surface_from_surface3(pAttached) : NULL);
-}
-
-struct callback_info
-{
-    LPDDENUMSURFACESCALLBACK callback;
-    LPVOID context;
-};
-
-static HRESULT CALLBACK
-EnumCallback(LPDIRECTDRAWSURFACE7 iface, LPDDSURFACEDESC2 pDDSD,
-            LPVOID context)
-{
-    const struct callback_info* info = context;
-
-#if 0
-    /* This is an outgoing conversion so we have to do it. */
-    DDSURFACEDESC ddsd;
-    memset(&ddsd, 0, sizeof(ddsd));
-    ddsd.dwSize = sizeof(ddsd);
-    DDRAW_Convert_DDSURFACEDESC_2_To_1(pDDSD, &ddsd);
-#endif
-
-    /* the LPDDSURFACEDESC2 -> LPDDSURFACEDESC coercion is safe, since
-     * the data format is compatible with older enum procs */
-    return info->callback(iface ?
-            (IDirectDrawSurface *)&((IDirectDrawSurfaceImpl *)iface)->IDirectDrawSurface3_vtbl : NULL,
-            (LPDDSURFACEDESC)pDDSD, info->context);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_EnumAttachedSurfaces(LPDIRECTDRAWSURFACE3 This,
-                                            LPVOID context,
-                                            LPDDENUMSURFACESCALLBACK callback)
-{
-    struct callback_info info;
-
-    info.callback = callback;
-    info.context  = context;
-
-    return IDirectDrawSurface7_EnumAttachedSurfaces((IDirectDrawSurface7 *)surface_from_surface3(This),
-            &info, EnumCallback);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_EnumOverlayZOrders(LPDIRECTDRAWSURFACE3 This,
-                                          DWORD dwFlags, LPVOID context,
-                                          LPDDENUMSURFACESCALLBACK callback)
-{
-    struct callback_info info;
-
-    info.callback = callback;
-    info.context  = context;
-
-    return IDirectDrawSurface7_EnumOverlayZOrders((IDirectDrawSurface7 *)surface_from_surface3(This),
-            dwFlags, &info, EnumCallback);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_Flip(LPDIRECTDRAWSURFACE3 This,
-                            LPDIRECTDRAWSURFACE3 pOverride, DWORD dwFlags)
-{
-    return IDirectDrawSurface7_Flip((IDirectDrawSurface7 *)surface_from_surface3(This),
-            pOverride ? (IDirectDrawSurface7 *)surface_from_surface3(pOverride) : NULL, dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetAttachedSurface(LPDIRECTDRAWSURFACE3 This,
-                                          LPDDSCAPS pCaps,
-                                          LPDIRECTDRAWSURFACE3* ppAttached)
-{
-    DDSCAPS2 caps;
-    LPDIRECTDRAWSURFACE7 pAttached7;
-    HRESULT hr;
-
-    caps.dwCaps  = pCaps->dwCaps;
-    caps.dwCaps2 = 0;
-    caps.dwCaps3 = 0;
-    caps.dwCaps4 = 0;
-
-    hr = IDirectDrawSurface7_GetAttachedSurface((IDirectDrawSurface7 *)surface_from_surface3(This), &caps, &pAttached7);
-    if (FAILED(hr)) *ppAttached = NULL;
-    else *ppAttached = pAttached7 ?
-            (IDirectDrawSurface3 *)&((IDirectDrawSurfaceImpl *)pAttached7)->IDirectDrawSurface3_vtbl : NULL;
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetBltStatus(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags)
-{
-    return IDirectDrawSurface7_GetBltStatus((IDirectDrawSurface7 *)surface_from_surface3(This), dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetCaps(LPDIRECTDRAWSURFACE3 This, LPDDSCAPS pCaps)
-{
-    DDSCAPS2 caps;
-    HRESULT hr;
-
-    hr = IDirectDrawSurface7_GetCaps((IDirectDrawSurface7 *)surface_from_surface3(This), &caps);
-    if (FAILED(hr)) return hr;
-
-    pCaps->dwCaps = caps.dwCaps;
-    return hr;
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetClipper(LPDIRECTDRAWSURFACE3 This,
-                                  LPDIRECTDRAWCLIPPER* ppClipper)
-{
-    return IDirectDrawSurface7_GetClipper((IDirectDrawSurface7 *)surface_from_surface3(This), ppClipper);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetColorKey(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags,
-                                   LPDDCOLORKEY pCKey)
-{
-    return IDirectDrawSurface7_GetColorKey((IDirectDrawSurface7 *)surface_from_surface3(This), dwFlags, pCKey);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetDC(LPDIRECTDRAWSURFACE3 This, HDC* phDC)
-{
-    return IDirectDrawSurface7_GetDC((IDirectDrawSurface7 *)surface_from_surface3(This), phDC);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetFlipStatus(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags)
-{
-    return IDirectDrawSurface7_GetFlipStatus((IDirectDrawSurface7 *)surface_from_surface3(This), dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetOverlayPosition(LPDIRECTDRAWSURFACE3 This, LPLONG pX,
-                                      LPLONG pY)
-{
-    return IDirectDrawSurface7_GetOverlayPosition((IDirectDrawSurface7 *)surface_from_surface3(This), pX, pY);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetPalette(LPDIRECTDRAWSURFACE3 This,
-                                  LPDIRECTDRAWPALETTE* ppPalette)
-{
-    return IDirectDrawSurface7_GetPalette((IDirectDrawSurface7 *)surface_from_surface3(This), ppPalette);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetPixelFormat(LPDIRECTDRAWSURFACE3 This,
-                                      LPDDPIXELFORMAT pPixelFormat)
-{
-    return IDirectDrawSurface7_GetPixelFormat((IDirectDrawSurface7 *)surface_from_surface3(This), pPixelFormat);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetSurfaceDesc(LPDIRECTDRAWSURFACE3 iface,
-                                      LPDDSURFACEDESC pDDSD)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_surface3(iface);
-
-    TRACE_(ddraw)("(%p)->(%p)\n",This,pDDSD);
-
-    if(!pDDSD)
-        return DDERR_INVALIDPARAMS;
-
-    if (pDDSD->dwSize != sizeof(DDSURFACEDESC))
-    {
-        WARN("Incorrect struct size %d, returning DDERR_INVALIDPARAMS\n",pDDSD->dwSize);
-        return DDERR_INVALIDPARAMS;
-    }
-
-    EnterCriticalSection(&ddraw_cs);
-    DD_STRUCT_COPY_BYSIZE(pDDSD,(DDSURFACEDESC *) &This->surface_desc);
-    TRACE("Returning surface desc:\n");
-    if (TRACE_ON(ddraw))
-    {
-        /* DDRAW_dump_surface_desc handles the smaller size */
-        DDRAW_dump_surface_desc((DDSURFACEDESC2 *) pDDSD);
-    }
-
-    LeaveCriticalSection(&ddraw_cs);
-    return DD_OK;
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_Initialize(LPDIRECTDRAWSURFACE3 This, LPDIRECTDRAW pDD,
-                                  LPDDSURFACEDESC pDDSD)
-{
-    return IDirectDrawSurface7_Initialize((IDirectDrawSurface7 *)surface_from_surface3(This),
-            pDD, (LPDDSURFACEDESC2)pDDSD);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_IsLost(LPDIRECTDRAWSURFACE3 This)
-{
-    return IDirectDrawSurface7_IsLost((IDirectDrawSurface7 *)surface_from_surface3(This));
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_Lock(LPDIRECTDRAWSURFACE3 This, LPRECT pRect,
-                            LPDDSURFACEDESC pDDSD, DWORD dwFlags, HANDLE h)
-{
-    return IDirectDrawSurface7_Lock((IDirectDrawSurface7 *)surface_from_surface3(This),
-            pRect, (LPDDSURFACEDESC2)pDDSD, dwFlags, h);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_ReleaseDC(LPDIRECTDRAWSURFACE3 This, HDC hDC)
-{
-    return IDirectDrawSurface7_ReleaseDC((IDirectDrawSurface7 *)surface_from_surface3(This), hDC);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_Restore(LPDIRECTDRAWSURFACE3 This)
-{
-    return IDirectDrawSurface7_Restore((IDirectDrawSurface7 *)surface_from_surface3(This));
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_SetClipper(LPDIRECTDRAWSURFACE3 This,
-                                  LPDIRECTDRAWCLIPPER pClipper)
-{
-    return IDirectDrawSurface7_SetClipper((IDirectDrawSurface7 *)surface_from_surface3(This), pClipper);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_SetColorKey(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags,
-                                   LPDDCOLORKEY pCKey)
-{
-    return IDirectDrawSurface7_SetColorKey((IDirectDrawSurface7 *)surface_from_surface3(This), dwFlags, pCKey);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_SetOverlayPosition(LPDIRECTDRAWSURFACE3 This, LONG x,
-                                      LONG y)
-{
-    return IDirectDrawSurface7_SetOverlayPosition((IDirectDrawSurface7 *)surface_from_surface3(This), x, y);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_SetPalette(LPDIRECTDRAWSURFACE3 This,
-                                  LPDIRECTDRAWPALETTE pPalette)
-{
-    return IDirectDrawSurface7_SetPalette((IDirectDrawSurface7 *)surface_from_surface3(This), pPalette);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_Unlock(LPDIRECTDRAWSURFACE3 This, LPVOID data)
-{
-    /* data might not be the LPRECT of later versions, so drop it. */
-    return IDirectDrawSurface7_Unlock((IDirectDrawSurface7 *)surface_from_surface3(This), NULL);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_UpdateOverlay(LPDIRECTDRAWSURFACE3 This, LPRECT prcSrc,
-                                     LPDIRECTDRAWSURFACE3 pDstSurf,
-                                     LPRECT prcDst, DWORD dwFlags,
-                                     LPDDOVERLAYFX pFX)
-{
-    return IDirectDrawSurface7_UpdateOverlay((IDirectDrawSurface7 *)surface_from_surface3(This), prcSrc,
-            pDstSurf ? (IDirectDrawSurface7 *)surface_from_surface3(pDstSurf) : NULL, prcDst, dwFlags, pFX);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_UpdateOverlayDisplay(LPDIRECTDRAWSURFACE3 This,
-                                            DWORD dwFlags)
-{
-    return IDirectDrawSurface7_UpdateOverlayDisplay((IDirectDrawSurface7 *)surface_from_surface3(This), dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_UpdateOverlayZOrder(LPDIRECTDRAWSURFACE3 This,
-                                           DWORD dwFlags,
-                                           LPDIRECTDRAWSURFACE3 pSurfReference)
-{
-    return IDirectDrawSurface7_UpdateOverlayZOrder((IDirectDrawSurface7 *)surface_from_surface3(This), dwFlags,
-            pSurfReference ? (IDirectDrawSurface7 *)surface_from_surface3(pSurfReference) : NULL);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_GetDDInterface(LPDIRECTDRAWSURFACE3 This, LPVOID* ppDD)
-{
-    return IDirectDrawSurface7_GetDDInterface((IDirectDrawSurface7 *)surface_from_surface3(This), ppDD);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_PageLock(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags)
-{
-    return IDirectDrawSurface7_PageLock((IDirectDrawSurface7 *)surface_from_surface3(This), dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_PageUnlock(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags)
-{
-    return IDirectDrawSurface7_PageUnlock((IDirectDrawSurface7 *)surface_from_surface3(This), dwFlags);
-}
-
-static HRESULT WINAPI
-IDirectDrawSurface3Impl_SetSurfaceDesc(LPDIRECTDRAWSURFACE3 This,
-                                      LPDDSURFACEDESC pDDSD, DWORD dwFlags)
-{
-    return IDirectDrawSurface7_SetSurfaceDesc((IDirectDrawSurface7 *)surface_from_surface3(This),
-            (LPDDSURFACEDESC2)pDDSD, dwFlags);
-}
-
-const IDirectDrawSurface3Vtbl IDirectDrawSurface3_Vtbl =
-{
-    IDirectDrawSurface3Impl_QueryInterface,
-    IDirectDrawSurface3Impl_AddRef,
-    IDirectDrawSurface3Impl_Release,
-    IDirectDrawSurface3Impl_AddAttachedSurface,
-    IDirectDrawSurface3Impl_AddOverlayDirtyRect,
-    IDirectDrawSurface3Impl_Blt,
-    IDirectDrawSurface3Impl_BltBatch,
-    IDirectDrawSurface3Impl_BltFast,
-    IDirectDrawSurface3Impl_DeleteAttachedSurface,
-    IDirectDrawSurface3Impl_EnumAttachedSurfaces,
-    IDirectDrawSurface3Impl_EnumOverlayZOrders,
-    IDirectDrawSurface3Impl_Flip,
-    IDirectDrawSurface3Impl_GetAttachedSurface,
-    IDirectDrawSurface3Impl_GetBltStatus,
-    IDirectDrawSurface3Impl_GetCaps,
-    IDirectDrawSurface3Impl_GetClipper,
-    IDirectDrawSurface3Impl_GetColorKey,
-    IDirectDrawSurface3Impl_GetDC,
-    IDirectDrawSurface3Impl_GetFlipStatus,
-    IDirectDrawSurface3Impl_GetOverlayPosition,
-    IDirectDrawSurface3Impl_GetPalette,
-    IDirectDrawSurface3Impl_GetPixelFormat,
-    IDirectDrawSurface3Impl_GetSurfaceDesc,
-    IDirectDrawSurface3Impl_Initialize,
-    IDirectDrawSurface3Impl_IsLost,
-    IDirectDrawSurface3Impl_Lock,
-    IDirectDrawSurface3Impl_ReleaseDC,
-    IDirectDrawSurface3Impl_Restore,
-    IDirectDrawSurface3Impl_SetClipper,
-    IDirectDrawSurface3Impl_SetColorKey,
-    IDirectDrawSurface3Impl_SetOverlayPosition,
-    IDirectDrawSurface3Impl_SetPalette,
-    IDirectDrawSurface3Impl_Unlock,
-    IDirectDrawSurface3Impl_UpdateOverlay,
-    IDirectDrawSurface3Impl_UpdateOverlayDisplay,
-    IDirectDrawSurface3Impl_UpdateOverlayZOrder,
-    IDirectDrawSurface3Impl_GetDDInterface,
-    IDirectDrawSurface3Impl_PageLock,
-    IDirectDrawSurface3Impl_PageUnlock,
-    IDirectDrawSurface3Impl_SetSurfaceDesc
-};
diff --git a/reactos/dll/directx/wine/ddraw/texture.c b/reactos/dll/directx/wine/ddraw/texture.c
deleted file mode 100644 (file)
index 13b14f6..0000000
+++ /dev/null
@@ -1,498 +0,0 @@
-/* Direct3D Texture
- * Copyright (c) 1998 Lionel ULMER
- * Copyright (c) 2006 Stefan DÖSINGER
- *
- * This file contains the implementation of interface Direct3DTexture2.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
- */
-
-#include "config.h"
-#include "wine/port.h"
-
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-#define NONAMELESSUNION
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
-#include "ddraw_private.h"
-#include "wine/debug.h"
-
-WINE_DEFAULT_DEBUG_CHANNEL(d3d7);
-WINE_DECLARE_DEBUG_CHANNEL(ddraw_thunk);
-
-/*****************************************************************************
- * IUnknown interfaces. They are thunks to IDirectDrawSurface7
- *****************************************************************************/
-static HRESULT WINAPI
-Thunk_IDirect3DTextureImpl_2_QueryInterface(IDirect3DTexture2 *iface,
-                                            REFIID riid,
-                                            void **obj)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture2(iface);
-    TRACE("(%p)->(%s,%p) thunking to IDirectDrawSurface7 interface.\n", This, debugstr_guid(riid), obj);
-    return IDirectDrawSurface7_QueryInterface((IDirectDrawSurface7 *)This, riid, obj);
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DTextureImpl_1_QueryInterface(IDirect3DTexture *iface,
-                                            REFIID riid,
-                                            void **obj)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture1(iface);
-    TRACE("(%p)->(%s,%p) thunking to IDirectDrawSurface7 interface.\n", This, debugstr_guid(riid), obj);
-
-    return IDirectDrawSurface7_QueryInterface((IDirectDrawSurface7 *)This, riid, obj);
-}
-
-static ULONG WINAPI
-Thunk_IDirect3DTextureImpl_2_AddRef(IDirect3DTexture2 *iface)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture2(iface);
-    TRACE("(%p)->() thunking to IDirectDrawSurface7 interface.\n", This);
-
-    return IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)This);
-}
-
-static ULONG WINAPI
-Thunk_IDirect3DTextureImpl_1_AddRef(IDirect3DTexture *iface)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture1(iface);
-    TRACE("(%p)->() thunking to IDirectDrawSurface7 interface.\n", This);
-
-    return IDirectDrawSurface7_AddRef((IDirectDrawSurface7 *)This);
-}
-
-static ULONG WINAPI
-Thunk_IDirect3DTextureImpl_2_Release(IDirect3DTexture2 *iface)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture2(iface);
-    TRACE("(%p)->() thunking to IDirectDrawSurface7 interface.\n", This);
-
-    return IDirectDrawSurface7_Release((IDirectDrawSurface7 *)This);
-}
-
-
-static ULONG WINAPI
-Thunk_IDirect3DTextureImpl_1_Release(IDirect3DTexture *iface)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture1(iface);
-    TRACE("(%p)->() thunking to IDirectDrawSurface7 interface.\n", This);
-
-    return IDirectDrawSurface7_Release((IDirectDrawSurface7 *)This);
-}
-
-/*****************************************************************************
- * IDirect3DTexture interface
- *****************************************************************************/
-
-/*****************************************************************************
- * IDirect3DTexture1::Initialize
- *
- * The sdk says it's not implemented
- *
- * Params:
- *  ?
- *
- * Returns
- *  DDERR_UNSUPPORTED
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DTextureImpl_1_Initialize(IDirect3DTexture *iface,
-                                  IDirect3DDevice *Direct3DDevice,
-                                  IDirectDrawSurface *DDSurface)
-{
-    TRACE("(%p)->(%p,%p) Not implemented\n", iface, Direct3DDevice, DDSurface);
-    return DDERR_UNSUPPORTED; /* Unchecked */
-}
-
-/*****************************************************************************
- * IDirect3DTexture2::PaletteChanged
- *
- * Informs the texture about a palette change
- *
- * Params:
- *  Start: Start index of the change
- *  Count: The number of changed entries
- *
- * Returns
- *  D3D_OK, because it's a stub
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DTextureImpl_PaletteChanged(IDirect3DTexture2 *iface,
-                                         DWORD Start,
-                                         DWORD Count)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture2(iface);
-    FIXME("(%p)->(%08x,%08x): stub!\n", This, Start, Count);
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DTextureImpl_1_PaletteChanged(IDirect3DTexture *iface,
-                                            DWORD Start,
-                                            DWORD Count)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture1(iface);
-    TRACE("(%p)->(%08x,%08x) thunking to IDirect3DTexture2 interface.\n", This, Start, Count);
-
-    return IDirect3DTexture2_PaletteChanged((IDirect3DTexture2 *)&This->IDirect3DTexture2_vtbl, Start, Count);
-}
-
-
-/*****************************************************************************
- * IDirect3DTexture::Unload
- *
- * DX5 SDK: "The IDirect3DTexture2::Unload method is not implemented
- *
- *
- * Returns:
- *  DDERR_UNSUPPORTED
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DTextureImpl_1_Unload(IDirect3DTexture *iface)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture1(iface);
-    TRACE("(%p)->(): not implemented!\n", This);
-    return DDERR_UNSUPPORTED;
-}
-
-/*****************************************************************************
- * IDirect3DTexture2::GetHandle
- *
- * Returns handle for the texture. At the moment, the interface
- * to the IWineD3DTexture is used.
- *
- * Params:
- *  Direct3DDevice2: Device this handle is assigned to
- *  Handle: Address to store the handle at.
- *
- * Returns:
- *  D3D_OK
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DTextureImpl_GetHandle(IDirect3DTexture2 *iface,
-                                    IDirect3DDevice2 *Direct3DDevice2,
-                                    D3DTEXTUREHANDLE *lpHandle)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture2(iface);
-    IDirect3DDeviceImpl *d3d = device_from_device2(Direct3DDevice2);
-
-    TRACE("(%p)->(%p,%p)\n", This, d3d, lpHandle);
-
-    EnterCriticalSection(&ddraw_cs);
-    if(!This->Handle)
-    {
-        This->Handle = IDirect3DDeviceImpl_CreateHandle(d3d);
-        if(This->Handle)
-        {
-            d3d->Handles[This->Handle - 1].ptr = This;
-            d3d->Handles[This->Handle - 1].type = DDrawHandle_Texture;
-        }
-    }
-    *lpHandle = This->Handle;
-
-    TRACE(" returning handle %08x.\n", *lpHandle);
-
-    LeaveCriticalSection(&ddraw_cs);
-    return D3D_OK;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DTextureImpl_1_GetHandle(IDirect3DTexture *iface,
-                                       LPDIRECT3DDEVICE lpDirect3DDevice,
-                                       LPD3DTEXTUREHANDLE lpHandle)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture1(iface);
-    IDirect3DDeviceImpl *d3d = device_from_device1(lpDirect3DDevice);
-    IDirect3DTexture2 *d3d_texture2 = (IDirect3DTexture2 *)&This->IDirect3DTexture2_vtbl;
-    IDirect3DDevice2 *d3d_device2 = (IDirect3DDevice2 *)&d3d->IDirect3DDevice2_vtbl;
-
-    TRACE_(ddraw_thunk)("(%p)->(%p,%p) thunking to IDirect3DTexture2 interface.\n", This, d3d, lpHandle);
-
-    return IDirect3DTexture2_GetHandle(d3d_texture2, d3d_device2, lpHandle);
-}
-
-
-/*****************************************************************************
- * get_sub_mimaplevel
- *
- * Helper function that returns the next mipmap level
- *
- * tex_ptr: Surface of which to return the next level
- *
- *****************************************************************************/
-static IDirectDrawSurfaceImpl *
-get_sub_mimaplevel(IDirectDrawSurfaceImpl *tex_ptr)
-{
-    /* Now go down the mipmap chain to the next surface */
-    static DDSCAPS2 mipmap_caps = { DDSCAPS_MIPMAP | DDSCAPS_TEXTURE, 0, 0, {0} };
-    LPDIRECTDRAWSURFACE7 next_level;
-    IDirectDrawSurfaceImpl *surf_ptr;
-    HRESULT hr;
-
-    hr = IDirectDrawSurface7_GetAttachedSurface((IDirectDrawSurface7 *)tex_ptr, &mipmap_caps, &next_level);
-    if (FAILED(hr)) return NULL;
-
-    surf_ptr = (IDirectDrawSurfaceImpl *)next_level;
-    IDirectDrawSurface7_Release(next_level);
-
-    return surf_ptr;
-}
-
-/*****************************************************************************
- * IDirect3DTexture2::Load
- *
- * Loads a texture created with the DDSCAPS_ALLOCONLOAD
- *
- * This function isn't relayed to WineD3D because the whole interface is
- * implemented in DDraw only. For speed improvements a implementation which
- * takes OpenGL more into account could be placed into WineD3D.
- *
- * Params:
- *  D3DTexture2: Address of the texture to load
- *
- * Returns:
- *  D3D_OK on success
- *  D3DERR_TEXTURE_LOAD_FAILED.
- *
- *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DTextureImpl_Load(IDirect3DTexture2 *iface,
-                          IDirect3DTexture2 *D3DTexture2)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture2(iface);
-    IDirectDrawSurfaceImpl *src_ptr = surface_from_texture2(D3DTexture2);
-    HRESULT ret_value = D3D_OK;
-    if(src_ptr == This)
-    {
-        TRACE("copying surface %p to surface %p, why?\n", src_ptr, This);
-        return ret_value;
-    }
-
-    TRACE("(%p)->(%p)\n", This, src_ptr);
-    EnterCriticalSection(&ddraw_cs);
-
-    if (((src_ptr->surface_desc.ddsCaps.dwCaps & DDSCAPS_MIPMAP) != (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_MIPMAP)) ||
-        (src_ptr->surface_desc.u2.dwMipMapCount != This->surface_desc.u2.dwMipMapCount))
-    {
-        ERR("Trying to load surfaces with different mip-map counts !\n");
-    }
-
-    while(1)
-    {
-        IWineD3DPalette *wine_pal, *wine_pal_src;
-        IDirectDrawPalette *pal = NULL, *pal_src = NULL;
-        DDSURFACEDESC *src_d, *dst_d;
-
-        TRACE(" copying surface %p to surface %p (mipmap level %d)\n", src_ptr, This, src_ptr->mipmap_level);
-
-        /* Suppress the ALLOCONLOAD flag */
-        This->surface_desc.ddsCaps.dwCaps &= ~DDSCAPS_ALLOCONLOAD;
-
-        /* Get the palettes */
-        ret_value = IWineD3DSurface_GetPalette(This->WineD3DSurface, &wine_pal);
-        if( ret_value != D3D_OK)
-        {
-            ERR("IWineD3DSurface::GetPalette failed! This is unexpected\n");
-            LeaveCriticalSection(&ddraw_cs);
-            return D3DERR_TEXTURE_LOAD_FAILED;
-        }
-        if(wine_pal)
-        {
-            ret_value = IWineD3DPalette_GetParent(wine_pal, (IUnknown **) &pal);
-            if(ret_value != D3D_OK)
-            {
-                ERR("IWineD3DPalette::GetParent failed! This is unexpected\n");
-                LeaveCriticalSection(&ddraw_cs);
-                return D3DERR_TEXTURE_LOAD_FAILED;
-            }
-        }
-
-        ret_value = IWineD3DSurface_GetPalette(src_ptr->WineD3DSurface, &wine_pal_src);
-        if( ret_value != D3D_OK)
-        {
-            ERR("IWineD3DSurface::GetPalette failed! This is unexpected\n");
-            LeaveCriticalSection(&ddraw_cs);
-            return D3DERR_TEXTURE_LOAD_FAILED;
-        }
-        if(wine_pal_src)
-        {
-            ret_value = IWineD3DPalette_GetParent(wine_pal_src, (IUnknown **) &pal_src);
-            if(ret_value != D3D_OK)
-            {
-                ERR("IWineD3DPalette::GetParent failed! This is unexpected\n");
-                if (pal) IDirectDrawPalette_Release(pal);
-                LeaveCriticalSection(&ddraw_cs);
-                return D3DERR_TEXTURE_LOAD_FAILED;
-            }
-        }
-
-        if (pal_src != NULL)
-        {
-            PALETTEENTRY palent[256];
-
-            if (pal == NULL)
-            {
-                IDirectDrawPalette_Release(pal_src);
-                LeaveCriticalSection(&ddraw_cs);
-                return DDERR_NOPALETTEATTACHED;
-            }
-            IDirectDrawPalette_GetEntries(pal_src, 0, 0, 256, palent);
-            IDirectDrawPalette_SetEntries(pal, 0, 0, 256, palent);
-        }
-
-        if (pal) IDirectDrawPalette_Release(pal);
-        if (pal_src) IDirectDrawPalette_Release(pal_src);
-
-        /* Copy one surface on the other */
-        dst_d = (DDSURFACEDESC *)&(This->surface_desc);
-        src_d = (DDSURFACEDESC *)&(src_ptr->surface_desc);
-
-        if ((src_d->dwWidth != dst_d->dwWidth) || (src_d->dwHeight != dst_d->dwHeight))
-        {
-            /* Should also check for same pixel format, u1.lPitch, ... */
-            ERR("Error in surface sizes\n");
-            LeaveCriticalSection(&ddraw_cs);
-            return D3DERR_TEXTURE_LOAD_FAILED;
-        }
-        else
-        {
-            WINED3DLOCKED_RECT pSrcRect, pDstRect;
-
-            /* LPDIRECT3DDEVICE2 d3dd = (LPDIRECT3DDEVICE2) This->D3Ddevice; */
-            /* I should put a macro for the calculus of bpp */
-
-            /* Copy also the ColorKeying stuff */
-            if (src_d->dwFlags & DDSD_CKSRCBLT)
-            {
-                dst_d->dwFlags |= DDSD_CKSRCBLT;
-                dst_d->ddckCKSrcBlt.dwColorSpaceLowValue = src_d->ddckCKSrcBlt.dwColorSpaceLowValue;
-                dst_d->ddckCKSrcBlt.dwColorSpaceHighValue = src_d->ddckCKSrcBlt.dwColorSpaceHighValue;
-            }
-
-            /* Copy the main memory texture into the surface that corresponds to the OpenGL
-              texture object. */
-
-            ret_value = IWineD3DSurface_LockRect(src_ptr->WineD3DSurface, &pSrcRect, NULL, 0);
-            if(ret_value != D3D_OK)
-            {
-                ERR(" (%p) Locking the source surface failed\n", This);
-                LeaveCriticalSection(&ddraw_cs);
-                return D3DERR_TEXTURE_LOAD_FAILED;
-            }
-
-            ret_value = IWineD3DSurface_LockRect(This->WineD3DSurface, &pDstRect, NULL, 0);
-            if(ret_value != D3D_OK)
-            {
-                ERR(" (%p) Locking the destination surface failed\n", This);
-                IWineD3DSurface_UnlockRect(src_ptr->WineD3DSurface);
-                LeaveCriticalSection(&ddraw_cs);
-                return D3DERR_TEXTURE_LOAD_FAILED;
-            }
-
-            if (This->surface_desc.u4.ddpfPixelFormat.dwFlags & DDPF_FOURCC)
-                memcpy(pDstRect.pBits, pSrcRect.pBits, src_ptr->surface_desc.u1.dwLinearSize);
-            else
-                memcpy(pDstRect.pBits, pSrcRect.pBits, pSrcRect.Pitch * src_d->dwHeight);
-
-            IWineD3DSurface_UnlockRect(src_ptr->WineD3DSurface);
-            IWineD3DSurface_UnlockRect(This->WineD3DSurface);
-        }
-
-        if (src_ptr->surface_desc.ddsCaps.dwCaps & DDSCAPS_MIPMAP)
-        {
-            src_ptr = get_sub_mimaplevel(src_ptr);
-        }
-        else
-        {
-            src_ptr = NULL;
-        }
-        if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_MIPMAP)
-        {
-            This = get_sub_mimaplevel(This);
-        }
-        else
-        {
-            This = NULL;
-        }
-
-        if ((src_ptr == NULL) || (This == NULL))
-        {
-            if (src_ptr != This)
-            {
-                ERR(" Loading surface with different mipmap structure !!!\n");
-            }
-            break;
-        }
-    }
-
-    LeaveCriticalSection(&ddraw_cs);
-    return ret_value;
-}
-
-static HRESULT WINAPI
-Thunk_IDirect3DTextureImpl_1_Load(IDirect3DTexture *iface,
-                                  IDirect3DTexture *D3DTexture)
-{
-    IDirectDrawSurfaceImpl *This = surface_from_texture1(iface);
-    IDirectDrawSurfaceImpl *Texture = surface_from_texture1(D3DTexture);
-    TRACE("(%p)->(%p) thunking to IDirect3DTexture2 interface.\n", This, Texture);
-
-    return IDirect3DTexture2_Load((IDirect3DTexture2 *)&This->IDirect3DTexture2_vtbl,
-            D3DTexture ? (IDirect3DTexture2 *)&surface_from_texture1(D3DTexture)->IDirect3DTexture2_vtbl : NULL);
-}
-
-/*****************************************************************************
- * The VTables
- *****************************************************************************/
-const IDirect3DTexture2Vtbl IDirect3DTexture2_Vtbl =
-{
-    Thunk_IDirect3DTextureImpl_2_QueryInterface,
-    Thunk_IDirect3DTextureImpl_2_AddRef,
-    Thunk_IDirect3DTextureImpl_2_Release,
-    IDirect3DTextureImpl_GetHandle,
-    IDirect3DTextureImpl_PaletteChanged,
-    IDirect3DTextureImpl_Load,
-};
-
-
-const IDirect3DTextureVtbl IDirect3DTexture1_Vtbl =
-{
-    Thunk_IDirect3DTextureImpl_1_QueryInterface,
-    Thunk_IDirect3DTextureImpl_1_AddRef,
-    Thunk_IDirect3DTextureImpl_1_Release,
-    IDirect3DTextureImpl_1_Initialize,
-    Thunk_IDirect3DTextureImpl_1_GetHandle,
-    Thunk_IDirect3DTextureImpl_1_PaletteChanged,
-    Thunk_IDirect3DTextureImpl_1_Load,
-    IDirect3DTextureImpl_1_Unload,
-};
index 5166b16..039a3a0 100644 (file)
  */
 
 #include "config.h"
-
-#define NONAMELESSUNION
+#include "wine/port.h"
 
 #include "ddraw_private.h"
-#include "wine/debug.h"
 
 WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
@@ -35,19 +33,17 @@ static void DDRAW_dump_pixelformat(const DDPIXELFORMAT *pf);
 /*****************************************************************************
  * PixelFormat_WineD3DtoDD
  *
- * Converts an WINED3DFORMAT value into a DDPIXELFORMAT structure
+ * Converts an wined3d format ID into a DDPIXELFORMAT structure
  *
  * Params:
  *  DDPixelFormat: Address of the structure to write the pixel format to
  *  WineD3DFormat: Source format
  *
  *****************************************************************************/
-void
-PixelFormat_WineD3DtoDD(DDPIXELFORMAT *DDPixelFormat,
-                        WINED3DFORMAT WineD3DFormat)
+void PixelFormat_WineD3DtoDD(DDPIXELFORMAT *DDPixelFormat, enum wined3d_format_id WineD3DFormat)
 {
     DWORD Size = DDPixelFormat->dwSize;
-    TRACE("Converting WINED3DFORMAT %d to DDRAW\n", WineD3DFormat);
+    TRACE("Converting wined3d format %#x to DDRAW.\n", WineD3DFormat);
 
     if(Size==0) return;
 
@@ -315,6 +311,16 @@ PixelFormat_WineD3DtoDD(DDPIXELFORMAT *DDPixelFormat,
             DDPixelFormat->u5.dwLuminanceAlphaBitMask = 0x00000000;
             break;
 
+        case WINED3DFMT_R16G16_SNORM:
+            DDPixelFormat->dwFlags = DDPF_BUMPDUDV;
+            DDPixelFormat->dwFourCC = 0;
+            DDPixelFormat->u1.dwBumpBitCount = 32;
+            DDPixelFormat->u2.dwBumpDuBitMask =         0x0000ffff;
+            DDPixelFormat->u3.dwBumpDvBitMask =         0xffff0000;
+            DDPixelFormat->u4.dwBumpLuminanceBitMask =  0x00000000;
+            DDPixelFormat->u5.dwLuminanceAlphaBitMask = 0x00000000;
+            break;
+
         case WINED3DFMT_R5G5_SNORM_L6_UNORM:
             DDPixelFormat->dwFlags = DDPF_BUMPDUDV;
             DDPixelFormat->dwFourCC = 0;
@@ -347,17 +353,17 @@ PixelFormat_WineD3DtoDD(DDPIXELFORMAT *DDPixelFormat,
 /*****************************************************************************
  * PixelFormat_DD2WineD3D
  *
- * Reads a DDPIXELFORMAT structure and returns the equal WINED3DFORMAT
+ * Reads a DDPIXELFORMAT structure and returns the equivalent wined3d
+ * format ID.
  *
  * Params:
  *  DDPixelFormat: The source format
  *
  * Returns:
- *  The WINED3DFORMAT equal to the DDraw format
+ *  The wined3d format ID equivalent to the DDraw format
  *  WINED3DFMT_UNKNOWN if a matching format wasn't found
  *****************************************************************************/
-WINED3DFORMAT
-PixelFormat_DD2WineD3D(const DDPIXELFORMAT *DDPixelFormat)
+enum wined3d_format_id PixelFormat_DD2WineD3D(const DDPIXELFORMAT *DDPixelFormat)
 {
     TRACE("Convert a DirectDraw Pixelformat to a WineD3D Pixelformat\n");
     if(TRACE_ON(ddraw))
@@ -572,47 +578,7 @@ PixelFormat_DD2WineD3D(const DDPIXELFORMAT *DDPixelFormat)
     }
     else if(DDPixelFormat->dwFlags & DDPF_FOURCC)
     {
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('U', 'Y', 'V', 'Y'))
-        {
-            return WINED3DFMT_UYVY;
-        }
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('Y', 'U', 'Y', '2'))
-        {
-            return WINED3DFMT_YUY2;
-        }
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('Y', 'V', '1', '2'))
-        {
-            return WINED3DFMT_YV12;
-        }
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('D', 'X', 'T', '1'))
-        {
-            return WINED3DFMT_DXT1;
-        }
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('D', 'X', 'T', '2'))
-        {
-            return WINED3DFMT_DXT2;
-        }
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('D', 'X', 'T', '3'))
-        {
-           return WINED3DFMT_DXT3;
-        }
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('D', 'X', 'T', '4'))
-        {
-            return WINED3DFMT_DXT4;
-        }
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('D', 'X', 'T', '5'))
-        {
-           return WINED3DFMT_DXT5;
-        }
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('G', 'R', 'G', 'B'))
-        {
-            return WINED3DFMT_G8R8_G8B8;
-        }
-        if(DDPixelFormat->dwFourCC == MAKEFOURCC('R', 'G', 'B', 'G'))
-        {
-            return WINED3DFMT_R8G8_B8G8;
-        }
-        return WINED3DFMT_UNKNOWN;  /* Abuse this as an error value */
+        return DDPixelFormat->dwFourCC;
     }
     else if(DDPixelFormat->dwFlags & DDPF_BUMPDUDV)
     {
@@ -623,6 +589,13 @@ PixelFormat_DD2WineD3D(const DDPIXELFORMAT *DDPixelFormat)
         {
             return WINED3DFMT_R8G8_SNORM;
         }
+        else if ( (DDPixelFormat->u1.dwBumpBitCount         == 32        ) &&
+                  (DDPixelFormat->u2.dwBumpDuBitMask        == 0x0000ffff) &&
+                  (DDPixelFormat->u3.dwBumpDvBitMask        == 0xffff0000) &&
+                  (DDPixelFormat->u4.dwBumpLuminanceBitMask == 0x00000000) )
+        {
+            return WINED3DFMT_R16G16_SNORM;
+        }
         else if ( (DDPixelFormat->u1.dwBumpBitCount         == 16        ) &&
                   (DDPixelFormat->u2.dwBumpDuBitMask        == 0x0000001f) &&
                   (DDPixelFormat->u3.dwBumpDvBitMask        == 0x000003e0) &&
@@ -668,7 +641,7 @@ DDRAW_dump_DDCOLORKEY(const DDCOLORKEY *ddck)
 static void DDRAW_dump_flags_nolf(DWORD flags, const flag_info* names,
                                   size_t num_names)
 {
-    unsigned int       i;
+    unsigned int i;
 
     for (i=0; i < num_names; i++)
         if ((flags & names[i].val) ||      /* standard flag value */
index f16cf12..36087f2 100644 (file)
 
 #include "config.h"
 #include "wine/port.h"
-#include "wine/debug.h"
-
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
 
 #include "ddraw_private.h"
 
-WINE_DEFAULT_DEBUG_CHANNEL(d3d7);
-WINE_DECLARE_DEBUG_CHANNEL(ddraw_thunk);
+WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
 /*****************************************************************************
  * IUnknown Methods
@@ -69,7 +51,8 @@ IDirect3DVertexBufferImpl_QueryInterface(IDirect3DVertexBuffer7 *iface,
                                          void  **obj)
 {
     IDirect3DVertexBufferImpl *This = (IDirect3DVertexBufferImpl *)iface;
-    TRACE("(%p)->(%s,%p)\n", This, debugstr_guid(riid), obj);
+
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obj);
 
     /* By default, set the object pointer to NULL */
     *obj = NULL;
@@ -104,10 +87,9 @@ Thunk_IDirect3DVertexBufferImpl_1_QueryInterface(IDirect3DVertexBuffer *iface,
                                                  REFIID riid,
                                                  void **obj)
 {
-    IDirect3DVertexBufferImpl *This = vb_from_vb1(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%s,%p) thunking to IDirect3DVertexBuffer7 interface.\n", This, debugstr_guid(riid), obj);
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), obj);
 
-    return IDirect3DVertexBuffer7_QueryInterface((IDirect3DVertexBuffer7 *)This, riid, obj);
+    return IDirect3DVertexBuffer7_QueryInterface((IDirect3DVertexBuffer7 *)vb_from_vb1(iface), riid, obj);
 }
 
 /*****************************************************************************
@@ -125,7 +107,7 @@ IDirect3DVertexBufferImpl_AddRef(IDirect3DVertexBuffer7 *iface)
     IDirect3DVertexBufferImpl *This = (IDirect3DVertexBufferImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    TRACE("(%p/%p)->() incrementing from %u.\n", This, iface, ref - 1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -133,10 +115,9 @@ IDirect3DVertexBufferImpl_AddRef(IDirect3DVertexBuffer7 *iface)
 static ULONG WINAPI
 Thunk_IDirect3DVertexBufferImpl_1_AddRef(IDirect3DVertexBuffer *iface)
 {
-    IDirect3DVertexBufferImpl *This = vb_from_vb1(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DVertexBuffer7 interface.\n", This);
+    TRACE("iface %p.\n", iface);
 
-    return IDirect3DVertexBuffer7_AddRef((IDirect3DVertexBuffer7 *)This);
+    return IDirect3DVertexBuffer7_AddRef((IDirect3DVertexBuffer7 *)vb_from_vb1(iface));
 }
 
 
@@ -155,7 +136,7 @@ IDirect3DVertexBufferImpl_Release(IDirect3DVertexBuffer7 *iface)
     IDirect3DVertexBufferImpl *This = (IDirect3DVertexBufferImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
 
-    TRACE("(%p)->() decrementing from %u.\n", This, ref + 1);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (ref == 0)
     {
@@ -198,10 +179,9 @@ IDirect3DVertexBufferImpl_Release(IDirect3DVertexBuffer7 *iface)
 static ULONG WINAPI
 Thunk_IDirect3DVertexBufferImpl_1_Release(IDirect3DVertexBuffer *iface)
 {
-    IDirect3DVertexBufferImpl *This = vb_from_vb1(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DVertexBuffer7 interface.\n", This);
+    TRACE("iface %p.\n", iface);
 
-    return IDirect3DVertexBuffer7_Release((IDirect3DVertexBuffer7 *)This);
+    return IDirect3DVertexBuffer7_Release((IDirect3DVertexBuffer7 *)vb_from_vb1(iface));
 }
 
 /*****************************************************************************
@@ -237,7 +217,8 @@ IDirect3DVertexBufferImpl_Lock(IDirect3DVertexBuffer7 *iface,
     WINED3DBUFFER_DESC Desc;
     HRESULT hr;
     DWORD wined3d_flags = 0;
-    TRACE("(%p)->(%08x,%p,%p)\n", This, Flags, Data, Size);
+
+    TRACE("iface %p, flags %#x, data %p, data_size %p.\n", iface, Flags, Data, Size);
 
     /* Writeonly: Pointless. Event: Unsupported by native according to the sdk
      * nosyslock: Not applicable
@@ -251,13 +232,7 @@ IDirect3DVertexBufferImpl_Lock(IDirect3DVertexBuffer7 *iface,
     if(Size)
     {
         /* Get the size, for returning it, and for locking */
-        hr = IWineD3DBuffer_GetDesc(This->wineD3DVertexBuffer, &Desc);
-        if(hr != D3D_OK)
-        {
-            ERR("(%p) IWineD3DBuffer::GetDesc failed with hr=%08x\n", This, hr);
-            LeaveCriticalSection(&ddraw_cs);
-            return hr;
-        }
+        IWineD3DBuffer_GetDesc(This->wineD3DVertexBuffer, &Desc);
         *Size = Desc.Size;
     }
 
@@ -273,10 +248,9 @@ Thunk_IDirect3DVertexBufferImpl_1_Lock(IDirect3DVertexBuffer *iface,
                                        void **Data,
                                        DWORD *Size)
 {
-    IDirect3DVertexBufferImpl *This = vb_from_vb1(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%p,%p) thunking to IDirect3DVertexBuffer7 interface.\n", This, Flags, Data, Size);
+    TRACE("iface %p, flags %#x, data %p, data_size %p.\n", iface, Flags, Data, Size);
 
-    return IDirect3DVertexBuffer7_Lock((IDirect3DVertexBuffer7 *)This, Flags, Data, Size);
+    return IDirect3DVertexBuffer7_Lock((IDirect3DVertexBuffer7 *)vb_from_vb1(iface), Flags, Data, Size);
 }
 
 /*****************************************************************************
@@ -293,7 +267,8 @@ IDirect3DVertexBufferImpl_Unlock(IDirect3DVertexBuffer7 *iface)
 {
     IDirect3DVertexBufferImpl *This = (IDirect3DVertexBufferImpl *)iface;
     HRESULT hr;
-    TRACE("(%p)->()\n", This);
+
+    TRACE("iface %p.\n", iface);
 
     EnterCriticalSection(&ddraw_cs);
     hr = IWineD3DBuffer_Unmap(This->wineD3DVertexBuffer);
@@ -305,10 +280,9 @@ IDirect3DVertexBufferImpl_Unlock(IDirect3DVertexBuffer7 *iface)
 static HRESULT WINAPI
 Thunk_IDirect3DVertexBufferImpl_1_Unlock(IDirect3DVertexBuffer *iface)
 {
-    IDirect3DVertexBufferImpl *This = vb_from_vb1(iface);
-    TRACE_(ddraw_thunk)("(%p)->() thunking to IDirect3DVertexBuffer7 interface.\n", This);
+    TRACE("iface %p.\n", iface);
 
-    return IDirect3DVertexBuffer7_Unlock((IDirect3DVertexBuffer7 *)This);
+    return IDirect3DVertexBuffer7_Unlock((IDirect3DVertexBuffer7 *)vb_from_vb1(iface));
 }
 
 
@@ -350,7 +324,8 @@ IDirect3DVertexBufferImpl_ProcessVertices(IDirect3DVertexBuffer7 *iface,
     BOOL oldClip, doClip;
     HRESULT hr;
 
-    TRACE("(%p)->(%08x,%d,%d,%p,%d,%p,%08x)\n", This, VertexOp, DestIndex, Count, Src, SrcIndex, D3D, Flags);
+    TRACE("iface %p, vertex_op %#x, dst_idx %u, count %u, src_buffer %p, src_idx %u, device %p, flags %#x.\n",
+            iface, VertexOp, DestIndex, Count, SrcBuffer, SrcIndex, D3DDevice, Flags);
 
     /* Vertex operations:
      * D3DVOP_CLIP: Clips vertices outside the viewing frustrum. Needs clipping information
@@ -415,14 +390,14 @@ Thunk_IDirect3DVertexBufferImpl_1_ProcessVertices(IDirect3DVertexBuffer *iface,
                                                   IDirect3DDevice3 *D3DDevice,
                                                   DWORD Flags)
 {
-    IDirect3DVertexBufferImpl *This = vb_from_vb1(iface);
     IDirect3DVertexBufferImpl *Src = SrcBuffer ? vb_from_vb1(SrcBuffer) : NULL;
     IDirect3DDeviceImpl *D3D = D3DDevice ? device_from_device3(D3DDevice) : NULL;
 
-    TRACE_(ddraw_thunk)("(%p)->(%08x,%08x,%08x,%p,%08x,%p,%08x) thunking to IDirect3DVertexBuffer7 interface.\n", This, VertexOp, DestIndex, Count, Src, SrcIndex, D3D, Flags);
+    TRACE("iface %p, vertex_op %#x, dst_idx %u, count %u, src_buffer %p, src_idx %u, device %p, flags %#x.\n",
+            iface, VertexOp, DestIndex, Count, SrcBuffer, SrcIndex, D3DDevice, Flags);
 
-    return IDirect3DVertexBuffer7_ProcessVertices((IDirect3DVertexBuffer7 *)This, VertexOp, DestIndex,
-            Count, (IDirect3DVertexBuffer7 *)Src, SrcIndex, (IDirect3DDevice7 *)D3D, Flags);
+    return IDirect3DVertexBuffer7_ProcessVertices((IDirect3DVertexBuffer7 *)vb_from_vb1(iface), VertexOp,
+            DestIndex, Count, (IDirect3DVertexBuffer7 *)Src, SrcIndex, (IDirect3DDevice7 *)D3D, Flags);
 }
 
 /*****************************************************************************
@@ -444,25 +419,19 @@ IDirect3DVertexBufferImpl_GetVertexBufferDesc(IDirect3DVertexBuffer7 *iface,
 {
     IDirect3DVertexBufferImpl *This = (IDirect3DVertexBufferImpl *)iface;
     WINED3DBUFFER_DESC WDesc;
-    HRESULT hr;
-    TRACE("(%p)->(%p)\n", This, Desc);
+
+    TRACE("iface %p, desc %p.\n", iface, Desc);
 
     if(!Desc) return DDERR_INVALIDPARAMS;
 
     EnterCriticalSection(&ddraw_cs);
-    hr = IWineD3DBuffer_GetDesc(This->wineD3DVertexBuffer, &WDesc);
-    if(hr != D3D_OK)
-    {
-        ERR("(%p) IWineD3DBuffer::GetDesc failed with hr=%08x\n", This, hr);
-        LeaveCriticalSection(&ddraw_cs);
-        return hr;
-    }
+    IWineD3DBuffer_GetDesc(This->wineD3DVertexBuffer, &WDesc);
+    LeaveCriticalSection(&ddraw_cs);
 
     /* Now fill the Desc structure */
     Desc->dwCaps = This->Caps;
     Desc->dwFVF = This->fvf;
     Desc->dwNumVertices = WDesc.Size / get_flexible_vertex_size(This->fvf);
-    LeaveCriticalSection(&ddraw_cs);
 
     return D3D_OK;
 }
@@ -471,10 +440,9 @@ static HRESULT WINAPI
 Thunk_IDirect3DVertexBufferImpl_1_GetVertexBufferDesc(IDirect3DVertexBuffer *iface,
                                                       D3DVERTEXBUFFERDESC *Desc)
 {
-    IDirect3DVertexBufferImpl *This = vb_from_vb1(iface);
-    TRACE_(ddraw_thunk)("(%p)->(%p) thunking to IDirect3DVertexBuffer7 interface.\n", This, Desc);
+    TRACE("iface %p, desc %p.\n", iface, Desc);
 
-    return IDirect3DVertexBuffer7_GetVertexBufferDesc((IDirect3DVertexBuffer7 *)This, Desc);
+    return IDirect3DVertexBuffer7_GetVertexBufferDesc((IDirect3DVertexBuffer7 *)vb_from_vb1(iface), Desc);
 }
 
 
@@ -497,12 +465,13 @@ IDirect3DVertexBufferImpl_Optimize(IDirect3DVertexBuffer7 *iface,
                                    DWORD Flags)
 {
     IDirect3DVertexBufferImpl *This = (IDirect3DVertexBufferImpl *)iface;
-    IDirect3DDeviceImpl *D3D = (IDirect3DDeviceImpl *)D3DDevice;
     static BOOL hide = FALSE;
 
+    TRACE("iface %p, device %p, flags %#x.\n", iface, D3DDevice, Flags);
+
     if (!hide)
     {
-        FIXME("(%p)->(%p,%08x): stub!\n", This, D3D, Flags);
+        FIXME("iface %p, device %p, flags %#x stub!\n", iface, D3DDevice, Flags);
         hide = TRUE;
     }
 
@@ -521,11 +490,12 @@ Thunk_IDirect3DVertexBufferImpl_1_Optimize(IDirect3DVertexBuffer *iface,
                                            IDirect3DDevice3 *D3DDevice,
                                            DWORD Flags)
 {
-    IDirect3DVertexBufferImpl *This = vb_from_vb1(iface);
     IDirect3DDeviceImpl *D3D = D3DDevice ? device_from_device3(D3DDevice) : NULL;
-    TRACE_(ddraw_thunk)("(%p)->(%p,%08x) thunking to IDirect3DVertexBuffer7 interface.\n", This, D3D, Flags);
 
-    return IDirect3DVertexBuffer7_Optimize((IDirect3DVertexBuffer7 *)This, (IDirect3DDevice7 *)D3D, Flags);
+    TRACE("iface %p, device %p, flags %#x.\n", iface, D3DDevice, Flags);
+
+    return IDirect3DVertexBuffer7_Optimize((IDirect3DVertexBuffer7 *)vb_from_vb1(iface),
+            (IDirect3DDevice7 *)D3D, Flags);
 }
 
 /*****************************************************************************
@@ -560,9 +530,9 @@ IDirect3DVertexBufferImpl_ProcessVerticesStrided(IDirect3DVertexBuffer7 *iface,
                                                  IDirect3DDevice7 *D3DDevice,
                                                  DWORD Flags)
 {
-    IDirect3DVertexBufferImpl *This = (IDirect3DVertexBufferImpl *)iface;
-    IDirect3DDeviceImpl *D3D = (IDirect3DDeviceImpl *)D3DDevice;
-    FIXME("(%p)->(%08x,%08x,%08x,%p,%08x,%p,%08x): stub!\n", This, VertexOp, DestIndex, Count, StrideData, VertexTypeDesc, D3D, Flags);
+    FIXME("iface %p, vertex_op %#x, dst_idx %u, count %u, data %p, vertex_type %#x, device %p, flags %#x stub!\n",
+            iface, VertexOp, DestIndex, Count, StrideData, VertexTypeDesc, D3DDevice, Flags);
+
     return DD_OK;
 }
 
@@ -570,7 +540,7 @@ IDirect3DVertexBufferImpl_ProcessVerticesStrided(IDirect3DVertexBuffer7 *iface,
  * The VTables
  *****************************************************************************/
 
-const IDirect3DVertexBuffer7Vtbl IDirect3DVertexBuffer7_Vtbl =
+static const struct IDirect3DVertexBuffer7Vtbl d3d_vertex_buffer7_vtbl =
 {
     /*** IUnknown Methods ***/
     IDirect3DVertexBufferImpl_QueryInterface,
@@ -586,7 +556,7 @@ const IDirect3DVertexBuffer7Vtbl IDirect3DVertexBuffer7_Vtbl =
     IDirect3DVertexBufferImpl_ProcessVerticesStrided
 };
 
-const IDirect3DVertexBufferVtbl IDirect3DVertexBuffer1_Vtbl =
+static const struct IDirect3DVertexBufferVtbl d3d_vertex_buffer1_vtbl =
 {
     /*** IUnknown Methods ***/
     Thunk_IDirect3DVertexBufferImpl_1_QueryInterface,
@@ -599,3 +569,53 @@ const IDirect3DVertexBufferVtbl IDirect3DVertexBuffer1_Vtbl =
     Thunk_IDirect3DVertexBufferImpl_1_GetVertexBufferDesc,
     Thunk_IDirect3DVertexBufferImpl_1_Optimize
 };
+
+HRESULT d3d_vertex_buffer_init(IDirect3DVertexBufferImpl *buffer,
+        IDirectDrawImpl *ddraw, D3DVERTEXBUFFERDESC *desc)
+{
+    DWORD usage;
+    HRESULT hr;
+
+    buffer->lpVtbl = &d3d_vertex_buffer7_vtbl;
+    buffer->IDirect3DVertexBuffer_vtbl = &d3d_vertex_buffer1_vtbl;
+    buffer->ref = 1;
+
+    buffer->ddraw = ddraw;
+    buffer->Caps = desc->dwCaps;
+    buffer->fvf = desc->dwFVF;
+
+    usage = desc->dwCaps & D3DVBCAPS_WRITEONLY ? WINED3DUSAGE_WRITEONLY : 0;
+    usage |= WINED3DUSAGE_STATICDECL;
+
+    EnterCriticalSection(&ddraw_cs);
+
+    hr = IWineD3DDevice_CreateVertexBuffer(ddraw->wineD3DDevice,
+            get_flexible_vertex_size(desc->dwFVF) * desc->dwNumVertices,
+            usage, desc->dwCaps & D3DVBCAPS_SYSTEMMEMORY ? WINED3DPOOL_SYSTEMMEM : WINED3DPOOL_DEFAULT,
+            buffer, &ddraw_null_wined3d_parent_ops, &buffer->wineD3DVertexBuffer);
+    if (FAILED(hr))
+    {
+        WARN("Failed to create wined3d vertex buffer, hr %#x.\n", hr);
+        LeaveCriticalSection(&ddraw_cs);
+
+        if (hr == WINED3DERR_INVALIDCALL)
+            return DDERR_INVALIDPARAMS;
+        else
+            return hr;
+    }
+
+    buffer->wineD3DVertexDeclaration = ddraw_find_decl(ddraw, desc->dwFVF);
+    if (!buffer->wineD3DVertexDeclaration)
+    {
+        ERR("Failed to find vertex declaration for fvf %#x.\n", desc->dwFVF);
+        IWineD3DBuffer_Release(buffer->wineD3DVertexBuffer);
+        LeaveCriticalSection(&ddraw_cs);
+
+        return DDERR_INVALIDPARAMS;
+    }
+    IWineD3DVertexDeclaration_AddRef(buffer->wineD3DVertexDeclaration);
+
+    LeaveCriticalSection(&ddraw_cs);
+
+    return D3D_OK;
+}
index b637df1..6e0725e 100644 (file)
 #include "config.h"
 #include "wine/port.h"
 
-#include <assert.h>
-#include <stdarg.h>
-#include <string.h>
-#include <stdlib.h>
-
-#define COBJMACROS
-#define NONAMELESSUNION
-
-#include "windef.h"
-#include "winbase.h"
-#include "winerror.h"
-#include "wingdi.h"
-#include "wine/exception.h"
-
-#include "ddraw.h"
-#include "d3d.h"
-
 #include "ddraw_private.h"
-#include "wine/debug.h"
 
-WINE_DEFAULT_DEBUG_CHANNEL(d3d7);
+WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
 
 /*****************************************************************************
  * Helper functions
@@ -62,27 +44,31 @@ void viewport_activate(IDirect3DViewportImpl* This, BOOL ignore_lights) {
         /* Activate all the lights associated with this context */
         light = This->lights;
 
-        while (light != NULL) {
-            light->activate(light);
+        while (light)
+        {
+            light_activate(light);
             light = light->next;
         }
     }
 
     /* And copy the values in the structure used by the device */
-    if (This->use_vp2) {
+    if (This->use_vp2)
+    {
         vp.dwX = This->viewports.vp2.dwX;
-       vp.dwY = This->viewports.vp2.dwY;
-       vp.dwHeight = This->viewports.vp2.dwHeight;
-       vp.dwWidth = This->viewports.vp2.dwWidth;
-       vp.dvMinZ = This->viewports.vp2.dvMinZ;
-       vp.dvMaxZ = This->viewports.vp2.dvMaxZ;
-    } else {
+        vp.dwY = This->viewports.vp2.dwY;
+        vp.dwHeight = This->viewports.vp2.dwHeight;
+        vp.dwWidth = This->viewports.vp2.dwWidth;
+        vp.dvMinZ = This->viewports.vp2.dvMinZ;
+        vp.dvMaxZ = This->viewports.vp2.dvMaxZ;
+    }
+    else
+    {
         vp.dwX = This->viewports.vp1.dwX;
-       vp.dwY = This->viewports.vp1.dwY;
-       vp.dwHeight = This->viewports.vp1.dwHeight;
-       vp.dwWidth = This->viewports.vp1.dwWidth;
-       vp.dvMinZ = This->viewports.vp1.dvMinZ;
-       vp.dvMaxZ = This->viewports.vp1.dvMaxZ;
+        vp.dwY = This->viewports.vp1.dwY;
+        vp.dwHeight = This->viewports.vp1.dwHeight;
+        vp.dwWidth = This->viewports.vp1.dwWidth;
+        vp.dvMinZ = This->viewports.vp1.dvMinZ;
+        vp.dvMaxZ = This->viewports.vp1.dvMaxZ;
     }
 
     /* And also set the viewport */
@@ -98,29 +84,29 @@ void viewport_activate(IDirect3DViewportImpl* This, BOOL ignore_lights) {
 static void _dump_D3DVIEWPORT(const D3DVIEWPORT *lpvp)
 {
     TRACE("    - dwSize = %d   dwX = %d   dwY = %d\n",
-         lpvp->dwSize, lpvp->dwX, lpvp->dwY);
+            lpvp->dwSize, lpvp->dwX, lpvp->dwY);
     TRACE("    - dwWidth = %d   dwHeight = %d\n",
-         lpvp->dwWidth, lpvp->dwHeight);
+            lpvp->dwWidth, lpvp->dwHeight);
     TRACE("    - dvScaleX = %f   dvScaleY = %f\n",
-         lpvp->dvScaleX, lpvp->dvScaleY);
+            lpvp->dvScaleX, lpvp->dvScaleY);
     TRACE("    - dvMaxX = %f   dvMaxY = %f\n",
-         lpvp->dvMaxX, lpvp->dvMaxY);
+            lpvp->dvMaxX, lpvp->dvMaxY);
     TRACE("    - dvMinZ = %f   dvMaxZ = %f\n",
-         lpvp->dvMinZ, lpvp->dvMaxZ);
+            lpvp->dvMinZ, lpvp->dvMaxZ);
 }
 
 static void _dump_D3DVIEWPORT2(const D3DVIEWPORT2 *lpvp)
 {
     TRACE("    - dwSize = %d   dwX = %d   dwY = %d\n",
-         lpvp->dwSize, lpvp->dwX, lpvp->dwY);
+            lpvp->dwSize, lpvp->dwX, lpvp->dwY);
     TRACE("    - dwWidth = %d   dwHeight = %d\n",
-         lpvp->dwWidth, lpvp->dwHeight);
+            lpvp->dwWidth, lpvp->dwHeight);
     TRACE("    - dvClipX = %f   dvClipY = %f\n",
-         lpvp->dvClipX, lpvp->dvClipY);
+            lpvp->dvClipX, lpvp->dvClipY);
     TRACE("    - dvClipWidth = %f   dvClipHeight = %f\n",
-         lpvp->dvClipWidth, lpvp->dvClipHeight);
+            lpvp->dvClipWidth, lpvp->dvClipHeight);
     TRACE("    - dvMinZ = %f   dvMaxZ = %f\n",
-         lpvp->dvMinZ, lpvp->dvMaxZ);
+            lpvp->dvMinZ, lpvp->dvMaxZ);
 }
 
 /*****************************************************************************
@@ -143,25 +129,23 @@ static void _dump_D3DVIEWPORT2(const D3DVIEWPORT2 *lpvp)
  *  E_NOINTERFACE if the requested interface wasn't found
  *
  *****************************************************************************/
-static HRESULT WINAPI
-IDirect3DViewportImpl_QueryInterface(IDirect3DViewport3 *iface,
-                                     REFIID riid,
-                                     void **obp)
+static HRESULT WINAPI IDirect3DViewportImpl_QueryInterface(IDirect3DViewport3 *iface, REFIID riid, void **object)
 {
-    TRACE("(%p)->(%s,%p)\n", iface, debugstr_guid(riid), obp);
-
-    *obp = NULL;
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
 
-    if ( IsEqualGUID(&IID_IUnknown,  riid) ||
-        IsEqualGUID(&IID_IDirect3DViewport, riid) ||
-        IsEqualGUID(&IID_IDirect3DViewport2, riid) ||
-        IsEqualGUID(&IID_IDirect3DViewport3, riid) ) {
+    if (IsEqualGUID(&IID_IDirect3DViewport3, riid)
+            || IsEqualGUID(&IID_IDirect3DViewport2, riid)
+            || IsEqualGUID(&IID_IDirect3DViewport, riid)
+            || IsEqualGUID(&IID_IUnknown, riid))
+    {
         IDirect3DViewport3_AddRef(iface);
-        *obp = iface;
-       TRACE("  Creating IDirect3DViewport1/2/3 interface %p\n", *obp);
-       return S_OK;
+        *object = iface;
+        return S_OK;
     }
-    FIXME("(%p): interface for IID %s NOT found!\n", iface, debugstr_guid(riid));
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
     return E_NOINTERFACE;
 }
 
@@ -180,7 +164,7 @@ IDirect3DViewportImpl_AddRef(IDirect3DViewport3 *iface)
     IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
     ULONG ref = InterlockedIncrement(&This->ref);
 
-    TRACE("(%p)->() incrementing from %u.\n", This, ref - 1);
+    TRACE("%p increasing refcount to %u.\n", This, ref);
 
     return ref;
 }
@@ -200,11 +184,11 @@ IDirect3DViewportImpl_Release(IDirect3DViewport3 *iface)
     IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
     ULONG ref = InterlockedDecrement(&This->ref);
 
-    TRACE("(%p)->() decrementing from %u.\n", This, ref + 1);
+    TRACE("%p decreasing refcount to %u.\n", This, ref);
 
     if (!ref) {
         HeapFree(GetProcessHeap(), 0, This);
-       return 0;
+        return 0;
     }
     return ref;
 }
@@ -229,7 +213,8 @@ static HRESULT WINAPI
 IDirect3DViewportImpl_Initialize(IDirect3DViewport3 *iface,
                                  IDirect3D *Direct3D)
 {
-    TRACE("(%p)->(%p) no-op...\n", iface, Direct3D);
+    TRACE("iface %p, d3d %p.\n", iface, Direct3D);
+
     return DDERR_ALREADYINITIALIZED;
 }
 
@@ -252,7 +237,8 @@ IDirect3DViewportImpl_GetViewport(IDirect3DViewport3 *iface,
 {
     IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
     DWORD dwSize;
-    TRACE("(%p/%p)->(%p)\n", This, iface, lpData);
+
+    TRACE("iface %p, data %p.\n", iface, lpData);
 
     EnterCriticalSection(&ddraw_cs);
     dwSize = lpData->dwSize;
@@ -275,9 +261,10 @@ IDirect3DViewportImpl_GetViewport(IDirect3DViewport3 *iface,
         memcpy(lpData, &vp1, dwSize);
     }
 
-    if (TRACE_ON(d3d7)) {
+    if (TRACE_ON(ddraw))
+    {
         TRACE("  returning D3DVIEWPORT :\n");
-       _dump_D3DVIEWPORT(lpData);
+        _dump_D3DVIEWPORT(lpData);
     }
     LeaveCriticalSection(&ddraw_cs);
 
@@ -303,11 +290,13 @@ IDirect3DViewportImpl_SetViewport(IDirect3DViewport3 *iface,
 {
     IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
     LPDIRECT3DVIEWPORT3 current_viewport;
-    TRACE("(%p/%p)->(%p)\n", This, iface, lpData);
 
-    if (TRACE_ON(d3d7)) {
+    TRACE("iface %p, data %p.\n", iface, lpData);
+
+    if (TRACE_ON(ddraw))
+    {
         TRACE("  getting D3DVIEWPORT :\n");
-       _dump_D3DVIEWPORT(lpData);
+        _dump_D3DVIEWPORT(lpData);
     }
 
     EnterCriticalSection(&ddraw_cs);
@@ -324,8 +313,9 @@ IDirect3DViewportImpl_SetViewport(IDirect3DViewport3 *iface,
     if (This->active_device) {
         IDirect3DDevice3 *d3d_device3 = (IDirect3DDevice3 *)&This->active_device->IDirect3DDevice3_vtbl;
         IDirect3DDevice3_GetCurrentViewport(d3d_device3, &current_viewport);
-        if (current_viewport) {
-            if ((IDirect3DViewportImpl *)current_viewport == This) This->activate(This, FALSE);
+        if (current_viewport)
+        {
+            if ((IDirect3DViewportImpl *)current_viewport == This) viewport_activate(This, FALSE);
             IDirect3DViewport3_Release(current_viewport);
         }
     }
@@ -376,7 +366,9 @@ IDirect3DViewportImpl_TransformVertices(IDirect3DViewport3 *iface,
     unsigned int i;
     D3DVIEWPORT vp = This->viewports.vp1;
     D3DHVERTEX *outH;
-    TRACE("(%p)->(%08x,%p,%08x,%p)\n", This, dwVertexCount, lpData, dwFlags, lpOffScreen);
+
+    TRACE("iface %p, vertex_count %u, vertex_data %p, flags %#x, clip_plane %p.\n",
+            iface, dwVertexCount, lpData, dwFlags, lpOffScreen);
 
     /* Tests on windows show that Windows crashes when this occurs,
      * so don't return the (intuitive) return value
@@ -507,8 +499,8 @@ IDirect3DViewportImpl_LightElements(IDirect3DViewport3 *iface,
                                     DWORD dwElementCount,
                                     LPD3DLIGHTDATA lpData)
 {
-    IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
-    TRACE("(%p)->(%08x,%p): Unimplemented!\n", This, dwElementCount, lpData);
+    TRACE("iface %p, element_count %u, data %p.\n", iface, dwElementCount, lpData);
+
     return DDERR_UNSUPPORTED;
 }
 
@@ -529,36 +521,32 @@ IDirect3DViewportImpl_SetBackground(IDirect3DViewport3 *iface,
                                     D3DMATERIALHANDLE hMat)
 {
     IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
-    TRACE("(%p)->(%d)\n", This, hMat);
+    IDirect3DMaterialImpl *m;
+
+    TRACE("iface %p, material %#x.\n", iface, hMat);
 
     EnterCriticalSection(&ddraw_cs);
-    if(hMat && hMat > This->ddraw->d3ddevice->numHandles)
+
+    if (!hMat)
     {
-        WARN("Specified Handle %d out of range\n", hMat);
+        This->background = NULL;
+        TRACE("Setting background to NULL\n");
         LeaveCriticalSection(&ddraw_cs);
-        return DDERR_INVALIDPARAMS;
+        return D3D_OK;
     }
-    else if(hMat && This->ddraw->d3ddevice->Handles[hMat - 1].type != DDrawHandle_Material)
+
+    m = ddraw_get_object(&This->ddraw->d3ddevice->handle_table, hMat - 1, DDRAW_HANDLE_MATERIAL);
+    if (!m)
     {
-        WARN("Handle %d is not a material handle\n", hMat);
+        WARN("Invalid material handle.\n");
         LeaveCriticalSection(&ddraw_cs);
         return DDERR_INVALIDPARAMS;
     }
 
-    if(hMat)
-    {
-        This->background = This->ddraw->d3ddevice->Handles[hMat - 1].ptr;
-        TRACE(" setting background color : %f %f %f %f\n",
-              This->background->mat.u.diffuse.u1.r,
-              This->background->mat.u.diffuse.u2.g,
-              This->background->mat.u.diffuse.u3.b,
-              This->background->mat.u.diffuse.u4.a);
-    }
-    else
-    {
-        This->background = NULL;
-        TRACE("Setting background to NULL\n");
-    }
+    TRACE("Setting background color : %.8e %.8e %.8e %.8e.\n",
+            m->mat.u.diffuse.u1.r, m->mat.u.diffuse.u2.g,
+            m->mat.u.diffuse.u3.b, m->mat.u.diffuse.u4.a);
+    This->background = m;
 
     LeaveCriticalSection(&ddraw_cs);
     return D3D_OK;
@@ -583,7 +571,8 @@ IDirect3DViewportImpl_GetBackground(IDirect3DViewport3 *iface,
                                     BOOL *lpValid)
 {
     IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
-    TRACE("(%p)->(%p,%p)\n", This, lphMat, lpValid);
+
+    TRACE("iface %p, material %p, valid %p.\n", iface, lphMat, lpValid);
 
     EnterCriticalSection(&ddraw_cs);
     if(lpValid)
@@ -622,8 +611,8 @@ static HRESULT WINAPI
 IDirect3DViewportImpl_SetBackgroundDepth(IDirect3DViewport3 *iface,
                                          IDirectDrawSurface *lpDDSurface)
 {
-    IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
-    FIXME("(%p)->(%p): stub!\n", This, lpDDSurface);
+    FIXME("iface %p, surface %p stub!\n", iface, lpDDSurface);
+
     return D3D_OK;
 }
 
@@ -646,8 +635,8 @@ IDirect3DViewportImpl_GetBackgroundDepth(IDirect3DViewport3 *iface,
                                          IDirectDrawSurface **lplpDDSurface,
                                          LPBOOL lpValid)
 {
-    IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
-    FIXME("(%p)->(%p,%p): stub!\n", This, lplpDDSurface, lpValid);
+    FIXME("iface %p, surface %p, valid %p stub!\n", iface, lplpDDSurface, lpValid);
+
     return DD_OK;
 }
 
@@ -677,10 +666,11 @@ static HRESULT WINAPI IDirect3DViewportImpl_Clear(IDirect3DViewport3 *iface,
     LPDIRECT3DVIEWPORT3 current_viewport;
     IDirect3DDevice3 *d3d_device3;
 
-    TRACE("(%p/%p)->(%08x,%p,%08x)\n", This, iface, dwCount, lpRects, dwFlags);
+    TRACE("iface %p, rect_count %u, rects %p, flags %#x.\n", iface, dwCount, lpRects, dwFlags);
+
     if (This->active_device == NULL) {
         ERR(" Trying to clear a viewport not attached to a device !\n");
-       return D3DERR_VIEWPORTHASNODEVICE;
+        return D3DERR_VIEWPORTHASNODEVICE;
     }
     d3d_device3 = (IDirect3DDevice3 *)&This->active_device->IDirect3DDevice3_vtbl;
 
@@ -700,7 +690,7 @@ static HRESULT WINAPI IDirect3DViewportImpl_Clear(IDirect3DViewport3 *iface,
 
     /* Need to temporarily activate viewport to clear it. Previously active one will be restored
         afterwards. */
-    This->activate(This, TRUE);
+    viewport_activate(This, TRUE);
 
     hr = IDirect3DDevice7_Clear((IDirect3DDevice7 *)This->active_device, dwCount, lpRects,
             dwFlags & (D3DCLEAR_ZBUFFER | D3DCLEAR_TARGET), color, 1.0, 0x00000000);
@@ -708,7 +698,7 @@ static HRESULT WINAPI IDirect3DViewportImpl_Clear(IDirect3DViewport3 *iface,
     IDirect3DDevice3_GetCurrentViewport(d3d_device3, &current_viewport);
     if(current_viewport) {
         IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)current_viewport;
-        vp->activate(vp, TRUE);
+        viewport_activate(vp, TRUE);
         IDirect3DViewport3_Release(current_viewport);
     }
 
@@ -739,7 +729,7 @@ IDirect3DViewportImpl_AddLight(IDirect3DViewport3 *iface,
     DWORD i = 0;
     DWORD map = This->map_lights;
 
-    TRACE("(%p)->(%p)\n", This, lpDirect3DLight);
+    TRACE("iface %p, light %p.\n", iface, lpDirect3DLight);
 
     EnterCriticalSection(&ddraw_cs);
     if (This->num_lights >= 8)
@@ -749,9 +739,10 @@ IDirect3DViewportImpl_AddLight(IDirect3DViewport3 *iface,
     }
 
     /* Find a light number and update both light and viewports objects accordingly */
-    while(map&1) {
-        map>>=1;
-       i++;
+    while (map & 1)
+    {
+        map >>= 1;
+        ++i;
     }
     lpDirect3DLightImpl->dwLightIndex = i;
     This->num_lights++;
@@ -766,9 +757,8 @@ IDirect3DViewportImpl_AddLight(IDirect3DViewport3 *iface,
     lpDirect3DLightImpl->active_viewport = This;
 
     /* If active, activate the light */
-    if (This->active_device != NULL) {
-        lpDirect3DLightImpl->activate(lpDirect3DLightImpl);
-    }
+    if (This->active_device)
+        light_activate(lpDirect3DLightImpl);
 
     LeaveCriticalSection(&ddraw_cs);
     return D3D_OK;
@@ -795,25 +785,26 @@ IDirect3DViewportImpl_DeleteLight(IDirect3DViewport3 *iface,
     IDirect3DLightImpl *lpDirect3DLightImpl = (IDirect3DLightImpl *)lpDirect3DLight;
     IDirect3DLightImpl *cur_light, *prev_light = NULL;
 
-    TRACE("(%p)->(%p)\n", This, lpDirect3DLight);
+    TRACE("iface %p, light %p.\n", iface, lpDirect3DLight);
 
     EnterCriticalSection(&ddraw_cs);
     cur_light = This->lights;
     while (cur_light != NULL) {
-        if (cur_light == lpDirect3DLightImpl) {
-           lpDirect3DLightImpl->desactivate(lpDirect3DLightImpl);
-           if (prev_light == NULL) This->lights = cur_light->next;
-           else prev_light->next = cur_light->next;
-           /* Detach the light to the viewport */
-           cur_light->active_viewport = NULL;
-           IDirect3DLight_Release( (IDirect3DLight *)cur_light );
-           This->num_lights--;
-           This->map_lights &= ~(1<<lpDirect3DLightImpl->dwLightIndex);
+        if (cur_light == lpDirect3DLightImpl)
+        {
+            light_deactivate(lpDirect3DLightImpl);
+            if (!prev_light) This->lights = cur_light->next;
+            else prev_light->next = cur_light->next;
+            /* Detach the light from the viewport. */
+            cur_light->active_viewport = NULL;
+            IDirect3DLight_Release((IDirect3DLight *)cur_light);
+            --This->num_lights;
+            This->map_lights &= ~(1 << lpDirect3DLightImpl->dwLightIndex);
             LeaveCriticalSection(&ddraw_cs);
             return D3D_OK;
-       }
-       prev_light = cur_light;
-       cur_light = cur_light->next;
+        }
+        prev_light = cur_light;
+        cur_light = cur_light->next;
     }
     LeaveCriticalSection(&ddraw_cs);
 
@@ -842,7 +833,8 @@ IDirect3DViewportImpl_NextLight(IDirect3DViewport3 *iface,
     IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
     IDirect3DLightImpl *cur_light, *prev_light = NULL;
 
-    TRACE("(%p)->(%p,%p,%08x)\n", This, lpDirect3DLight, lplpDirect3DLight, dwFlags);
+    TRACE("iface %p, light %p, next_light %p, flags %#x.\n",
+            iface, lpDirect3DLight, lplpDirect3DLight, dwFlags);
 
     if (!lplpDirect3DLight)
         return DDERR_INVALIDPARAMS;
@@ -916,7 +908,8 @@ IDirect3DViewportImpl_GetViewport2(IDirect3DViewport3 *iface,
 {
     IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
     DWORD dwSize;
-    TRACE("(%p)->(%p)\n", This, lpData);
+
+    TRACE("iface %p, data %p.\n", iface, lpData);
 
     EnterCriticalSection(&ddraw_cs);
     dwSize = lpData->dwSize;
@@ -939,9 +932,10 @@ IDirect3DViewportImpl_GetViewport2(IDirect3DViewport3 *iface,
         memcpy(lpData, &vp2, dwSize);
     }
 
-    if (TRACE_ON(d3d7)) {
+    if (TRACE_ON(ddraw))
+    {
         TRACE("  returning D3DVIEWPORT2 :\n");
-       _dump_D3DVIEWPORT2(lpData);
+        _dump_D3DVIEWPORT2(lpData);
     }
 
     LeaveCriticalSection(&ddraw_cs);
@@ -966,11 +960,13 @@ IDirect3DViewportImpl_SetViewport2(IDirect3DViewport3 *iface,
 {
     IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
     LPDIRECT3DVIEWPORT3 current_viewport;
-    TRACE("(%p/%p)->(%p)\n", This, iface, lpData);
 
-    if (TRACE_ON(d3d7)) {
+    TRACE("iface %p, data %p.\n", iface, lpData);
+
+    if (TRACE_ON(ddraw))
+    {
         TRACE("  getting D3DVIEWPORT2 :\n");
-       _dump_D3DVIEWPORT2(lpData);
+        _dump_D3DVIEWPORT2(lpData);
     }
 
     EnterCriticalSection(&ddraw_cs);
@@ -981,8 +977,9 @@ IDirect3DViewportImpl_SetViewport2(IDirect3DViewport3 *iface,
     if (This->active_device) {
         IDirect3DDevice3 *d3d_device3 = (IDirect3DDevice3 *)&This->active_device->IDirect3DDevice3_vtbl;
         IDirect3DDevice3_GetCurrentViewport(d3d_device3, &current_viewport);
-        if (current_viewport) {
-            if ((IDirect3DViewportImpl *)current_viewport == This) This->activate(This, FALSE);
+        if (current_viewport)
+        {
+            if ((IDirect3DViewportImpl *)current_viewport == This) viewport_activate(This, FALSE);
             IDirect3DViewport3_Release(current_viewport);
         }
     }
@@ -1011,8 +1008,8 @@ static HRESULT WINAPI
 IDirect3DViewportImpl_SetBackgroundDepth2(IDirect3DViewport3 *iface,
                                           IDirectDrawSurface4 *lpDDS)
 {
-    IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
-    FIXME("(%p)->(%p): stub!\n", This, lpDDS);
+    FIXME("iface %p, surface %p stub!\n", iface, lpDDS);
+
     return D3D_OK;
 }
 
@@ -1034,8 +1031,8 @@ IDirect3DViewportImpl_GetBackgroundDepth2(IDirect3DViewport3 *iface,
                                           IDirectDrawSurface4 **lplpDDS,
                                           BOOL *lpValid)
 {
-    IDirect3DViewportImpl *This = (IDirect3DViewportImpl *)iface;
-    FIXME("(%p/%p)->(%p,%p): stub!\n", This, iface, lplpDDS, lpValid);
+    FIXME("iface %p, surface %p, valid %p stub!\n", iface, lplpDDS, lpValid);
+
     return D3D_OK;
 }
 
@@ -1068,7 +1065,9 @@ IDirect3DViewportImpl_Clear2(IDirect3DViewport3 *iface,
     HRESULT hr;
     LPDIRECT3DVIEWPORT3 current_viewport;
     IDirect3DDevice3 *d3d_device3;
-    TRACE("(%p)->(%08x,%p,%08x,%08x,%f,%08x)\n", This, dwCount, lpRects, dwFlags, dwColor, dvZ, dwStencil);
+
+    TRACE("iface %p, rect_count %u, rects %p, flags %#x, color 0x%08x, depth %.8e, stencil %u.\n",
+            iface, dwCount, lpRects, dwFlags, dwColor, dvZ, dwStencil);
 
     EnterCriticalSection(&ddraw_cs);
     if (This->active_device == NULL) {
@@ -1077,16 +1076,16 @@ IDirect3DViewportImpl_Clear2(IDirect3DViewport3 *iface,
         return D3DERR_VIEWPORTHASNODEVICE;
     }
     d3d_device3 = (IDirect3DDevice3 *)&This->active_device->IDirect3DDevice3_vtbl;
-    /* Need to temporarily activate viewport to clear it. Previously active one will be restored
-        afterwards. */
-    This->activate(This, TRUE);
+    /* Need to temporarily activate viewport to clear it. Previously active
+     * one will be restored afterwards. */
+    viewport_activate(This, TRUE);
 
     hr = IDirect3DDevice7_Clear((IDirect3DDevice7 *)This->active_device,
             dwCount, lpRects, dwFlags, dwColor, dvZ, dwStencil);
     IDirect3DDevice3_GetCurrentViewport(d3d_device3, &current_viewport);
     if(current_viewport) {
         IDirect3DViewportImpl *vp = (IDirect3DViewportImpl *)current_viewport;
-        vp->activate(vp, TRUE);
+        viewport_activate(vp, TRUE);
         IDirect3DViewport3_Release(current_viewport);
     }
     LeaveCriticalSection(&ddraw_cs);
@@ -1097,7 +1096,7 @@ IDirect3DViewportImpl_Clear2(IDirect3DViewport3 *iface,
  * The VTable
  *****************************************************************************/
 
-const IDirect3DViewport3Vtbl IDirect3DViewport3_Vtbl =
+static const struct IDirect3DViewport3Vtbl d3d_viewport_vtbl =
 {
     /*** IUnknown Methods ***/
     IDirect3DViewportImpl_QueryInterface,
@@ -1125,3 +1124,11 @@ const IDirect3DViewport3Vtbl IDirect3DViewport3_Vtbl =
     IDirect3DViewportImpl_GetBackgroundDepth2,
     IDirect3DViewportImpl_Clear2,
 };
+
+void d3d_viewport_init(IDirect3DViewportImpl *viewport, IDirectDrawImpl *ddraw)
+{
+    viewport->lpVtbl = &d3d_viewport_vtbl;
+    viewport->ref = 1;
+    viewport->ddraw = ddraw;
+    viewport->use_vp2 = 0xff;
+}
index 0824fed..c053e7f 100644 (file)
@@ -175,9 +175,9 @@ static const char *arb_get_helper_value(enum wined3d_shader_type shader, enum ar
     }
 }
 
-static inline BOOL ffp_clip_emul(IWineD3DStateBlockImpl *stateblock)
+static inline BOOL ffp_clip_emul(const struct wined3d_state *state)
 {
-    return stateblock->lowest_disabled_stage < 7;
+    return state->lowest_disabled_stage < 7;
 }
 
 /* ARB_program_shader private data */
@@ -248,8 +248,8 @@ struct arb_vs_compile_args
         struct
         {
             WORD                    bools;
-            char                    clip_texcoord;
-            char                    clipplane_mask;
+            unsigned char           clip_texcoord;
+            unsigned char           clipplane_mask;
         }                           boolclip;
         DWORD                       boolclip_compare;
     } clip;
@@ -503,8 +503,8 @@ static void shader_arb_load_np2fixup_constants(
 
         for (i = 0; active; active >>= 1, ++i) {
             const unsigned char idx = fixup->super.idx[i];
-            const IWineD3DTextureImpl* const tex = (const IWineD3DTextureImpl*) stateBlock->textures[i];
-            GLfloattex_dim = &np2fixup_constants[(idx >> 1) * 4];
+            const IWineD3DBaseTextureImpl *tex = stateBlock->state.textures[i];
+            GLfloat *tex_dim = &np2fixup_constants[(idx >> 1) * 4];
 
             if (!(active & 1)) continue;
 
@@ -542,8 +542,9 @@ static inline void shader_arb_ps_local_constants(IWineD3DDeviceImpl* deviceImpl)
         int texunit = gl_shader->bumpenvmatconst[i].texunit;
 
         /* The state manager takes care that this function is always called if the bump env matrix changes */
-        const float *data = (const float *)&stateBlock->textureState[texunit][WINED3DTSS_BUMPENVMAT00];
-        GL_EXTCALL(glProgramLocalParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB, gl_shader->bumpenvmatconst[i].const_num, data));
+        const float *data = (const float *)&stateBlock->state.texture_states[texunit][WINED3DTSS_BUMPENVMAT00];
+        GL_EXTCALL(glProgramLocalParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB,
+                gl_shader->bumpenvmatconst[i].const_num, data));
 
         if (gl_shader->luminanceconst[i].const_num != WINED3D_CONST_NUM_UNUSED)
         {
@@ -552,8 +553,9 @@ static inline void shader_arb_ps_local_constants(IWineD3DDeviceImpl* deviceImpl)
              * don't care about them. The pointers are valid for sure because the stateblock is bigger.
              * (they're WINED3DTSS_TEXTURETRANSFORMFLAGS and WINED3DTSS_ADDRESSW, so most likely 0 or NaN
             */
-            const float *scale = (const float *)&stateBlock->textureState[texunit][WINED3DTSS_BUMPENVLSCALE];
-            GL_EXTCALL(glProgramLocalParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB, gl_shader->luminanceconst[i].const_num, scale));
+            const float *scale = (const float *)&stateBlock->state.texture_states[texunit][WINED3DTSS_BUMPENVLSCALE];
+            GL_EXTCALL(glProgramLocalParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB,
+                    gl_shader->luminanceconst[i].const_num, scale));
         }
     }
     checkGLcall("Load bumpmap consts");
@@ -575,16 +577,16 @@ static inline void shader_arb_ps_local_constants(IWineD3DDeviceImpl* deviceImpl)
         checkGLcall("y correction loading");
     }
 
-    if(gl_shader->num_int_consts == 0) return;
+    if (!gl_shader->num_int_consts) return;
 
     for(i = 0; i < MAX_CONST_I; i++)
     {
         if(gl_shader->int_consts[i] != WINED3D_CONST_NUM_UNUSED)
         {
             float val[4];
-            val[0] = stateBlock->pixelShaderConstantI[4 * i];
-            val[1] = stateBlock->pixelShaderConstantI[4 * i + 1];
-            val[2] = stateBlock->pixelShaderConstantI[4 * i + 2];
+            val[0] = (float)stateBlock->state.ps_consts_i[4 * i];
+            val[1] = (float)stateBlock->state.ps_consts_i[4 * i + 1];
+            val[2] = (float)stateBlock->state.ps_consts_i[4 * i + 2];
             val[3] = -1.0f;
 
             GL_EXTCALL(glProgramLocalParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB, gl_shader->int_consts[i], val));
@@ -605,7 +607,7 @@ static inline void shader_arb_vs_local_constants(IWineD3DDeviceImpl* deviceImpl)
     /* Upload the position fixup */
     GL_EXTCALL(glProgramLocalParameter4fvARB(GL_VERTEX_PROGRAM_ARB, gl_shader->pos_fixup, deviceImpl->posFixup));
 
-    if(gl_shader->num_int_consts == 0) return;
+    if (!gl_shader->num_int_consts) return;
 
     stateBlock = deviceImpl->stateBlock;
 
@@ -614,9 +616,9 @@ static inline void shader_arb_vs_local_constants(IWineD3DDeviceImpl* deviceImpl)
         if(gl_shader->int_consts[i] != WINED3D_CONST_NUM_UNUSED)
         {
             float val[4];
-            val[0] = stateBlock->vertexShaderConstantI[4 * i];
-            val[1] = stateBlock->vertexShaderConstantI[4 * i + 1];
-            val[2] = stateBlock->vertexShaderConstantI[4 * i + 2];
+            val[0] = (float)stateBlock->state.vs_consts_i[4 * i];
+            val[1] = (float)stateBlock->state.vs_consts_i[4 * i + 1];
+            val[2] = (float)stateBlock->state.vs_consts_i[4 * i + 2];
             val[3] = -1.0f;
 
             GL_EXTCALL(glProgramLocalParameter4fvARB(GL_VERTEX_PROGRAM_ARB, gl_shader->int_consts[i], val));
@@ -638,21 +640,23 @@ static void shader_arb_load_constants(const struct wined3d_context *context, cha
     IWineD3DStateBlockImpl* stateBlock = device->stateBlock;
     const struct wined3d_gl_info *gl_info = context->gl_info;
 
-    if (useVertexShader) {
-        IWineD3DBaseShaderImpl* vshader = (IWineD3DBaseShaderImpl*) stateBlock->vertexShader;
+    if (useVertexShader)
+    {
+        IWineD3DBaseShaderImpl *vshader = (IWineD3DBaseShaderImpl *)stateBlock->state.vertex_shader;
 
         /* Load DirectX 9 float constants for vertex shader */
         device->highest_dirty_vs_const = shader_arb_load_constantsF(vshader, gl_info, GL_VERTEX_PROGRAM_ARB,
-                device->highest_dirty_vs_const, stateBlock->vertexShaderConstantF, context->vshader_const_dirty);
+                device->highest_dirty_vs_const, stateBlock->state.vs_consts_f, context->vshader_const_dirty);
         shader_arb_vs_local_constants(device);
     }
 
-    if (usePixelShader) {
-        IWineD3DBaseShaderImpl* pshader = (IWineD3DBaseShaderImpl*) stateBlock->pixelShader;
+    if (usePixelShader)
+    {
+        IWineD3DBaseShaderImpl *pshader = (IWineD3DBaseShaderImpl *)stateBlock->state.pixel_shader;
 
         /* Load DirectX 9 float constants for pixel shader */
         device->highest_dirty_ps_const = shader_arb_load_constantsF(pshader, gl_info, GL_FRAGMENT_PROGRAM_ARB,
-                device->highest_dirty_ps_const, stateBlock->pixelShaderConstantF, context->pshader_const_dirty);
+                device->highest_dirty_ps_const, stateBlock->state.ps_consts_f, context->pshader_const_dirty);
         shader_arb_ps_local_constants(device);
     }
 }
@@ -922,7 +926,7 @@ static void shader_arb_request_a0(const struct wined3d_shader_instruction *ins,
     struct shader_arb_ctx_priv *priv = ins->ctx->backend_data;
     struct wined3d_shader_buffer *buffer = ins->ctx->buffer;
 
-    if(strcmp(priv->addr_reg, src) == 0) return;
+    if (!strcmp(priv->addr_reg, src)) return;
 
     strcpy(priv->addr_reg, src);
     shader_addline(buffer, "ARL A0.x, %s;\n", src);
@@ -953,7 +957,7 @@ static void shader_arb_get_register_name(const struct wined3d_shader_instruction
             {
                 if(This->baseShader.reg_maps.shader_version.major < 3)
                 {
-                    if (reg->idx == 0) strcpy(register_name, "fragment.color.primary");
+                    if (!reg->idx) strcpy(register_name, "fragment.color.primary");
                     else strcpy(register_name, "fragment.color.secondary");
                 }
                 else
@@ -963,7 +967,7 @@ static void shader_arb_get_register_name(const struct wined3d_shader_instruction
                         char rel_reg[50];
                         shader_arb_get_src_param(ins, reg->rel_addr, 0, rel_reg);
 
-                        if(strcmp(rel_reg, "**aL_emul**") == 0)
+                        if (!strcmp(rel_reg, "**aL_emul**"))
                         {
                             DWORD idx = ctx->aL + reg->idx;
                             if(idx < MAX_REG_INPUT)
@@ -1045,7 +1049,8 @@ static void shader_arb_get_register_name(const struct wined3d_shader_instruction
                 } else {
                     shader_arb_get_src_param(ins, reg->rel_addr, 0, rel_reg);
                     if(ctx->target_version == ARB) {
-                        if(strcmp(rel_reg, "**aL_emul**") == 0) {
+                        if (!strcmp(rel_reg, "**aL_emul**"))
+                        {
                             aL = TRUE;
                         } else {
                             shader_arb_request_a0(ins, rel_reg);
@@ -1058,7 +1063,7 @@ static void shader_arb_get_register_name(const struct wined3d_shader_instruction
                 else if (reg->idx >= rel_offset)
                     sprintf(register_name, "C[%s + %u]", rel_reg, reg->idx - rel_offset);
                 else
-                    sprintf(register_name, "C[%s - %u]", rel_reg, -reg->idx + rel_offset);
+                    sprintf(register_name, "C[%s - %u]", rel_reg, rel_offset - reg->idx);
             }
             else
             {
@@ -1097,7 +1102,7 @@ static void shader_arb_get_register_name(const struct wined3d_shader_instruction
             break;
 
         case WINED3DSPR_COLOROUT:
-            if(ctx->cur_ps_args->super.srgb_correction && reg->idx == 0)
+            if (ctx->cur_ps_args->super.srgb_correction && !reg->idx)
             {
                 strcpy(register_name, "TMP_COLOR");
             }
@@ -1173,7 +1178,7 @@ static void shader_arb_get_register_name(const struct wined3d_shader_instruction
             break;
 
         case WINED3DSPR_MISCTYPE:
-            if(reg->idx == 0)
+            if (!reg->idx)
             {
                 sprintf(register_name, "vpos");
             }
@@ -1323,6 +1328,7 @@ static void shader_hw_sample(const struct wined3d_shader_instruction *ins, DWORD
 {
     struct wined3d_shader_buffer *buffer = ins->ctx->buffer;
     DWORD sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
+    IWineD3DBaseTextureImpl *texture;
     const char *tex_type;
     BOOL np2_fixup = FALSE;
     IWineD3DBaseShaderImpl *This = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
@@ -1340,8 +1346,9 @@ static void shader_hw_sample(const struct wined3d_shader_instruction *ins, DWORD
             break;
 
         case WINED3DSTT_2D:
-            if(device->stateBlock->textures[sampler_idx] &&
-               IWineD3DBaseTexture_GetTextureDimensions(device->stateBlock->textures[sampler_idx]) == GL_TEXTURE_RECTANGLE_ARB) {
+            texture = device->stateBlock->state.textures[sampler_idx];
+            if (texture && texture->baseTexture.target == GL_TEXTURE_RECTANGLE_ARB)
+            {
                 tex_type = "RECT";
             } else {
                 tex_type = "2D";
@@ -1807,7 +1814,7 @@ static void shader_hw_mov(const struct wined3d_shader_instruction *ins)
             shader_addline(buffer, "ARL A0.x, %s;\n", src0_param);
         }
     }
-    else if(ins->dst[0].reg.type == WINED3DSPR_COLOROUT && ins->dst[0].reg.idx == 0 && pshader)
+    else if (ins->dst[0].reg.type == WINED3DSPR_COLOROUT && !ins->dst[0].reg.idx && pshader)
     {
         IWineD3DPixelShaderImpl *ps = (IWineD3DPixelShaderImpl *) shader;
         if(ctx->cur_ps_args->super.srgb_correction && ps->color0_mov)
@@ -1877,8 +1884,7 @@ static void pshader_hw_texkill(const struct wined3d_shader_instruction *ins)
 
 static void pshader_hw_tex(const struct wined3d_shader_instruction *ins)
 {
-    IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
-    IWineD3DDeviceImpl *deviceImpl = (IWineD3DDeviceImpl *)shader->baseShader.device;
+    struct shader_arb_ctx_priv *priv = ins->ctx->backend_data;
     const struct wined3d_shader_dst_param *dst = &ins->dst[0];
     DWORD shader_version = WINED3D_SHADER_VERSION(ins->ctx->reg_maps->shader_version.major,
             ins->ctx->reg_maps->shader_version.minor);
@@ -1887,7 +1893,7 @@ static void pshader_hw_tex(const struct wined3d_shader_instruction *ins)
     char reg_dest[40];
     char reg_coord[40];
     DWORD reg_sampler_code;
-    DWORD myflags = 0;
+    WORD myflags = 0;
 
     /* All versions have a destination register */
     shader_arb_get_dst_param(ins, dst, reg_dest);
@@ -1919,12 +1925,10 @@ static void pshader_hw_tex(const struct wined3d_shader_instruction *ins)
     if (shader_version < WINED3D_SHADER_VERSION(1,4))
     {
         DWORD flags = 0;
-        if(reg_sampler_code < MAX_TEXTURES) {
-            flags = deviceImpl->stateBlock->textureState[reg_sampler_code][WINED3DTSS_TEXTURETRANSFORMFLAGS];
-        }
-        if (flags & WINED3DTTFF_PROJECTED) {
+        if (reg_sampler_code < MAX_TEXTURES)
+            flags = priv->cur_ps_args->super.tex_transform >> reg_sampler_code * WINED3D_PSARGS_TEXTRANSFORM_SHIFT;
+        if (flags & WINED3D_PSARGS_PROJECTED)
             myflags |= TEX_PROJ;
-        }
     }
     else if (shader_version < WINED3D_SHADER_VERSION(2,0))
     {
@@ -1972,9 +1976,7 @@ static void pshader_hw_texcoord(const struct wined3d_shader_instruction *ins)
 static void pshader_hw_texreg2ar(const struct wined3d_shader_instruction *ins)
 {
      struct wined3d_shader_buffer *buffer = ins->ctx->buffer;
-     IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
-     IWineD3DDeviceImpl *deviceImpl = (IWineD3DDeviceImpl *)shader->baseShader.device;
-     DWORD flags;
+     DWORD flags = 0;
 
      DWORD reg1 = ins->dst[0].reg.idx;
      char dst_str[50];
@@ -1986,8 +1988,12 @@ static void pshader_hw_texreg2ar(const struct wined3d_shader_instruction *ins)
      /* Move .x first in case src_str is "TA" */
      shader_addline(buffer, "MOV TA.y, %s.x;\n", src_str);
      shader_addline(buffer, "MOV TA.x, %s.w;\n", src_str);
-     flags = reg1 < MAX_TEXTURES ? deviceImpl->stateBlock->textureState[reg1][WINED3DTSS_TEXTURETRANSFORMFLAGS] : 0;
-     shader_hw_sample(ins, reg1, dst_str, "TA", flags & WINED3DTTFF_PROJECTED ? TEX_PROJ : 0, NULL, NULL);
+     if (reg1 < MAX_TEXTURES)
+     {
+         struct shader_arb_ctx_priv *priv = ins->ctx->backend_data;
+         flags = priv->cur_ps_args->super.tex_transform >> reg1 * WINED3D_PSARGS_TEXTRANSFORM_SHIFT;
+     }
+     shader_hw_sample(ins, reg1, dst_str, "TA", flags & WINED3D_PSARGS_PROJECTED ? TEX_PROJ : 0, NULL, NULL);
 }
 
 static void pshader_hw_texreg2gb(const struct wined3d_shader_instruction *ins)
@@ -2020,8 +2026,7 @@ static void pshader_hw_texreg2rgb(const struct wined3d_shader_instruction *ins)
 
 static void pshader_hw_texbem(const struct wined3d_shader_instruction *ins)
 {
-    IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
-    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)shader->baseShader.device;
+    struct shader_arb_ctx_priv *priv = ins->ctx->backend_data;
     const struct wined3d_shader_dst_param *dst = &ins->dst[0];
     struct wined3d_shader_buffer *buffer = ins->ctx->buffer;
     char reg_coord[40], dst_reg[50], src_reg[50];
@@ -2053,7 +2058,8 @@ static void pshader_hw_texbem(const struct wined3d_shader_instruction *ins)
     /* with projective textures, texbem only divides the static texture coord, not the displacement,
      * so we can't let the GL handle this.
      */
-    if (device->stateBlock->textureState[reg_dest_code][WINED3DTSS_TEXTURETRANSFORMFLAGS] & WINED3DTTFF_PROJECTED)
+    if ((priv->cur_ps_args->super.tex_transform >> reg_dest_code * WINED3D_PSARGS_TEXTRANSFORM_SHIFT)
+            & WINED3D_PSARGS_PROJECTED)
     {
         shader_addline(buffer, "RCP TB.w, %s.w;\n", reg_coord);
         shader_addline(buffer, "MUL TB.xy, %s, TB.w;\n", reg_coord);
@@ -2108,7 +2114,7 @@ static void pshader_hw_texm3x2tex(const struct wined3d_shader_instruction *ins)
     shader_arb_get_dst_param(ins, &ins->dst[0], dst_str);
     shader_arb_get_src_param(ins, &ins->src[0], 0, src0_name);
     shader_addline(buffer, "DP3 %s.y, fragment.texcoord[%u], %s;\n", dst_reg, reg, src0_name);
-    flags = reg < MAX_TEXTURES ? deviceImpl->stateBlock->textureState[reg][WINED3DTSS_TEXTURETRANSFORMFLAGS] : 0;
+    flags = reg < MAX_TEXTURES ? deviceImpl->stateBlock->state.texture_states[reg][WINED3DTSS_TEXTURETRANSFORMFLAGS] : 0;
     shader_hw_sample(ins, reg, dst_str, dst_reg, flags & WINED3DTTFF_PROJECTED ? TEX_PROJ : 0, NULL, NULL);
 }
 
@@ -2153,7 +2159,7 @@ static void pshader_hw_texm3x3tex(const struct wined3d_shader_instruction *ins)
 
     /* Sample the texture using the calculated coordinates */
     shader_arb_get_dst_param(ins, &ins->dst[0], dst_str);
-    flags = reg < MAX_TEXTURES ? deviceImpl->stateBlock->textureState[reg][WINED3DTSS_TEXTURETRANSFORMFLAGS] : 0;
+    flags = reg < MAX_TEXTURES ? deviceImpl->stateBlock->state.texture_states[reg][WINED3DTSS_TEXTURETRANSFORMFLAGS] : 0;
     shader_hw_sample(ins, reg, dst_str, dst_name, flags & WINED3DTTFF_PROJECTED ? TEX_PROJ : 0, NULL, NULL);
     current_state->current_row = 0;
 }
@@ -2195,7 +2201,7 @@ static void pshader_hw_texm3x3vspec(const struct wined3d_shader_instruction *ins
 
     /* Sample the texture using the calculated coordinates */
     shader_arb_get_dst_param(ins, &ins->dst[0], dst_str);
-    flags = reg < MAX_TEXTURES ? deviceImpl->stateBlock->textureState[reg][WINED3DTSS_TEXTURETRANSFORMFLAGS] : 0;
+    flags = reg < MAX_TEXTURES ? deviceImpl->stateBlock->state.texture_states[reg][WINED3DTSS_TEXTURETRANSFORMFLAGS] : 0;
     shader_hw_sample(ins, reg, dst_str, dst_reg, flags & WINED3DTTFF_PROJECTED ? TEX_PROJ : 0, NULL, NULL);
     current_state->current_row = 0;
 }
@@ -2237,7 +2243,7 @@ static void pshader_hw_texm3x3spec(const struct wined3d_shader_instruction *ins)
 
     /* Sample the texture using the calculated coordinates */
     shader_arb_get_dst_param(ins, &ins->dst[0], dst_str);
-    flags = reg < MAX_TEXTURES ? deviceImpl->stateBlock->textureState[reg][WINED3DTSS_TEXTURETRANSFORMFLAGS] : 0;
+    flags = reg < MAX_TEXTURES ? deviceImpl->stateBlock->state.texture_states[reg][WINED3DTSS_TEXTURETRANSFORMFLAGS] : 0;
     shader_hw_sample(ins, reg, dst_str, dst_reg, flags & WINED3DTTFF_PROJECTED ? TEX_PROJ : 0, NULL, NULL);
     current_state->current_row = 0;
 }
@@ -3052,7 +3058,7 @@ static void shader_hw_texldd(const struct wined3d_shader_instruction *ins)
     DWORD sampler_idx = ins->src[1].reg.idx;
     char reg_dest[40];
     char reg_src[3][40];
-    DWORD flags = TEX_DERIV;
+    WORD flags = TEX_DERIV;
 
     shader_arb_get_dst_param(ins, &ins->dst[0], reg_dest);
     shader_arb_get_src_param(ins, &ins->src[0], 0, reg_src[0]);
@@ -3070,7 +3076,7 @@ static void shader_hw_texldl(const struct wined3d_shader_instruction *ins)
     DWORD sampler_idx = ins->src[1].reg.idx;
     char reg_dest[40];
     char reg_coord[40];
-    DWORD flags = TEX_LOD;
+    WORD flags = TEX_LOD;
 
     shader_arb_get_dst_param(ins, &ins->dst[0], reg_dest);
     shader_arb_get_src_param(ins, &ins->src[0], 0, reg_coord);
@@ -3412,7 +3418,7 @@ static const DWORD *find_loop_control_values(IWineD3DBaseShaderImpl *This, DWORD
 static void init_ps_input(const IWineD3DPixelShaderImpl *This, const struct arb_ps_compile_args *args,
                           struct shader_arb_ctx_priv *priv)
 {
-    const char *texcoords[8] =
+    static const char * const texcoords[8] =
     {
         "fragment.texcoord[0]", "fragment.texcoord[1]", "fragment.texcoord[2]", "fragment.texcoord[3]",
         "fragment.texcoord[4]", "fragment.texcoord[5]", "fragment.texcoord[6]", "fragment.texcoord[7]"
@@ -3438,11 +3444,11 @@ static void init_ps_input(const IWineD3DPixelShaderImpl *This, const struct arb_
             {
                 semantic_name = sig[i].semantic_name;
                 semantic_idx = sig[i].semantic_idx;
-                if(semantic_name == NULL) continue;
+                if (!semantic_name) continue;
 
                 if(shader_match_semantic(semantic_name, WINED3DDECLUSAGE_COLOR))
                 {
-                    if(semantic_idx == 0) priv->ps_input[i] = "fragment.color.primary";
+                    if (!semantic_idx) priv->ps_input[i] = "fragment.color.primary";
                     else if(semantic_idx == 1) priv->ps_input[i] = "fragment.color.secondary";
                     else priv->ps_input[i] = "0.0";
                 }
@@ -3457,7 +3463,7 @@ static void init_ps_input(const IWineD3DPixelShaderImpl *This, const struct arb_
                 }
                 else if(shader_match_semantic(semantic_name, WINED3DDECLUSAGE_FOG))
                 {
-                    if(semantic_idx == 0) priv->ps_input[i] = "fragment.fogcoord";
+                    if (!semantic_idx) priv->ps_input[i] = "fragment.fogcoord";
                     else priv->ps_input[i] = "0.0";
                 }
                 else
@@ -3508,7 +3514,7 @@ static GLuint shader_arb_generate_pshader(IWineD3DPixelShaderImpl *This, struct
     {
         if (!(map & 1)
                 || (This->color0_mov && i == This->color0_reg)
-                || (reg_maps->shader_version.major < 2 && i == 0))
+                || (reg_maps->shader_version.major < 2 && !i))
             continue;
 
         sprintf(srgbtmp[found], "R%u", i);
@@ -3827,15 +3833,14 @@ static int compare_sig(const struct wined3d_shader_signature_element *sig1, cons
 
     for(i = 0; i < MAX_REG_INPUT; i++)
     {
-        if(sig1[i].semantic_name == NULL || sig2[i].semantic_name == NULL)
+        if (!sig1[i].semantic_name || !sig2[i].semantic_name)
         {
             /* Compare pointers, not contents. One string is NULL(element does not exist), the other one is not NULL */
             if(sig1[i].semantic_name != sig2[i].semantic_name) return sig1[i].semantic_name < sig2[i].semantic_name ? -1 : 1;
             continue;
         }
 
-        ret = strcmp(sig1[i].semantic_name, sig2[i].semantic_name);
-        if(ret != 0) return ret;
+        if ((ret = strcmp(sig1[i].semantic_name, sig2[i].semantic_name))) return ret;
         if(sig1[i].semantic_idx    != sig2[i].semantic_idx)    return sig1[i].semantic_idx    < sig2[i].semantic_idx    ? -1 : 1;
         if(sig1[i].sysval_semantic != sig2[i].sysval_semantic) return sig1[i].sysval_semantic < sig2[i].sysval_semantic ? -1 : 1;
         if(sig1[i].component_type  != sig2[i].component_type)  return sig1[i].sysval_semantic < sig2[i].component_type  ? -1 : 1;
@@ -3854,10 +3859,7 @@ static struct wined3d_shader_signature_element *clone_sig(const struct wined3d_s
     new = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*new) * MAX_REG_INPUT);
     for(i = 0; i < MAX_REG_INPUT; i++)
     {
-        if(sig[i].semantic_name == NULL)
-        {
-            continue;
-        }
+        if (!sig[i].semantic_name) continue;
 
         new[i] = sig[i];
         /* Clone the semantic string */
@@ -3873,7 +3875,7 @@ static DWORD find_input_signature(struct shader_arb_priv *priv, const struct win
     struct wine_rb_entry *entry = wine_rb_get(&priv->signature_tree, sig);
     struct ps_signature *found_sig;
 
-    if(entry != NULL)
+    if (entry)
     {
         found_sig = WINE_RB_ENTRY_VALUE(entry, struct ps_signature, entry);
         TRACE("Found existing signature %u\n", found_sig->idx);
@@ -3894,7 +3896,7 @@ static void init_output_registers(IWineD3DVertexShaderImpl *shader, DWORD sig_nu
                                   struct arb_vs_compiled_shader *compiled)
 {
     unsigned int i, j;
-    static const char *texcoords[8] =
+    static const char * const texcoords[8] =
     {
         "result.texcoord[0]", "result.texcoord[1]", "result.texcoord[2]", "result.texcoord[3]",
         "result.texcoord[4]", "result.texcoord[5]", "result.texcoord[6]", "result.texcoord[7]"
@@ -3908,10 +3910,10 @@ static void init_output_registers(IWineD3DVertexShaderImpl *shader, DWORD sig_nu
     /* Write generic input varyings 0 to 7 to result.texcoord[], varying 8 to result.color.primary
      * and varying 9 to result.color.secondary
      */
-    const char *decl_idx_to_string[MAX_REG_INPUT] =
+    static const char * const decl_idx_to_string[MAX_REG_INPUT] =
     {
-        texcoords[0], texcoords[1], texcoords[2], texcoords[3],
-        texcoords[4], texcoords[5], texcoords[6], texcoords[7],
+        "result.texcoord[0]", "result.texcoord[1]", "result.texcoord[2]", "result.texcoord[3]",
+        "result.texcoord[4]", "result.texcoord[5]", "result.texcoord[6]", "result.texcoord[7]",
         "result.color.primary", "result.color.secondary"
     };
 
@@ -3931,24 +3933,24 @@ static void init_output_registers(IWineD3DVertexShaderImpl *shader, DWORD sig_nu
         for (i = 0; i < (sizeof(baseshader->output_signature) / sizeof(*baseshader->output_signature)); ++i)
         {
             semantic_name = baseshader->output_signature[i].semantic_name;
-            if(semantic_name == NULL) continue;
+            if (!semantic_name) continue;
 
             if(shader_match_semantic(semantic_name, WINED3DDECLUSAGE_POSITION))
             {
                 TRACE("o%u is TMP_OUT\n", i);
-                if (baseshader->output_signature[i].semantic_idx == 0) priv_ctx->vs_output[i] = "TMP_OUT";
+                if (!baseshader->output_signature[i].semantic_idx) priv_ctx->vs_output[i] = "TMP_OUT";
                 else priv_ctx->vs_output[i] = "TA";
             }
             else if(shader_match_semantic(semantic_name, WINED3DDECLUSAGE_PSIZE))
             {
                 TRACE("o%u is result.pointsize\n", i);
-                if (baseshader->output_signature[i].semantic_idx == 0) priv_ctx->vs_output[i] = "result.pointsize";
+                if (!baseshader->output_signature[i].semantic_idx) priv_ctx->vs_output[i] = "result.pointsize";
                 else priv_ctx->vs_output[i] = "TA";
             }
             else if(shader_match_semantic(semantic_name, WINED3DDECLUSAGE_COLOR))
             {
                 TRACE("o%u is result.color.?, idx %u\n", i, baseshader->output_signature[i].semantic_idx);
-                if (baseshader->output_signature[i].semantic_idx == 0)
+                if (!baseshader->output_signature[i].semantic_idx)
                     priv_ctx->vs_output[i] = "result.color.primary";
                 else if (baseshader->output_signature[i].semantic_idx == 1)
                     priv_ctx->vs_output[i] = "result.color.secondary";
@@ -3977,7 +3979,7 @@ static void init_output_registers(IWineD3DVertexShaderImpl *shader, DWORD sig_nu
     /* Instead of searching for the signature in the signature list, read the one from the current pixel shader.
      * Its maybe not the shader where the signature came from, but it is the same signature and faster to find
      */
-    sig = ((IWineD3DPixelShaderImpl *)device->stateBlock->pixelShader)->baseShader.input_signature;
+    sig = device->stateBlock->state.pixel_shader->baseShader.input_signature;
     TRACE("Pixel shader uses declared varyings\n");
 
     /* Map builtin to declared. /dev/null the results by default to the TA temp reg */
@@ -3994,7 +3996,7 @@ static void init_output_registers(IWineD3DVertexShaderImpl *shader, DWORD sig_nu
         semantic_name = sig[i].semantic_name;
         semantic_idx = sig[i].semantic_idx;
         reg_idx = sig[i].register_idx;
-        if(semantic_name == NULL) continue;
+        if (!semantic_name) continue;
 
         /* If a declared input register is not written by builtin arguments, don't write to it.
          * GL_NV_vertex_program makes sure the input defaults to 0.0, which is correct with D3D
@@ -4012,15 +4014,15 @@ static void init_output_registers(IWineD3DVertexShaderImpl *shader, DWORD sig_nu
         }
         else if(shader_match_semantic(semantic_name, WINED3DDECLUSAGE_FOG))
         {
-            if(semantic_idx == 0) priv_ctx->fog_output = decl_idx_to_string[reg_idx];
+            if (!semantic_idx) priv_ctx->fog_output = decl_idx_to_string[reg_idx];
         }
         else
         {
             continue;
         }
 
-        if(strcmp(decl_idx_to_string[reg_idx], "result.color.primary") == 0 ||
-           strcmp(decl_idx_to_string[reg_idx], "result.color.secondary") == 0)
+        if (!strcmp(decl_idx_to_string[reg_idx], "result.color.primary")
+                || !strcmp(decl_idx_to_string[reg_idx], "result.color.secondary"))
         {
             compiled->need_color_unclamp = TRUE;
         }
@@ -4032,19 +4034,16 @@ static void init_output_registers(IWineD3DVertexShaderImpl *shader, DWORD sig_nu
         /* Write unread output to TA to throw them away */
         priv_ctx->vs_output[i] = "TA";
         semantic_name = baseshader->output_signature[i].semantic_name;
-        if(semantic_name == NULL)
-        {
-            continue;
-        }
+        if (!semantic_name) continue;
 
         if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_POSITION)
-                && baseshader->output_signature[i].semantic_idx == 0)
+                && !baseshader->output_signature[i].semantic_idx)
         {
             priv_ctx->vs_output[i] = "TMP_OUT";
             continue;
         }
         else if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_PSIZE)
-                && baseshader->output_signature[i].semantic_idx == 0)
+                && !baseshader->output_signature[i].semantic_idx)
         {
             priv_ctx->vs_output[i] = "result.pointsize";
             continue;
@@ -4052,18 +4051,15 @@ static void init_output_registers(IWineD3DVertexShaderImpl *shader, DWORD sig_nu
 
         for(j = 0; j < MAX_REG_INPUT; j++)
         {
-            if(sig[j].semantic_name == NULL)
-            {
-                continue;
-            }
+            if (!sig[j].semantic_name) continue;
 
-            if (strcmp(sig[j].semantic_name, semantic_name) == 0
+            if (!strcmp(sig[j].semantic_name, semantic_name)
                     && sig[j].semantic_idx == baseshader->output_signature[i].semantic_idx)
             {
                 priv_ctx->vs_output[i] = decl_idx_to_string[sig[j].register_idx];
 
-                if(strcmp(priv_ctx->vs_output[i], "result.color.primary") == 0 ||
-                   strcmp(priv_ctx->vs_output[i], "result.color.secondary") == 0)
+                if (!strcmp(priv_ctx->vs_output[i], "result.color.primary")
+                        || !strcmp(priv_ctx->vs_output[i], "result.color.secondary"))
                 {
                     compiled->need_color_unclamp = TRUE;
                 }
@@ -4175,10 +4171,9 @@ static GLuint shader_arb_generate_vshader(IWineD3DVertexShaderImpl *This, struct
             const char *one = arb_get_helper_value(WINED3D_SHADER_TYPE_VERTEX, ARB_ONE);
             for(i = 0; i < min(8, MAX_REG_TEXCRD); i++)
             {
-                if (This->baseShader.reg_maps.texcoord_mask[i] != 0 &&
-                This->baseShader.reg_maps.texcoord_mask[i] != WINED3DSP_WRITEMASK_ALL) {
+                if (This->baseShader.reg_maps.texcoord_mask[i]
+                        && This->baseShader.reg_maps.texcoord_mask[i] != WINED3DSP_WRITEMASK_ALL)
                     shader_addline(buffer, "MOV result.texcoord[%u].w, %s\n", i, one);
-                }
             }
         }
     }
@@ -4236,6 +4231,7 @@ static GLuint shader_arb_generate_vshader(IWineD3DVertexShaderImpl *This, struct
 /* GL locking is done by the caller */
 static struct arb_ps_compiled_shader *find_arb_pshader(IWineD3DPixelShaderImpl *shader, const struct arb_ps_compile_args *args)
 {
+    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)shader->baseShader.device;
     UINT i;
     DWORD new_size;
     struct arb_ps_compiled_shader *new_array;
@@ -4245,7 +4241,6 @@ static struct arb_ps_compiled_shader *find_arb_pshader(IWineD3DPixelShaderImpl *
 
     if (!shader->baseShader.backend_data)
     {
-        IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *) shader->baseShader.device;
         const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
         struct shader_arb_priv *priv = device->shader_priv;
 
@@ -4271,10 +4266,10 @@ static struct arb_ps_compiled_shader *find_arb_pshader(IWineD3DPixelShaderImpl *
      * so a linear search is more performant than a hashmap or a binary search
      * (cache coherency etc)
      */
-    for(i = 0; i < shader_data->num_gl_shaders; i++) {
-        if(memcmp(&shader_data->gl_shaders[i].args, args, sizeof(*args)) == 0) {
+    for (i = 0; i < shader_data->num_gl_shaders; ++i)
+    {
+        if (!memcmp(&shader_data->gl_shaders[i].args, args, sizeof(*args)))
             return &shader_data->gl_shaders[i];
-        }
     }
 
     TRACE("No matching GL shader found, compiling a new shader\n");
@@ -4300,7 +4295,7 @@ static struct arb_ps_compiled_shader *find_arb_pshader(IWineD3DPixelShaderImpl *
     shader_data->gl_shaders[shader_data->num_gl_shaders].args = *args;
 
     pixelshader_update_samplers(&shader->baseShader.reg_maps,
-            ((IWineD3DDeviceImpl *)shader->baseShader.device)->stateBlock->textures);
+            (IWineD3DBaseTexture **)device->stateBlock->state.textures);
 
     if (!shader_buffer_init(&buffer))
     {
@@ -4326,7 +4321,7 @@ static inline BOOL vs_args_equal(const struct arb_vs_compile_args *stored, const
     if(stored->vertex.samplers_compare != new->vertex.samplers_compare) return FALSE;
     if(skip_int) return TRUE;
 
-    return memcmp(stored->loop_ctrl, new->loop_ctrl, sizeof(stored->loop_ctrl)) == 0;
+    return !memcmp(stored->loop_ctrl, new->loop_ctrl, sizeof(stored->loop_ctrl));
 }
 
 static struct arb_vs_compiled_shader *find_arb_vshader(IWineD3DVertexShaderImpl *shader, const struct arb_vs_compile_args *args)
@@ -4395,35 +4390,34 @@ static struct arb_vs_compiled_shader *find_arb_vshader(IWineD3DVertexShaderImpl
     return &shader_data->gl_shaders[shader_data->num_gl_shaders++];
 }
 
-static inline void find_arb_ps_compile_args(IWineD3DPixelShaderImpl *shader, IWineD3DStateBlockImpl *stateblock,
-        struct arb_ps_compile_args *args)
+static void find_arb_ps_compile_args(const struct wined3d_state *state,
+        IWineD3DPixelShaderImpl *shader, struct arb_ps_compile_args *args)
 {
     int i;
     WORD int_skip;
     const struct wined3d_gl_info *gl_info = &((IWineD3DDeviceImpl *)shader->baseShader.device)->adapter->gl_info;
-    find_ps_compile_args(shader, stateblock, &args->super);
+
+    find_ps_compile_args(state, shader, &args->super);
 
     /* This forces all local boolean constants to 1 to make them stateblock independent */
     args->bools = shader->baseShader.reg_maps.local_bool_consts;
 
     for(i = 0; i < MAX_CONST_B; i++)
     {
-        if(stateblock->pixelShaderConstantB[i]) args->bools |= ( 1 << i);
+        if (state->ps_consts_b[i])
+            args->bools |= ( 1 << i);
     }
 
     /* Only enable the clip plane emulation KIL if at least one clipplane is enabled. The KIL instruction
      * is quite expensive because it forces the driver to disable early Z discards. It is cheaper to
      * duplicate the shader than have a no-op KIL instruction in every shader
      */
-    if((!((IWineD3DDeviceImpl *) shader->baseShader.device)->vs_clipping) && use_vs(stateblock) &&
-       stateblock->renderState[WINED3DRS_CLIPPING] && stateblock->renderState[WINED3DRS_CLIPPLANEENABLE])
-    {
+    if ((!((IWineD3DDeviceImpl *)shader->baseShader.device)->vs_clipping) && use_vs(state)
+            && state->render_states[WINED3DRS_CLIPPING]
+            && state->render_states[WINED3DRS_CLIPPLANEENABLE])
         args->clip = 1;
-    }
     else
-    {
         args->clip = 0;
-    }
 
     /* Skip if unused or local, or supported natively */
     int_skip = ~shader->baseShader.reg_maps.integer_constants | shader->baseShader.reg_maps.local_int_consts;
@@ -4443,26 +4437,27 @@ static inline void find_arb_ps_compile_args(IWineD3DPixelShaderImpl *shader, IWi
         }
         else
         {
-            args->loop_ctrl[i][0] = stateblock->pixelShaderConstantI[i * 4];
-            args->loop_ctrl[i][1] = stateblock->pixelShaderConstantI[i * 4 + 1];
-            args->loop_ctrl[i][2] = stateblock->pixelShaderConstantI[i * 4 + 2];
+            args->loop_ctrl[i][0] = state->ps_consts_i[i * 4];
+            args->loop_ctrl[i][1] = state->ps_consts_i[i * 4 + 1];
+            args->loop_ctrl[i][2] = state->ps_consts_i[i * 4 + 2];
         }
     }
 }
 
-static inline void find_arb_vs_compile_args(IWineD3DVertexShaderImpl *shader, IWineD3DStateBlockImpl *stateblock,
-        struct arb_vs_compile_args *args)
+static void find_arb_vs_compile_args(const struct wined3d_state *state,
+        IWineD3DVertexShaderImpl *shader, struct arb_vs_compile_args *args)
 {
     int i;
     WORD int_skip;
     IWineD3DDeviceImpl *dev = (IWineD3DDeviceImpl *)shader->baseShader.device;
     const struct wined3d_gl_info *gl_info = &dev->adapter->gl_info;
-    find_vs_compile_args(shader, stateblock, &args->super);
+
+    find_vs_compile_args(state, shader, &args->super);
 
     args->clip.boolclip_compare = 0;
-    if(use_ps(stateblock))
+    if (use_ps(state))
     {
-        IWineD3DPixelShaderImpl *ps = (IWineD3DPixelShaderImpl *) stateblock->pixelShader;
+        IWineD3DPixelShaderImpl *ps = state->pixel_shader;
         struct arb_pshader_private *shader_priv = ps->baseShader.backend_data;
         args->ps_signature = shader_priv->input_signature_idx;
 
@@ -4473,17 +4468,15 @@ static inline void find_arb_vs_compile_args(IWineD3DVertexShaderImpl *shader, IW
         args->ps_signature = ~0;
         if(!dev->vs_clipping)
         {
-            args->clip.boolclip.clip_texcoord = ffp_clip_emul(stateblock) ? gl_info->limits.texture_stages : 0;
+            args->clip.boolclip.clip_texcoord = ffp_clip_emul(state) ? gl_info->limits.texture_stages : 0;
         }
         /* Otherwise: Setting boolclip_compare set clip_texcoord to 0 */
     }
 
-    if(args->clip.boolclip.clip_texcoord)
+    if (args->clip.boolclip.clip_texcoord)
     {
-        if(stateblock->renderState[WINED3DRS_CLIPPING])
-        {
-            args->clip.boolclip.clipplane_mask = stateblock->renderState[WINED3DRS_CLIPPLANEENABLE];
-        }
+        if (state->render_states[WINED3DRS_CLIPPING])
+            args->clip.boolclip.clipplane_mask = (unsigned char)state->render_states[WINED3DRS_CLIPPLANEENABLE];
         /* clipplane_mask was set to 0 by setting boolclip_compare to 0 */
     }
 
@@ -4492,7 +4485,8 @@ static inline void find_arb_vs_compile_args(IWineD3DVertexShaderImpl *shader, IW
     /* TODO: Figure out if it would be better to store bool constants as bitmasks in the stateblock */
     for(i = 0; i < MAX_CONST_B; i++)
     {
-        if(stateblock->vertexShaderConstantB[i]) args->clip.boolclip.bools |= ( 1 << i);
+        if (state->vs_consts_b[i])
+            args->clip.boolclip.bools |= ( 1 << i);
     }
 
     args->vertex.samplers[0] = dev->texUnitMap[MAX_FRAGMENT_SAMPLERS + 0];
@@ -4519,9 +4513,9 @@ static inline void find_arb_vs_compile_args(IWineD3DVertexShaderImpl *shader, IW
         }
         else
         {
-            args->loop_ctrl[i][0] = stateblock->vertexShaderConstantI[i * 4];
-            args->loop_ctrl[i][1] = stateblock->vertexShaderConstantI[i * 4 + 1];
-            args->loop_ctrl[i][2] = stateblock->vertexShaderConstantI[i * 4 + 2];
+            args->loop_ctrl[i][0] = state->vs_consts_i[i * 4];
+            args->loop_ctrl[i][1] = state->vs_consts_i[i * 4 + 1];
+            args->loop_ctrl[i][2] = state->vs_consts_i[i * 4 + 2];
         }
     }
 }
@@ -4532,16 +4526,18 @@ static void shader_arb_select(const struct wined3d_context *context, BOOL usePS,
     IWineD3DDeviceImpl *This = context->swapchain->device;
     struct shader_arb_priv *priv = This->shader_priv;
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &This->stateBlock->state;
     int i;
 
     /* Deal with pixel shaders first so the vertex shader arg function has the input signature ready */
-    if (usePS) {
+    if (usePS)
+    {
+        IWineD3DPixelShaderImpl *ps = state->pixel_shader;
         struct arb_ps_compile_args compile_args;
         struct arb_ps_compiled_shader *compiled;
-        IWineD3DPixelShaderImpl *ps = (IWineD3DPixelShaderImpl *) This->stateBlock->pixelShader;
 
-        TRACE("Using pixel shader %p\n", This->stateBlock->pixelShader);
-        find_arb_ps_compile_args(ps, This->stateBlock, &compile_args);
+        TRACE("Using pixel shader %p.\n", ps);
+        find_arb_ps_compile_args(state, ps, &compile_args);
         compiled = find_arb_pshader(ps, &compile_args);
         priv->current_fprogram_id = compiled->prgId;
         priv->compiled_fprog = compiled;
@@ -4591,13 +4587,14 @@ static void shader_arb_select(const struct wined3d_context *context, BOOL usePS,
         priv->current_fprogram_id = 0;
     }
 
-    if (useVS) {
+    if (useVS)
+    {
+        IWineD3DVertexShaderImpl *vs = state->vertex_shader;
         struct arb_vs_compile_args compile_args;
         struct arb_vs_compiled_shader *compiled;
-        IWineD3DVertexShaderImpl *vs = (IWineD3DVertexShaderImpl *) This->stateBlock->vertexShader;
 
-        TRACE("Using vertex shader %p\n", This->stateBlock->vertexShader);
-        find_arb_vs_compile_args(vs, This->stateBlock, &compile_args);
+        TRACE("Using vertex shader %p\n", vs);
+        find_arb_vs_compile_args(state, vs, &compile_args);
         compiled = find_arb_vshader(vs, &compile_args);
         priv->current_vprogram_id = compiled->prgId;
         priv->compiled_vprog = compiled;
@@ -4919,7 +4916,7 @@ static void shader_arb_add_instruction_modifiers(const struct wined3d_shader_ins
 
     dst = &ins->dst[0];
     shift = dst->shift;
-    if(shift == 0) return; /* Saturate alone is handled by the instructions */
+    if (!shift) return; /* Saturate alone is handled by the instructions */
 
     shader_arb_get_write_mask(ins, dst, write_mask);
     shader_arb_get_register_name(ins, &dst->reg, regstr, &is_color);
@@ -4936,6 +4933,7 @@ static const SHADER_HANDLER shader_arb_instruction_handler_table[WINED3DSIH_TABL
 {
     /* WINED3DSIH_ABS           */ shader_hw_map2gl,
     /* WINED3DSIH_ADD           */ shader_hw_map2gl,
+    /* WINED3DSIH_AND           */ NULL,
     /* WINED3DSIH_BEM           */ pshader_hw_bem,
     /* WINED3DSIH_BREAK         */ shader_hw_break,
     /* WINED3DSIH_BREAKC        */ shader_hw_breakc,
@@ -4968,6 +4966,7 @@ static const SHADER_HANDLER shader_arb_instruction_handler_table[WINED3DSIH_TABL
     /* WINED3DSIH_IF            */ NULL /* Hardcoded into the shader */,
     /* WINED3DSIH_IFC           */ shader_hw_ifc,
     /* WINED3DSIH_IGE           */ NULL,
+    /* WINED3DSIH_IMUL          */ NULL,
     /* WINED3DSIH_LABEL         */ shader_hw_label,
     /* WINED3DSIH_LIT           */ shader_hw_map2gl,
     /* WINED3DSIH_LOG           */ shader_hw_log_pow,
@@ -4985,6 +4984,7 @@ static const SHADER_HANDLER shader_arb_instruction_handler_table[WINED3DSIH_TABL
     /* WINED3DSIH_MIN           */ shader_hw_map2gl,
     /* WINED3DSIH_MOV           */ shader_hw_mov,
     /* WINED3DSIH_MOVA          */ shader_hw_mov,
+    /* WINED3DSIH_MOVC          */ NULL,
     /* WINED3DSIH_MUL           */ shader_hw_map2gl,
     /* WINED3DSIH_NOP           */ shader_hw_nop,
     /* WINED3DSIH_NRM           */ shader_hw_nrm,
@@ -5244,7 +5244,8 @@ static void shader_arb_handle_instruction(const struct wined3d_shader_instructio
 
             if(control_frame->outer_loop)
             {
-                int iteration, aL = 0;
+                unsigned int iteration;
+                int aL = 0;
                 struct list copy;
 
                 /* Turn off recording before playback */
@@ -5276,11 +5277,11 @@ static void shader_arb_handle_instruction(const struct wined3d_shader_instructio
                     if(ins->handler_idx == WINED3DSIH_ENDLOOP)
                     {
                         priv->aL = aL;
-                        shader_addline(buffer, "#Iteration %d, aL=%d\n", iteration, aL);
+                        shader_addline(buffer, "#Iteration %u, aL=%d\n", iteration, aL);
                     }
                     else
                     {
-                        shader_addline(buffer, "#Iteration %d\n", iteration);
+                        shader_addline(buffer, "#Iteration %u\n", iteration);
                     }
 
                     LIST_FOR_EACH_ENTRY(rec_ins, &copy, struct recorded_instruction, entry)
@@ -5322,7 +5323,7 @@ static void shader_arb_handle_instruction(const struct wined3d_shader_instructio
 
         bool_const = get_bool_const(ins, This, ins->src[0].reg.idx);
         if(ins->src[0].modifiers == WINED3DSPSM_NOT) bool_const = !bool_const;
-        if(!priv->muted && bool_const == FALSE)
+        if (!priv->muted && !bool_const)
         {
             shader_addline(buffer, "#if(FALSE){\n");
             priv->muted = TRUE;
@@ -5536,45 +5537,51 @@ static void arbfp_get_caps(const struct wined3d_gl_info *gl_info, struct fragmen
     caps->MaxSimultaneousTextures = min(gl_info->limits.fragment_samplers, 8);
 }
 
-static void state_texfactor_arbfp(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void state_texfactor_arbfp(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
     IWineD3DDeviceImpl *device = stateblock->device;
     float col[4];
 
     /* Don't load the parameter if we're using an arbfp pixel shader, otherwise we'll overwrite
      * application provided constants
      */
-    if(device->shader_backend == &arb_program_shader_backend) {
-        if (use_ps(stateblock)) return;
+    if (device->shader_backend == &arb_program_shader_backend)
+    {
+        if (use_ps(state)) return;
 
         context->pshader_const_dirty[ARB_FFP_CONST_TFACTOR] = 1;
         device->highest_dirty_ps_const = max(device->highest_dirty_ps_const, ARB_FFP_CONST_TFACTOR + 1);
     }
 
-    D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_TEXTUREFACTOR], col);
+    D3DCOLORTOGLFLOAT4(state->render_states[WINED3DRS_TEXTUREFACTOR], col);
     GL_EXTCALL(glProgramEnvParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB, ARB_FFP_CONST_TFACTOR, col));
     checkGLcall("glProgramEnvParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB, ARB_FFP_CONST_TFACTOR, col)");
 
 }
 
-static void state_arb_specularenable(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void state_arb_specularenable(DWORD state_id,
+        IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
     IWineD3DDeviceImpl *device = stateblock->device;
     float col[4];
 
     /* Don't load the parameter if we're using an arbfp pixel shader, otherwise we'll overwrite
      * application provided constants
      */
-    if(device->shader_backend == &arb_program_shader_backend) {
-        if (use_ps(stateblock)) return;
+    if (device->shader_backend == &arb_program_shader_backend)
+    {
+        if (use_ps(state)) return;
 
         context->pshader_const_dirty[ARB_FFP_CONST_SPECULAR_ENABLE] = 1;
         device->highest_dirty_ps_const = max(device->highest_dirty_ps_const, ARB_FFP_CONST_SPECULAR_ENABLE + 1);
     }
 
-    if(stateblock->renderState[WINED3DRS_SPECULARENABLE]) {
+    if (state->render_states[WINED3DRS_SPECULARENABLE])
+    {
         /* The specular color has no alpha */
         col[0] = 1.0f; col[1] = 1.0f;
         col[2] = 1.0f; col[3] = 0.0f;
@@ -5586,17 +5593,18 @@ static void state_arb_specularenable(DWORD state, IWineD3DStateBlockImpl *stateb
     checkGLcall("glProgramEnvParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB, ARB_FFP_CONST_SPECULAR_ENABLE, col)");
 }
 
-static void set_bumpmat_arbfp(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void set_bumpmat_arbfp(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
+    DWORD stage = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
     IWineD3DDeviceImpl *device = stateblock->device;
     float mat[2][2];
 
-    if (use_ps(stateblock))
+    if (use_ps(state))
     {
-        if (stage != 0
-                && (((IWineD3DPixelShaderImpl *)stateblock->pixelShader)->baseShader.reg_maps.bumpmat & (1 << stage)))
+        IWineD3DPixelShaderImpl *ps = state->pixel_shader;
+        if (stage && (ps->baseShader.reg_maps.bumpmat & (1 << stage)))
         {
             /* The pixel shader has to know the bump env matrix. Do a constants update if it isn't scheduled
              * anyway
@@ -5614,26 +5622,27 @@ static void set_bumpmat_arbfp(DWORD state, IWineD3DStateBlockImpl *stateblock, s
         device->highest_dirty_ps_const = max(device->highest_dirty_ps_const, ARB_FFP_CONST_BUMPMAT(stage) + 1);
     }
 
-    mat[0][0] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT00]);
-    mat[0][1] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT01]);
-    mat[1][0] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT10]);
-    mat[1][1] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT11]);
+    mat[0][0] = *((float *)&state->texture_states[stage][WINED3DTSS_BUMPENVMAT00]);
+    mat[0][1] = *((float *)&state->texture_states[stage][WINED3DTSS_BUMPENVMAT01]);
+    mat[1][0] = *((float *)&state->texture_states[stage][WINED3DTSS_BUMPENVMAT10]);
+    mat[1][1] = *((float *)&state->texture_states[stage][WINED3DTSS_BUMPENVMAT11]);
 
     GL_EXTCALL(glProgramEnvParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB, ARB_FFP_CONST_BUMPMAT(stage), &mat[0][0]));
     checkGLcall("glProgramEnvParameter4fvARB(GL_FRAGMENT_PROGRAM_ARB, ARB_FFP_CONST_BUMPMAT(stage), &mat[0][0])");
 }
 
-static void tex_bumpenvlum_arbfp(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void tex_bumpenvlum_arbfp(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
+    DWORD stage = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
     IWineD3DDeviceImpl *device = stateblock->device;
     float param[4];
 
-    if (use_ps(stateblock))
+    if (use_ps(state))
     {
-        if (stage != 0
-                && (((IWineD3DPixelShaderImpl *)stateblock->pixelShader)->baseShader.reg_maps.luminanceparams & (1 << stage)))
+        IWineD3DPixelShaderImpl *ps = state->pixel_shader;
+        if (stage && (ps->baseShader.reg_maps.luminanceparams & (1 << stage)))
         {
             /* The pixel shader has to know the luminance offset. Do a constants update if it
              * isn't scheduled anyway
@@ -5651,8 +5660,8 @@ static void tex_bumpenvlum_arbfp(DWORD state, IWineD3DStateBlockImpl *stateblock
         device->highest_dirty_ps_const = max(device->highest_dirty_ps_const, ARB_FFP_CONST_LUMINANCE(stage) + 1);
     }
 
-    param[0] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVLSCALE]);
-    param[1] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVLOFFSET]);
+    param[0] = *((float *)&state->texture_states[stage][WINED3DTSS_BUMPENVLSCALE]);
+    param[1] = *((float *)&state->texture_states[stage][WINED3DTSS_BUMPENVLOFFSET]);
     param[2] = 0.0f;
     param[3] = 0.0f;
 
@@ -5671,7 +5680,7 @@ static const char *get_argreg(struct wined3d_shader_buffer *buffer, DWORD argnum
             ret = "fragment.color.primary"; break;
 
         case WINED3DTA_CURRENT:
-            if(stage == 0) ret = "fragment.color.primary";
+            if (!stage) ret = "fragment.color.primary";
             else ret = "ret";
             break;
 
@@ -5752,7 +5761,7 @@ static void gen_ffp_instr(struct wined3d_shader_buffer *buffer, unsigned int sta
 
     switch(op) {
         case WINED3DTOP_DISABLE:
-            if(stage == 0) shader_addline(buffer, "MOV %s%s, fragment.color.primary;\n", dstreg, dstmask);
+            if (!stage) shader_addline(buffer, "MOV %s%s, fragment.color.primary;\n", dstreg, dstmask);
             break;
 
         case WINED3DTOP_SELECTARG2:
@@ -5765,7 +5774,8 @@ static void gen_ffp_instr(struct wined3d_shader_buffer *buffer, unsigned int sta
             mul = 2;
         case WINED3DTOP_MODULATE2X:
             mul *= 2;
-            if(strcmp(dstreg, "result.color") == 0) {
+            if (!strcmp(dstreg, "result.color"))
+            {
                 dstreg = "ret";
                 mul_final_dest = TRUE;
             }
@@ -5775,7 +5785,8 @@ static void gen_ffp_instr(struct wined3d_shader_buffer *buffer, unsigned int sta
 
         case WINED3DTOP_ADDSIGNED2X:
             mul = 2;
-            if(strcmp(dstreg, "result.color") == 0) {
+            if (!strcmp(dstreg, "result.color"))
+            {
                 dstreg = "ret";
                 mul_final_dest = TRUE;
             }
@@ -5837,7 +5848,8 @@ static void gen_ffp_instr(struct wined3d_shader_buffer *buffer, unsigned int sta
 
         case WINED3DTOP_DOTPRODUCT3:
             mul = 4;
-            if(strcmp(dstreg, "result.color") == 0) {
+            if (!strcmp(dstreg, "result.color"))
+            {
                 dstreg = "ret";
                 mul_final_dest = TRUE;
             }
@@ -5982,7 +5994,8 @@ static GLuint gen_arbfp_ffp_shader(const struct ffp_frag_settings *settings, IWi
                        srgb_sub_high, 0.0, 0.0, 0.0);
     }
 
-    if(ffp_clip_emul(stateblock) && settings->emul_clipplanes) shader_addline(&buffer, "KIL fragment.texcoord[7];\n");
+    if (ffp_clip_emul(&stateblock->state) && settings->emul_clipplanes)
+        shader_addline(&buffer, "KIL fragment.texcoord[7];\n");
 
     /* Generate texture sampling instructions) */
     for(stage = 0; stage < MAX_TEXTURES && settings->op[stage].cop != WINED3DTOP_DISABLE; stage++) {
@@ -6060,11 +6073,11 @@ static GLuint gen_arbfp_ffp_shader(const struct ffp_frag_settings *settings, IWi
     }
 
     /* Generate the main shader */
-    for(stage = 0; stage < MAX_TEXTURES; stage++) {
-        if(settings->op[stage].cop == WINED3DTOP_DISABLE) {
-            if(stage == 0) {
-                final_combiner_src = "fragment.color.primary";
-            }
+    for (stage = 0; stage < MAX_TEXTURES; ++stage)
+    {
+        if (settings->op[stage].cop == WINED3DTOP_DISABLE)
+        {
+            if (!stage) final_combiner_src = "fragment.color.primary";
             break;
         }
 
@@ -6091,10 +6104,11 @@ static GLuint gen_arbfp_ffp_shader(const struct ffp_frag_settings *settings, IWi
             gen_ffp_instr(&buffer, stage, TRUE, FALSE, settings->op[stage].dst,
                           settings->op[stage].cop, settings->op[stage].carg0,
                           settings->op[stage].carg1, settings->op[stage].carg2);
-            if(stage == 0) {
+            if (!stage)
                 shader_addline(&buffer, "MOV ret.w, fragment.color.primary.w;\n");
-            }
-        } else if(op_equal) {
+        }
+        else if (op_equal)
+        {
             gen_ffp_instr(&buffer, stage, TRUE, TRUE, settings->op[stage].dst,
                           settings->op[stage].cop, settings->op[stage].carg0,
                           settings->op[stage].carg1, settings->op[stage].carg2);
@@ -6146,18 +6160,19 @@ static GLuint gen_arbfp_ffp_shader(const struct ffp_frag_settings *settings, IWi
     return ret;
 }
 
-static void fragment_prog_arbfp(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void fragment_prog_arbfp(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
     IWineD3DDeviceImpl *device = stateblock->device;
     struct shader_arb_priv *priv = device->fragment_priv;
-    BOOL use_pshader = use_ps(stateblock);
-    BOOL use_vshader = use_vs(stateblock);
+    BOOL use_vshader = use_vs(state);
+    BOOL use_pshader = use_ps(state);
     struct ffp_frag_settings settings;
     const struct arbfp_ffp_desc *desc;
     unsigned int i;
 
-    TRACE("state %#x, stateblock %p, context %p\n", state, stateblock, context);
+    TRACE("state_id %#x, stateblock %p, context %p\n", state_id, stateblock, context);
 
     if(isStateDirty(context, STATE_RENDER(WINED3DRS_FOGENABLE))) {
         if(!use_pshader && device->shader_backend == &arb_program_shader_backend && context->last_was_pshader) {
@@ -6243,27 +6258,31 @@ static void fragment_prog_arbfp(DWORD state, IWineD3DStateBlockImpl *stateblock,
  * is that changing the fog start and fog end(which links to FOGENABLE in vertex) results in the
  * fragment_prog_arbfp function being called because FOGENABLE is dirty, which calls this function here
  */
-static void state_arbfp_fog(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void state_arbfp_fog(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
+    const struct wined3d_state *state = &stateblock->state;
     enum fogsource new_source;
 
-    TRACE("state %#x, stateblock %p, context %p\n", state, stateblock, context);
+    TRACE("state_id %#x, stateblock %p, context %p\n", state_id, stateblock, context);
 
     if(!isStateDirty(context, STATE_PIXELSHADER)) {
-        fragment_prog_arbfp(state, stateblock, context);
+        fragment_prog_arbfp(state_id, stateblock, context);
     }
 
-    if(!stateblock->renderState[WINED3DRS_FOGENABLE]) return;
+    if (!state->render_states[WINED3DRS_FOGENABLE]) return;
 
-    if(stateblock->renderState[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE) {
-        if(use_vs(stateblock)) {
+    if (state->render_states[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE)
+    {
+        if (use_vs(state))
+        {
             new_source = FOGSOURCE_VS;
-        } else {
-            if(stateblock->renderState[WINED3DRS_FOGVERTEXMODE] == WINED3DFOG_NONE || context->last_was_rhw) {
+        }
+        else
+        {
+            if (state->render_states[WINED3DRS_FOGVERTEXMODE] == WINED3DFOG_NONE || context->last_was_rhw)
                 new_source = FOGSOURCE_COORD;
-            } else {
+            else
                 new_source = FOGSOURCE_FFP;
-            }
         }
     } else {
         new_source = FOGSOURCE_FFP;
@@ -6981,15 +7000,15 @@ static HRESULT arbfp_blit_set(IWineD3DDevice *iface, IWineD3DSurfaceImpl *surfac
     GLenum shader;
     IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *) iface;
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    float size[4] = {surface->pow2Width, surface->pow2Height, 1, 1};
+    float size[4] = {(float) surface->pow2Width, (float) surface->pow2Height, 1.0f, 1.0f};
     struct arbfp_blit_priv *priv = device->blit_priv;
     enum complex_fixup fixup;
     GLenum textype = surface->texture_target;
 
-    if (!is_complex_fixup(surface->resource.format_desc->color_fixup))
+    if (!is_complex_fixup(surface->resource.format->color_fixup))
     {
         TRACE("Fixup:\n");
-        dump_color_fixup_desc(surface->resource.format_desc->color_fixup);
+        dump_color_fixup_desc(surface->resource.format->color_fixup);
         /* Don't bother setting up a shader for unconverted formats */
         ENTER_GL();
         glEnable(textype);
@@ -6998,7 +7017,7 @@ static HRESULT arbfp_blit_set(IWineD3DDevice *iface, IWineD3DSurfaceImpl *surfac
         return WINED3D_OK;
     }
 
-    fixup = get_complex_fixup(surface->resource.format_desc->color_fixup);
+    fixup = get_complex_fixup(surface->resource.format->color_fixup);
 
     switch(fixup)
     {
@@ -7068,10 +7087,8 @@ static void arbfp_blit_unset(IWineD3DDevice *iface) {
 }
 
 static BOOL arbfp_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_operation blit_op,
-                                 const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool,
-                                 const struct wined3d_format_desc *src_format_desc,
-                                 const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool,
-                                 const struct wined3d_format_desc *dst_format_desc)
+        const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool, const struct wined3d_format *src_format,
+        const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool, const struct wined3d_format *dst_format)
 {
     enum complex_fixup src_fixup;
 
@@ -7081,27 +7098,27 @@ static BOOL arbfp_blit_supported(const struct wined3d_gl_info *gl_info, enum bli
         return FALSE;
     }
 
-    src_fixup = get_complex_fixup(src_format_desc->color_fixup);
+    src_fixup = get_complex_fixup(src_format->color_fixup);
     if (TRACE_ON(d3d_shader) && TRACE_ON(d3d))
     {
         TRACE("Checking support for fixup:\n");
-        dump_color_fixup_desc(src_format_desc->color_fixup);
+        dump_color_fixup_desc(src_format->color_fixup);
     }
 
-    if (!is_identity_fixup(dst_format_desc->color_fixup))
+    if (!is_identity_fixup(dst_format->color_fixup))
     {
         TRACE("Destination fixups are not supported\n");
         return FALSE;
     }
 
-    if (is_identity_fixup(src_format_desc->color_fixup))
+    if (is_identity_fixup(src_format->color_fixup))
     {
         TRACE("[OK]\n");
         return TRUE;
     }
 
      /* We only support YUV conversions. */
-    if (!is_complex_fixup(src_format_desc->color_fixup))
+    if (!is_complex_fixup(src_format->color_fixup))
     {
         TRACE("[FAILED]\n");
         return FALSE;
@@ -7143,7 +7160,8 @@ HRESULT arbfp_blit_surface(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *src_
      * Also beware of the origin difference(top left vs bottom left).
      * Also beware that the front buffer's surface size is screen width x screen height,
      * whereas the real gl drawable size is the size of the window. */
-    dst_swapchain = (dst_surface->Flags & SFLAG_SWAPCHAIN) ? (IWineD3DSwapChainImpl *)dst_surface->container : NULL;
+    dst_swapchain = dst_surface->container.type == WINED3D_CONTAINER_SWAPCHAIN
+            ? dst_surface->container.u.swapchain : NULL;
     if (dst_swapchain && dst_surface == dst_swapchain->front_buffer)
         surface_translate_frontbuffer_coords(dst_surface, context->win_handle, &dst_rect);
 
@@ -7166,11 +7184,13 @@ HRESULT arbfp_blit_surface(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *src_
 
     context_release(context);
 
-    IWineD3DSurface_ModifyLocation((IWineD3DSurface *)dst_surface, SFLAG_INDRAWABLE, TRUE);
+    surface_modify_location(dst_surface, SFLAG_INDRAWABLE, TRUE);
     return WINED3D_OK;
 }
 
-static HRESULT arbfp_blit_color_fill(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *dst_surface, const RECT *dst_rect, DWORD fill_color)
+/* Do not call while under the GL lock. */
+static HRESULT arbfp_blit_color_fill(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *dst_surface,
+        const RECT *dst_rect, const WINED3DCOLORVALUE *color)
 {
     FIXME("Color filling not implemented by arbfp_blit\n");
     return WINED3DERR_INVALIDCALL;
index 993ece0..35838e1 100644 (file)
@@ -273,11 +273,7 @@ static GLuint register_for_arg(DWORD arg, const struct wined3d_gl_info *gl_info,
              * instruction writing to reg0. Afterwards texture0 is not used any longer.
              * If we're reading from current
              */
-            if(stage == 0) {
-                ret = GL_PRIMARY_COLOR;
-            } else {
-                ret = GL_REG_0_ATI;
-            }
+            ret = stage ? GL_REG_0_ATI : GL_PRIMARY_COLOR;
             break;
 
         case WINED3DTA_TEXTURE:
@@ -517,9 +513,12 @@ static GLuint gen_ati_shader(const struct texture_stage_op op[MAX_TEXTURES], con
     }
 
     /* Pass 4: Generate the arithmetic instructions */
-    for(stage = 0; stage < MAX_TEXTURES; stage++) {
-        if(op[stage].cop == WINED3DTOP_DISABLE) {
-            if(stage == 0) {
+    for (stage = 0; stage < MAX_TEXTURES; ++stage)
+    {
+        if (op[stage].cop == WINED3DTOP_DISABLE)
+        {
+            if (!stage)
+            {
                 /* Handle complete texture disabling gracefully */
                 wrap_op1(gl_info, GL_MOV_ATI, GL_REG_0_ATI, GL_NONE, GL_NONE,
                          GL_PRIMARY_COLOR, GL_NONE, GL_NONE);
@@ -679,7 +678,8 @@ static GLuint gen_ati_shader(const struct texture_stage_op op[MAX_TEXTURES], con
         switch(op[stage].aop) {
             case WINED3DTOP_DISABLE:
                 /* Get the primary color to the output if on stage 0, otherwise leave register 0 untouched */
-                if(stage == 0) {
+                if (!stage)
+                {
                     wrap_op1(gl_info, GL_MOV_ATI, GL_REG_0_ATI, GL_ALPHA, GL_NONE,
                              GL_PRIMARY_COLOR, GL_NONE, GL_NONE);
                 }
@@ -838,7 +838,7 @@ static void set_tex_op_atifs(DWORD state, IWineD3DStateBlockImpl *stateblock, st
         {
             GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
             checkGLcall("glActiveTextureARB");
-            texture_activate_dimensions(i, stateblock, context);
+            texture_activate_dimensions(stateblock->state.textures[i], gl_info);
         }
     }
 
@@ -849,7 +849,7 @@ static void state_texfactor_atifs(DWORD state, IWineD3DStateBlockImpl *statebloc
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
     float col[4];
-    D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_TEXTUREFACTOR], col);
+    D3DCOLORTOGLFLOAT4(stateblock->state.render_states[WINED3DRS_TEXTUREFACTOR], col);
 
     GL_EXTCALL(glSetFragmentShaderConstantATI(ATI_FFP_CONST_TFACTOR, col));
     checkGLcall("glSetFragmentShaderConstantATI(ATI_FFP_CONST_TFACTOR, col)");
@@ -861,10 +861,10 @@ static void set_bumpmat(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
     const struct wined3d_gl_info *gl_info = context->gl_info;
     float mat[2][2];
 
-    mat[0][0] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT00]);
-    mat[1][0] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT01]);
-    mat[0][1] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT10]);
-    mat[1][1] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT11]);
+    mat[0][0] = *((float *)&stateblock->state.texture_states[stage][WINED3DTSS_BUMPENVMAT00]);
+    mat[1][0] = *((float *)&stateblock->state.texture_states[stage][WINED3DTSS_BUMPENVMAT01]);
+    mat[0][1] = *((float *)&stateblock->state.texture_states[stage][WINED3DTSS_BUMPENVMAT10]);
+    mat[1][1] = *((float *)&stateblock->state.texture_states[stage][WINED3DTSS_BUMPENVMAT11]);
     /* GL_ATI_fragment_shader allows only constants from 0.0 to 1.0, but the bumpmat
      * constants can be in any range. While they should stay between [-1.0 and 1.0] because
      * Shader Model 1.x pixel shaders are clamped to that range negative values are used occasionally,
@@ -887,12 +887,13 @@ static void textransform(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
     }
 }
 
-static void atifs_apply_pixelshader(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void atifs_apply_pixelshader(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
+    const struct wined3d_state *state = &stateblock->state;
     IWineD3DDeviceImpl *device = stateblock->device;
-    BOOL use_vshader = use_vs(stateblock);
+    BOOL use_vshader = use_vs(state);
 
-    context->last_was_pshader = use_ps(stateblock);
+    context->last_was_pshader = use_ps(state);
     /* The ATIFS code does not support pixel shaders currently, but we have to provide a state handler
      * to call shader_select to select a vertex shader if one is applied because the vertex shader state
      * may defer calling the shader backend if the pshader state is dirty.
@@ -912,6 +913,12 @@ static void atifs_apply_pixelshader(DWORD state, IWineD3DStateBlockImpl *statebl
     }
 }
 
+static void atifs_srgbwriteenable(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+{
+    if (stateblock->state.render_states[WINED3DRS_SRGBWRITEENABLE])
+        WARN("sRGB writes are not supported by this fragment pipe.\n");
+}
+
 static const struct StateEntryTemplate atifs_fragmentstate_template[] = {
     {STATE_RENDER(WINED3DRS_TEXTUREFACTOR),               { STATE_RENDER(WINED3DRS_TEXTUREFACTOR),              state_texfactor_atifs   }, WINED3D_GL_EXT_NONE             },
     {STATE_RENDER(WINED3DRS_FOGCOLOR),                    { STATE_RENDER(WINED3DRS_FOGCOLOR),                   state_fogcolor          }, WINED3D_GL_EXT_NONE             },
@@ -921,6 +928,7 @@ static const struct StateEntryTemplate atifs_fragmentstate_template[] = {
     {STATE_RENDER(WINED3DRS_FOGVERTEXMODE),               { STATE_RENDER(WINED3DRS_FOGENABLE),                  NULL                    }, WINED3D_GL_EXT_NONE             },
     {STATE_RENDER(WINED3DRS_FOGSTART),                    { STATE_RENDER(WINED3DRS_FOGSTART),                   state_fogstartend       }, WINED3D_GL_EXT_NONE             },
     {STATE_RENDER(WINED3DRS_FOGEND),                      { STATE_RENDER(WINED3DRS_FOGSTART),                   NULL                    }, WINED3D_GL_EXT_NONE             },
+    {STATE_RENDER(WINED3DRS_SRGBWRITEENABLE),             { STATE_RENDER(WINED3DRS_SRGBWRITEENABLE),            atifs_srgbwriteenable   }, WINED3D_GL_EXT_NONE             },
     {STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP),           { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP),          set_tex_op_atifs        }, WINED3D_GL_EXT_NONE             },
     {STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG1),         { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP),          NULL                    }, WINED3D_GL_EXT_NONE             },
     {STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG2),         { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP),          NULL                    }, WINED3D_GL_EXT_NONE             },
index deab4fb..bf3b4d4 100644 (file)
@@ -29,13 +29,13 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d_texture);
 
 HRESULT basetexture_init(IWineD3DBaseTextureImpl *texture, UINT layer_count, UINT level_count,
         WINED3DRESOURCETYPE resource_type, IWineD3DDeviceImpl *device, UINT size, DWORD usage,
-        const struct wined3d_format_desc *format_desc, WINED3DPOOL pool, IUnknown *parent,
+        const struct wined3d_format *format, WINED3DPOOL pool, void *parent,
         const struct wined3d_parent_ops *parent_ops)
 {
     HRESULT hr;
 
     hr = resource_init((IWineD3DResource *)texture, resource_type, device,
-            size, usage, format_desc, pool, parent, parent_ops);
+            size, usage, format, pool, parent, parent_ops);
     if (FAILED(hr))
     {
         WARN("Failed to initialize resource, returning %#x\n", hr);
@@ -60,7 +60,7 @@ HRESULT basetexture_init(IWineD3DBaseTextureImpl *texture, UINT layer_count, UIN
     texture->baseTexture.is_srgb = FALSE;
     texture->baseTexture.pow2Matrix_identity = TRUE;
 
-    if (texture->resource.format_desc->Flags & WINED3DFMT_FLAG_FILTERING)
+    if (texture->resource.format->Flags & WINED3DFMT_FLAG_FILTERING)
     {
         texture->baseTexture.minMipLookup = minMipLookup;
         texture->baseTexture.magLookup = magLookup;
@@ -129,6 +129,8 @@ void basetexture_unload(IWineD3DBaseTexture *iface)
 
     This->baseTexture.texture_rgb.dirty = TRUE;
     This->baseTexture.texture_srgb.dirty = TRUE;
+
+    resource_unload((IWineD3DResourceImpl *)This);
 }
 
 DWORD basetexture_set_lod(IWineD3DBaseTexture *iface, DWORD LODNew)
@@ -182,7 +184,7 @@ HRESULT basetexture_set_autogen_filter_type(IWineD3DBaseTexture *iface, WINED3DT
 {
   IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
   IWineD3DDeviceImpl *device = This->resource.device;
-  UINT textureDimensions = IWineD3DBaseTexture_GetTextureDimensions(iface);
+  GLenum textureDimensions = This->baseTexture.target;
 
   if (!(This->resource.usage & WINED3DUSAGE_AUTOGENMIPMAP)) {
       TRACE("(%p) : returning invalid call\n", This);
@@ -260,7 +262,7 @@ HRESULT basetexture_bind(IWineD3DBaseTexture *iface, BOOL srgb, BOOL *set_surfac
 {
     IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
     HRESULT hr = WINED3D_OK;
-    UINT textureDimensions;
+    GLenum textureDimensions;
     BOOL isNewTexture = FALSE;
     struct gl_texture *gl_tex;
     TRACE("(%p) : About to bind texture\n", This);
@@ -272,10 +274,11 @@ HRESULT basetexture_bind(IWineD3DBaseTexture *iface, BOOL srgb, BOOL *set_surfac
         gl_tex = &This->baseTexture.texture_rgb;
     }
 
-    textureDimensions = IWineD3DBaseTexture_GetTextureDimensions(iface);
+    textureDimensions = This->baseTexture.target;
     ENTER_GL();
     /* Generate a texture name if we don't already have one */
-    if (gl_tex->name == 0) {
+    if (!gl_tex->name)
+    {
         *set_surface_desc = TRUE;
         glGenTextures(1, &gl_tex->name);
         checkGLcall("glGenTextures");
@@ -317,7 +320,8 @@ HRESULT basetexture_bind(IWineD3DBaseTexture *iface, BOOL srgb, BOOL *set_surfac
     }
 
     /* Bind the texture */
-    if (gl_tex->name != 0) {
+    if (gl_tex->name)
+    {
         glBindTexture(textureDimensions, gl_tex->name);
         checkGLcall("glBindTexture");
         if (isNewTexture) {
@@ -385,8 +389,8 @@ void basetexture_apply_state_changes(IWineD3DBaseTexture *iface,
         const struct wined3d_gl_info *gl_info)
 {
     IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
+    GLenum textureDimensions = This->baseTexture.target;
     DWORD state;
-    GLint textureDimensions = IWineD3DBaseTexture_GetTextureDimensions(iface);
     BOOL cond_np2 = IWineD3DBaseTexture_IsCondNP2(iface);
     DWORD aniso;
     struct gl_texture *gl_tex;
@@ -518,10 +522,10 @@ void basetexture_apply_state_changes(IWineD3DBaseTexture *iface,
         gl_tex->states[WINED3DTEXSTA_MAXANISOTROPY] = aniso;
     }
 
-    if (!(This->resource.format_desc->Flags & WINED3DFMT_FLAG_SHADOW)
+    if (!(This->resource.format->Flags & WINED3DFMT_FLAG_SHADOW)
             != !gl_tex->states[WINED3DTEXSTA_SHADOW])
     {
-        if (This->resource.format_desc->Flags & WINED3DFMT_FLAG_SHADOW)
+        if (This->resource.format->Flags & WINED3DFMT_FLAG_SHADOW)
         {
             glTexParameteri(textureDimensions, GL_DEPTH_TEXTURE_MODE_ARB, GL_LUMINANCE);
             glTexParameteri(textureDimensions, GL_TEXTURE_COMPARE_MODE_ARB, GL_COMPARE_R_TO_TEXTURE_ARB);
index daece20..23b4a4a 100644 (file)
@@ -78,7 +78,7 @@ static inline void buffer_clear_dirty_areas(struct wined3d_buffer *This)
 
 static inline BOOL buffer_is_dirty(struct wined3d_buffer *This)
 {
-    return This->modified_areas != 0;
+    return !!This->modified_areas;
 }
 
 static inline BOOL buffer_is_fully_dirty(struct wined3d_buffer *This)
@@ -87,7 +87,7 @@ static inline BOOL buffer_is_fully_dirty(struct wined3d_buffer *This)
 
     for(i = 0; i < This->modified_areas; i++)
     {
-        if(This->maps[i].offset == 0 && This->maps[i].size == This->resource.size)
+        if (!This->maps[i].offset && This->maps[i].size == This->resource.size)
         {
             return TRUE;
         }
@@ -231,10 +231,10 @@ static BOOL buffer_process_converted_attribute(struct wined3d_buffer *This,
         const enum wined3d_buffer_conversion_type conversion_type,
         const struct wined3d_stream_info_element *attrib, DWORD *stride_this_run)
 {
+    DWORD offset = This->resource.device->stateBlock->state.streams[attrib->stream_idx].offset;
     DWORD attrib_size;
     BOOL ret = FALSE;
     unsigned int i;
-    DWORD offset = This->resource.device->stateBlock->streamOffset[attrib->stream_idx];
     DWORD_PTR data;
 
     /* Check for some valid situations which cause us pain. One is if the buffer is used for
@@ -245,7 +245,7 @@ static BOOL buffer_process_converted_attribute(struct wined3d_buffer *This,
     if (!attrib->stride)
     {
         FIXME("%s used with stride 0, let's hope we get the vertex stride from somewhere else\n",
-                debug_d3dformat(attrib->format_desc->format));
+                debug_d3dformat(attrib->format->id));
     }
     else if(attrib->stride != *stride_this_run && *stride_this_run)
     {
@@ -269,7 +269,7 @@ static BOOL buffer_process_converted_attribute(struct wined3d_buffer *This,
     }
 
     data = (((DWORD_PTR)attrib->data) + offset) % This->stride;
-    attrib_size = attrib->format_desc->component_count * attrib->format_desc->component_size;
+    attrib_size = attrib->format->component_count * attrib->format->component_size;
     for (i = 0; i < attrib_size; ++i)
     {
         DWORD_PTR idx = (data + i) % This->stride;
@@ -292,8 +292,8 @@ static BOOL buffer_check_attribute(struct wined3d_buffer *This, const struct win
     const struct wined3d_stream_info_element *attrib = &si->elements[attrib_idx];
     IWineD3DDeviceImpl *device = This->resource.device;
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
+    enum wined3d_format_id format;
     BOOL ret = FALSE;
-    WINED3DFORMAT format;
 
     /* Ignore attributes that do not have our vbo. After that check we can be sure that the attribute is
      * there, on nonexistent attribs the vbo is 0.
@@ -302,7 +302,7 @@ static BOOL buffer_check_attribute(struct wined3d_buffer *This, const struct win
             || attrib->buffer_object != This->buffer_object)
         return FALSE;
 
-    format = attrib->format_desc->format;
+    format = attrib->format->id;
     /* Look for newly appeared conversion */
     if (!gl_info->supported[ARB_HALF_FLOAT_VERTEX]
             && (format == WINED3DFMT_R16G16_FLOAT || format == WINED3DFMT_R16G16B16A16_FLOAT))
@@ -346,11 +346,11 @@ static UINT *find_conversion_shift(struct wined3d_buffer *This,
     ret = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(DWORD) * stride);
     for (i = 0; i < MAX_ATTRIBS; ++i)
     {
-        WINED3DFORMAT format;
+        enum wined3d_format_id format;
 
         if (!(strided->use_map & (1 << i)) || strided->elements[i].buffer_object != This->buffer_object) continue;
 
-        format = strided->elements[i].format_desc->format;
+        format = strided->elements[i].format->id;
         if (format == WINED3DFMT_R16G16_FLOAT)
         {
             shift = 4;
@@ -374,8 +374,8 @@ static UINT *find_conversion_shift(struct wined3d_buffer *This,
 
         if (shift)
         {
-            orig_type_size = strided->elements[i].format_desc->component_count
-                    * strided->elements[i].format_desc->component_size;
+            orig_type_size = strided->elements[i].format->component_count
+                    * strided->elements[i].format->component_size;
             for (j = (DWORD_PTR)strided->elements[i].data + orig_type_size; j < stride; ++j)
             {
                 ret[j] += shift;
@@ -401,6 +401,7 @@ static BOOL buffer_find_decl(struct wined3d_buffer *This)
     IWineD3DDeviceImpl *device = This->resource.device;
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
     const struct wined3d_stream_info *si = &device->strided_streams;
+    const struct wined3d_state *state = &device->stateBlock->state;
     UINT stride_this_run = 0;
     BOOL float16_used = FALSE;
     BOOL ret = FALSE;
@@ -460,14 +461,14 @@ static BOOL buffer_find_decl(struct wined3d_buffer *This)
      * conversion types depend on the semantic as well, for example a FLOAT4
      * texcoord needs no conversion while a FLOAT4 positiont needs one
      */
-    if (use_vs(device->stateBlock))
+    if (use_vs(state))
     {
         TRACE("vshader\n");
         /* If the current vertex declaration is marked for no half float conversion don't bother to
          * analyse the strided streams in depth, just set them up for no conversion. Return decl changed
          * if we used conversion before
          */
-        if (!((IWineD3DVertexDeclarationImpl *) device->stateBlock->vertexDecl)->half_float_conv_needed)
+        if (!state->vertex_declaration->half_float_conv_needed)
         {
             if (This->conversion_map)
             {
@@ -534,7 +535,7 @@ static BOOL buffer_find_decl(struct wined3d_buffer *This)
         if (float16_used) FIXME("Float16 conversion used with fixed function vertex processing\n");
     }
 
-    if (stride_this_run == 0 && This->conversion_map)
+    if (!stride_this_run && This->conversion_map)
     {
         /* Sanity test */
         if (!ret) ERR("no converted attributes found, old conversion map exists, and no declaration change?\n");
@@ -686,6 +687,7 @@ BYTE *buffer_get_sysmem(struct wined3d_buffer *This, const struct wined3d_gl_inf
     return This->resource.allocatedMemory;
 }
 
+/* Do not call while under the GL lock. */
 static void STDMETHODCALLTYPE buffer_UnLoad(IWineD3DBuffer *iface)
 {
     struct wined3d_buffer *This = (struct wined3d_buffer *)iface;
@@ -720,8 +722,11 @@ static void STDMETHODCALLTYPE buffer_UnLoad(IWineD3DBuffer *iface)
         This->conversion_stride = 0;
         This->flags &= ~WINED3D_BUFFER_HASDESC;
     }
+
+    resource_unload((IWineD3DResourceImpl *)This);
 }
 
+/* Do not call while under the GL lock. */
 static ULONG STDMETHODCALLTYPE buffer_Release(IWineD3DBuffer *iface)
 {
     struct wined3d_buffer *This = (struct wined3d_buffer *)iface;
@@ -742,10 +747,11 @@ static ULONG STDMETHODCALLTYPE buffer_Release(IWineD3DBuffer *iface)
 }
 
 /* IWineD3DBase methods */
-
-static HRESULT STDMETHODCALLTYPE buffer_GetParent(IWineD3DBuffer *iface, IUnknown **parent)
+static void * STDMETHODCALLTYPE buffer_GetParent(IWineD3DBuffer *iface)
 {
-    return resource_get_parent((IWineD3DResource *)iface, parent);
+    TRACE("iface %p.\n", iface);
+
+    return ((struct wined3d_buffer *)iface)->resource.parent;
 }
 
 /* IWineD3DResource methods */
@@ -918,6 +924,7 @@ static void buffer_direct_upload(struct wined3d_buffer *This, const struct wined
         LEAVE_GL();
 }
 
+/* Do not call while under the GL lock. */
 static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface)
 {
     struct wined3d_buffer *This = (struct wined3d_buffer *)iface;
@@ -1000,7 +1007,7 @@ static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface)
         if(!buffer_add_dirty_area(This, 0, 0))
         {
             ERR("buffer_add_dirty_area failed, this is not expected\n");
-            return;
+            goto end;
         }
         /* Avoid unfenced updates, we might overwrite more areas of the buffer than the application
          * cleared for unsynchronized updates
@@ -1342,7 +1349,7 @@ static HRESULT STDMETHODCALLTYPE buffer_Unmap(IWineD3DBuffer *iface)
      * number of Map calls, d3d returns always D3D_OK.
      * This is also needed to prevent Map from returning garbage on
      * the next call (this will happen if the lock_count is < 0). */
-    if(This->lock_count == 0)
+    if (!This->lock_count)
     {
         TRACE("Unmap called without a previous Map call!\n");
         return WINED3D_OK;
@@ -1407,7 +1414,7 @@ static HRESULT STDMETHODCALLTYPE buffer_Unmap(IWineD3DBuffer *iface)
     return WINED3D_OK;
 }
 
-static HRESULT STDMETHODCALLTYPE buffer_GetDesc(IWineD3DBuffer *iface, WINED3DBUFFER_DESC *desc)
+static void STDMETHODCALLTYPE buffer_GetDesc(IWineD3DBuffer *iface, WINED3DBUFFER_DESC *desc)
 {
     struct wined3d_buffer *This = (struct wined3d_buffer *)iface;
 
@@ -1417,8 +1424,6 @@ static HRESULT STDMETHODCALLTYPE buffer_GetDesc(IWineD3DBuffer *iface, WINED3DBU
     desc->Usage = This->resource.usage;
     desc->Pool = This->resource.pool;
     desc->Size = This->resource.size;
-
-    return WINED3D_OK;
 }
 
 static const struct IWineD3DBufferVtbl wined3d_buffer_vtbl =
@@ -1445,12 +1450,12 @@ static const struct IWineD3DBufferVtbl wined3d_buffer_vtbl =
 };
 
 HRESULT buffer_init(struct wined3d_buffer *buffer, IWineD3DDeviceImpl *device,
-        UINT size, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool, GLenum bind_hint,
-        const char *data, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        UINT size, DWORD usage, enum wined3d_format_id format_id, WINED3DPOOL pool, GLenum bind_hint,
+        const char *data, void *parent, const struct wined3d_parent_ops *parent_ops)
 {
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, &device->adapter->gl_info);
-    HRESULT hr;
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
+    const struct wined3d_format *format = wined3d_get_format(gl_info, format_id);
+    HRESULT hr;
     BOOL dynamic_buffer_ok;
 
     if (!size)
@@ -1462,7 +1467,7 @@ HRESULT buffer_init(struct wined3d_buffer *buffer, IWineD3DDeviceImpl *device,
     buffer->vtbl = &wined3d_buffer_vtbl;
 
     hr = resource_init((IWineD3DResource *)buffer, WINED3DRTYPE_BUFFER,
-            device, size, usage, format_desc, pool, parent, parent_ops);
+            device, size, usage, format, pool, parent, parent_ops);
     if (FAILED(hr))
     {
         WARN("Failed to initialize resource, hr %#x\n", hr);
@@ -1471,7 +1476,7 @@ HRESULT buffer_init(struct wined3d_buffer *buffer, IWineD3DDeviceImpl *device,
     buffer->buffer_type_hint = bind_hint;
 
     TRACE("size %#x, usage %#x, format %s, memory @ %p, iface @ %p.\n", buffer->resource.size, buffer->resource.usage,
-            debug_d3dformat(buffer->resource.format_desc->format), buffer->resource.allocatedMemory, buffer);
+            debug_d3dformat(buffer->resource.format->id), buffer->resource.allocatedMemory, buffer);
 
     /* GL_ARB_map_buffer_range is disabled for now due to numerous bugs and no gains */
     dynamic_buffer_ok = gl_info->supported[APPLE_FLUSH_BUFFER_RANGE];
index 8be3a95..48ce06f 100644 (file)
@@ -33,7 +33,6 @@ static HRESULT WINAPI IWineD3DClipperImpl_QueryInterface(IWineD3DClipper *iface,
     TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
 
     if (IsEqualGUID(riid, &IID_IWineD3DClipper)
-            || IsEqualGUID(riid, &IID_IWineD3DBase)
             || IsEqualGUID(riid, &IID_IUnknown))
     {
         IUnknown_AddRef(iface);
@@ -64,22 +63,9 @@ static ULONG WINAPI IWineD3DClipperImpl_Release(IWineD3DClipper *iface)
 
     TRACE("(%p)->() decrementing from %u.\n", This, ref + 1);
 
-    if (ref == 0)
-    {
-        HeapFree(GetProcessHeap(), 0, This);
-        return 0;
-    }
-    else return ref;
-}
+    if (!ref) HeapFree(GetProcessHeap(), 0, This);
 
-static HRESULT WINAPI IWineD3DClipperImpl_GetParent(IWineD3DClipper *iface, IUnknown **Parent)
-{
-    IWineD3DClipperImpl *This = (IWineD3DClipperImpl *)iface;
-    TRACE("(%p)->(%p)\n", This, Parent);
-
-    *Parent = This->Parent;
-    IUnknown_AddRef(*Parent);
-    return WINED3D_OK;
+    return ref;
 }
 
 static HRESULT WINAPI IWineD3DClipperImpl_SetHwnd(IWineD3DClipper *iface, DWORD Flags, HWND hWnd)
@@ -146,7 +132,7 @@ static HRESULT WINAPI IWineD3DClipperImpl_SetClipList(IWineD3DClipper *iface, co
 {
     static int warned = 0;
 
-    if (warned++ < 10 || rgn == NULL)
+    if (warned++ < 10 || !rgn)
         FIXME("iface %p, region %p, flags %#x stub!\n", iface, rgn, Flags);
 
     return WINED3D_OK;
@@ -176,7 +162,6 @@ static const IWineD3DClipperVtbl IWineD3DClipper_Vtbl =
     IWineD3DClipperImpl_QueryInterface,
     IWineD3DClipperImpl_AddRef,
     IWineD3DClipperImpl_Release,
-    IWineD3DClipperImpl_GetParent,
     IWineD3DClipperImpl_GetClipList,
     IWineD3DClipperImpl_GetHwnd,
     IWineD3DClipperImpl_IsClipListChanged,
@@ -184,11 +169,12 @@ static const IWineD3DClipperVtbl IWineD3DClipper_Vtbl =
     IWineD3DClipperImpl_SetHwnd
 };
 
-IWineD3DClipper* WINAPI WineDirect3DCreateClipper(IUnknown *Parent)
+IWineD3DClipper * WINAPI WineDirect3DCreateClipper(void)
 {
     IWineD3DClipperImpl *obj;
 
-    TRACE("Creating clipper, parent %p\n", Parent);
+    TRACE("\n");
+
     obj = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*obj));
     if(!obj)
     {
@@ -197,7 +183,6 @@ IWineD3DClipper* WINAPI WineDirect3DCreateClipper(IUnknown *Parent)
     }
 
     obj->lpVtbl = &IWineD3DClipper_Vtbl;
-    obj->Parent = Parent;
 
     IWineD3DClipper_AddRef((IWineD3DClipper *)obj);
     return (IWineD3DClipper *) obj;
index 5304af2..6f9d9d7 100644 (file)
@@ -112,29 +112,44 @@ static void context_destroy_fbo(struct wined3d_context *context, GLuint *fbo)
 }
 
 /* GL locking is done by the caller */
-static void context_apply_attachment_filter_states(IWineD3DSurfaceImpl *surface)
+static void context_apply_attachment_filter_states(IWineD3DSurfaceImpl *surface, DWORD location)
 {
-    IWineD3DBaseTextureImpl *texture_impl;
-
     /* Update base texture states array */
-    if (SUCCEEDED(IWineD3DSurface_GetContainer((IWineD3DSurface *)surface,
-            &IID_IWineD3DBaseTexture, (void **)&texture_impl)))
+    if (surface->container.type == WINED3D_CONTAINER_TEXTURE)
     {
+        IWineD3DBaseTextureImpl *texture_impl = surface->container.u.texture;
         IWineD3DDeviceImpl *device = surface->resource.device;
         BOOL update_minfilter = FALSE;
         BOOL update_magfilter = FALSE;
+        struct gl_texture *gl_tex;
+
+        switch (location)
+        {
+            case SFLAG_INTEXTURE:
+                gl_tex = &texture_impl->baseTexture.texture_rgb;
+                break;
+
+            case SFLAG_INSRGBTEX:
+                gl_tex = &texture_impl->baseTexture.texture_srgb;
+                break;
+
+            default:
+                ERR("Unsupported location %s (%#x).\n", debug_surflocation(location), location);
+                IWineD3DBaseTexture_Release((IWineD3DBaseTexture *)texture_impl);
+                return;
+        }
 
-        if (texture_impl->baseTexture.texture_rgb.states[WINED3DTEXSTA_MINFILTER] != WINED3DTEXF_POINT
-            || texture_impl->baseTexture.texture_rgb.states[WINED3DTEXSTA_MIPFILTER] != WINED3DTEXF_NONE)
+        if (gl_tex->states[WINED3DTEXSTA_MINFILTER] != WINED3DTEXF_POINT
+            || gl_tex->states[WINED3DTEXSTA_MIPFILTER] != WINED3DTEXF_NONE)
         {
-            texture_impl->baseTexture.texture_rgb.states[WINED3DTEXSTA_MINFILTER] = WINED3DTEXF_POINT;
-            texture_impl->baseTexture.texture_rgb.states[WINED3DTEXSTA_MIPFILTER] = WINED3DTEXF_NONE;
+            gl_tex->states[WINED3DTEXSTA_MINFILTER] = WINED3DTEXF_POINT;
+            gl_tex->states[WINED3DTEXSTA_MIPFILTER] = WINED3DTEXF_NONE;
             update_minfilter = TRUE;
         }
 
-        if (texture_impl->baseTexture.texture_rgb.states[WINED3DTEXSTA_MAGFILTER] != WINED3DTEXF_POINT)
+        if (gl_tex->states[WINED3DTEXSTA_MAGFILTER] != WINED3DTEXF_POINT)
         {
-            texture_impl->baseTexture.texture_rgb.states[WINED3DTEXSTA_MAGFILTER] = WINED3DTEXF_POINT;
+            gl_tex->states[WINED3DTEXSTA_MAGFILTER] = WINED3DTEXF_POINT;
             update_magfilter = TRUE;
         }
 
@@ -144,8 +159,6 @@ static void context_apply_attachment_filter_states(IWineD3DSurfaceImpl *surface)
             IWineD3DDeviceImpl_MarkStateDirty(device, STATE_SAMPLER(texture_impl->baseTexture.sampler));
         }
 
-        IWineD3DBaseTexture_Release((IWineD3DBaseTexture *)texture_impl);
-
         if (update_minfilter || update_magfilter)
         {
             GLenum target, bind_target;
@@ -168,7 +181,7 @@ static void context_apply_attachment_filter_states(IWineD3DSurfaceImpl *surface)
                 glGetIntegerv(GL_TEXTURE_BINDING_CUBE_MAP_ARB, &old_binding);
             }
 
-            glBindTexture(bind_target, surface->texture_name);
+            glBindTexture(bind_target, gl_tex->name);
             if (update_minfilter) glTexParameteri(bind_target, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
             if (update_magfilter) glTexParameteri(bind_target, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
             glBindTexture(bind_target, old_binding);
@@ -188,7 +201,7 @@ void context_attach_depth_stencil_fbo(struct wined3d_context *context,
 
     if (depth_stencil)
     {
-        DWORD format_flags = depth_stencil->resource.format_desc->Flags;
+        DWORD format_flags = depth_stencil->resource.format->Flags;
 
         if (use_render_buffer && depth_stencil->current_renderbuffer)
         {
@@ -209,7 +222,7 @@ void context_attach_depth_stencil_fbo(struct wined3d_context *context,
         else
         {
             surface_prepare_texture(depth_stencil, gl_info, FALSE);
-            context_apply_attachment_filter_states(depth_stencil);
+            context_apply_attachment_filter_states(depth_stencil, SFLAG_INTEXTURE);
 
             if (format_flags & WINED3DFMT_FLAG_DEPTH)
             {
@@ -252,7 +265,7 @@ void context_attach_depth_stencil_fbo(struct wined3d_context *context,
 
 /* GL locking is done by the caller */
 static void context_attach_surface_fbo(const struct wined3d_context *context,
-        GLenum fbo_target, DWORD idx, IWineD3DSurfaceImpl *surface)
+        GLenum fbo_target, DWORD idx, IWineD3DSurfaceImpl *surface, DWORD location)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
 
@@ -260,11 +273,26 @@ static void context_attach_surface_fbo(const struct wined3d_context *context,
 
     if (surface)
     {
-        surface_prepare_texture(surface, gl_info, FALSE);
-        context_apply_attachment_filter_states(surface);
+        switch (location)
+        {
+            case SFLAG_INTEXTURE:
+                surface_prepare_texture(surface, gl_info, FALSE);
+                context_apply_attachment_filter_states(surface, location);
+                gl_info->fbo_ops.glFramebufferTexture2D(fbo_target, GL_COLOR_ATTACHMENT0 + idx,
+                        surface->texture_target, surface->texture_name, surface->texture_level);
+                break;
+
+            case SFLAG_INSRGBTEX:
+                surface_prepare_texture(surface, gl_info, TRUE);
+                context_apply_attachment_filter_states(surface, location);
+                gl_info->fbo_ops.glFramebufferTexture2D(fbo_target, GL_COLOR_ATTACHMENT0 + idx,
+                        surface->texture_target, surface->texture_name_srgb, surface->texture_level);
+                break;
 
-        gl_info->fbo_ops.glFramebufferTexture2D(fbo_target, GL_COLOR_ATTACHMENT0 + idx, surface->texture_target,
-                surface->texture_name, surface->texture_level);
+            default:
+                ERR("Unsupported location %s (%#x).\n", debug_surflocation(location), location);
+                break;
+        }
         checkGLcall("glFramebufferTexture2D()");
     }
     else
@@ -295,6 +323,9 @@ static void context_check_fbo_status(struct wined3d_context *context, GLenum tar
             return;
         }
 
+        FIXME("\tLocation %s (%#x).\n", debug_surflocation(context->current_fbo->location),
+                context->current_fbo->location);
+
         /* Dump the FBO attachments */
         for (i = 0; i < gl_info->limits.buffers; ++i)
         {
@@ -302,7 +333,7 @@ static void context_check_fbo_status(struct wined3d_context *context, GLenum tar
             if (attachment)
             {
                 FIXME("\tColor attachment %d: (%p) %s %ux%u\n",
-                        i, attachment, debug_d3dformat(attachment->resource.format_desc->format),
+                        i, attachment, debug_d3dformat(attachment->resource.format->id),
                         attachment->pow2Width, attachment->pow2Height);
             }
         }
@@ -310,14 +341,14 @@ static void context_check_fbo_status(struct wined3d_context *context, GLenum tar
         if (attachment)
         {
             FIXME("\tDepth attachment: (%p) %s %ux%u\n",
-                    attachment, debug_d3dformat(attachment->resource.format_desc->format),
+                    attachment, debug_d3dformat(attachment->resource.format->id),
                     attachment->pow2Width, attachment->pow2Height);
         }
     }
 }
 
 static struct fbo_entry *context_create_fbo_entry(struct wined3d_context *context,
-        IWineD3DSurfaceImpl **render_targets, IWineD3DSurfaceImpl *depth_stencil)
+        IWineD3DSurfaceImpl **render_targets, IWineD3DSurfaceImpl *depth_stencil, DWORD location)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
     struct fbo_entry *entry;
@@ -326,6 +357,7 @@ static struct fbo_entry *context_create_fbo_entry(struct wined3d_context *contex
     entry->render_targets = HeapAlloc(GetProcessHeap(), 0, gl_info->limits.buffers * sizeof(*entry->render_targets));
     memcpy(entry->render_targets, render_targets, gl_info->limits.buffers * sizeof(*entry->render_targets));
     entry->depth_stencil = depth_stencil;
+    entry->location = location;
     entry->attached = FALSE;
     entry->id = 0;
 
@@ -335,7 +367,7 @@ static struct fbo_entry *context_create_fbo_entry(struct wined3d_context *contex
 /* GL locking is done by the caller */
 static void context_reuse_fbo_entry(struct wined3d_context *context, GLenum target,
         IWineD3DSurfaceImpl **render_targets, IWineD3DSurfaceImpl *depth_stencil,
-        struct fbo_entry *entry)
+        DWORD location, struct fbo_entry *entry)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
 
@@ -344,6 +376,7 @@ static void context_reuse_fbo_entry(struct wined3d_context *context, GLenum targ
 
     memcpy(entry->render_targets, render_targets, gl_info->limits.buffers * sizeof(*entry->render_targets));
     entry->depth_stencil = depth_stencil;
+    entry->location = location;
     entry->attached = FALSE;
 }
 
@@ -364,7 +397,7 @@ static void context_destroy_fbo_entry(struct wined3d_context *context, struct fb
 
 /* GL locking is done by the caller */
 static struct fbo_entry *context_find_fbo_entry(struct wined3d_context *context, GLenum target,
-        IWineD3DSurfaceImpl **render_targets, IWineD3DSurfaceImpl *depth_stencil)
+        IWineD3DSurfaceImpl **render_targets, IWineD3DSurfaceImpl *depth_stencil, DWORD location)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
     struct fbo_entry *entry;
@@ -373,7 +406,7 @@ static struct fbo_entry *context_find_fbo_entry(struct wined3d_context *context,
     {
         if (!memcmp(entry->render_targets,
                 render_targets, gl_info->limits.buffers * sizeof(*entry->render_targets))
-                && entry->depth_stencil == depth_stencil)
+                && entry->depth_stencil == depth_stencil && entry->location == location)
         {
             list_remove(&entry->entry);
             list_add_head(&context->fbo_list, &entry->entry);
@@ -383,14 +416,14 @@ static struct fbo_entry *context_find_fbo_entry(struct wined3d_context *context,
 
     if (context->fbo_entry_count < WINED3D_MAX_FBO_ENTRIES)
     {
-        entry = context_create_fbo_entry(context, render_targets, depth_stencil);
+        entry = context_create_fbo_entry(context, render_targets, depth_stencil, location);
         list_add_head(&context->fbo_list, &entry->entry);
         ++context->fbo_entry_count;
     }
     else
     {
         entry = LIST_ENTRY(list_tail(&context->fbo_list), struct fbo_entry, entry);
-        context_reuse_fbo_entry(context, target, render_targets, depth_stencil, entry);
+        context_reuse_fbo_entry(context, target, render_targets, depth_stencil, location, entry);
         list_remove(&entry->entry);
         list_add_head(&context->fbo_list, &entry->entry);
     }
@@ -411,7 +444,7 @@ static void context_apply_fbo_entry(struct wined3d_context *context, GLenum targ
         /* Apply render targets */
         for (i = 0; i < gl_info->limits.buffers; ++i)
         {
-            context_attach_surface_fbo(context, target, i, entry->render_targets[i]);
+            context_attach_surface_fbo(context, target, i, entry->render_targets[i], entry->location);
         }
 
         /* Apply depth targets */
@@ -429,16 +462,16 @@ static void context_apply_fbo_entry(struct wined3d_context *context, GLenum targ
         for (i = 0; i < gl_info->limits.buffers; ++i)
         {
             if (entry->render_targets[i])
-                context_apply_attachment_filter_states(entry->render_targets[i]);
+                context_apply_attachment_filter_states(entry->render_targets[i], entry->location);
         }
         if (entry->depth_stencil)
-            context_apply_attachment_filter_states(entry->depth_stencil);
+            context_apply_attachment_filter_states(entry->depth_stencil, SFLAG_INTEXTURE);
     }
 }
 
 /* GL locking is done by the caller */
 static void context_apply_fbo_state(struct wined3d_context *context, GLenum target,
-        IWineD3DSurfaceImpl **render_targets, IWineD3DSurfaceImpl *depth_stencil)
+        IWineD3DSurfaceImpl **render_targets, IWineD3DSurfaceImpl *depth_stencil, DWORD location)
 {
     struct fbo_entry *entry, *entry2;
 
@@ -455,7 +488,7 @@ static void context_apply_fbo_state(struct wined3d_context *context, GLenum targ
 
     if (render_targets)
     {
-        context->current_fbo = context_find_fbo_entry(context, target, render_targets, depth_stencil);
+        context->current_fbo = context_find_fbo_entry(context, target, render_targets, depth_stencil, location);
         context_apply_fbo_entry(context, target, context->current_fbo);
     }
     else
@@ -469,16 +502,18 @@ static void context_apply_fbo_state(struct wined3d_context *context, GLenum targ
 
 /* GL locking is done by the caller */
 void context_apply_fbo_state_blit(struct wined3d_context *context, GLenum target,
-        IWineD3DSurfaceImpl *render_target, IWineD3DSurfaceImpl *depth_stencil)
+        IWineD3DSurfaceImpl *render_target, IWineD3DSurfaceImpl *depth_stencil, DWORD location)
 {
     if (surface_is_offscreen(render_target))
     {
+        UINT clear_size = (context->gl_info->limits.buffers - 1) * sizeof(*context->blit_targets);
         context->blit_targets[0] = render_target;
-        context_apply_fbo_state(context, target, context->blit_targets, depth_stencil);
+        if (clear_size) memset(&context->blit_targets[1], 0, clear_size);
+        context_apply_fbo_state(context, target, context->blit_targets, depth_stencil, location);
     }
     else
     {
-        context_apply_fbo_state(context, target, NULL, NULL);
+        context_apply_fbo_state(context, target, NULL, NULL, location);
     }
 }
 
@@ -611,50 +646,78 @@ void context_free_event_query(struct wined3d_event_query *query)
     context->free_event_queries[context->free_event_query_count++] = query->object;
 }
 
-void context_resource_released(IWineD3DDevice *iface, IWineD3DResource *resource, WINED3DRESOURCETYPE type)
+typedef void (context_fbo_entry_func_t)(struct wined3d_context *context, struct fbo_entry *entry);
+
+static void context_enum_surface_fbo_entries(IWineD3DDeviceImpl *device,
+        IWineD3DSurfaceImpl *surface, context_fbo_entry_func_t *callback)
 {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     UINT i;
 
-    if (!This->d3d_initialized) return;
-
-    switch(type)
+    for (i = 0; i < device->numContexts; ++i)
     {
-        case WINED3DRTYPE_SURFACE:
+        struct wined3d_context *context = device->contexts[i];
+        const struct wined3d_gl_info *gl_info = context->gl_info;
+        struct fbo_entry *entry, *entry2;
+
+        if (context->current_rt == surface) context->current_rt = NULL;
+
+        LIST_FOR_EACH_ENTRY_SAFE(entry, entry2, &context->fbo_list, struct fbo_entry, entry)
         {
-            for (i = 0; i < This->numContexts; ++i)
-            {
-                struct wined3d_context *context = This->contexts[i];
-                const struct wined3d_gl_info *gl_info = context->gl_info;
-                struct fbo_entry *entry, *entry2;
+            UINT j;
 
-                if (context->current_rt == (IWineD3DSurfaceImpl *)resource) context->current_rt = NULL;
+            if (entry->depth_stencil == surface)
+            {
+                callback(context, entry);
+                continue;
+            }
 
-                LIST_FOR_EACH_ENTRY_SAFE(entry, entry2, &context->fbo_list, struct fbo_entry, entry)
+            for (j = 0; j < gl_info->limits.buffers; ++j)
+            {
+                if (entry->render_targets[j] == surface)
                 {
-                    UINT j;
-
-                    if (entry->depth_stencil == (IWineD3DSurfaceImpl *)resource)
-                    {
-                        list_remove(&entry->entry);
-                        list_add_head(&context->fbo_destroy_list, &entry->entry);
-                        continue;
-                    }
-
-                    for (j = 0; j < gl_info->limits.buffers; ++j)
-                    {
-                        if (entry->render_targets[j] == (IWineD3DSurfaceImpl *)resource)
-                        {
-                            list_remove(&entry->entry);
-                            list_add_head(&context->fbo_destroy_list, &entry->entry);
-                            break;
-                        }
-                    }
+                    callback(context, entry);
+                    break;
                 }
             }
+        }
+    }
+}
 
+static void context_queue_fbo_entry_destruction(struct wined3d_context *context, struct fbo_entry *entry)
+{
+    list_remove(&entry->entry);
+    list_add_head(&context->fbo_destroy_list, &entry->entry);
+}
+
+void context_resource_released(IWineD3DDeviceImpl *device, IWineD3DResource *resource, WINED3DRESOURCETYPE type)
+{
+    if (!device->d3d_initialized) return;
+
+    switch (type)
+    {
+        case WINED3DRTYPE_SURFACE:
+            context_enum_surface_fbo_entries(device, (IWineD3DSurfaceImpl *)resource,
+                    context_queue_fbo_entry_destruction);
+            break;
+
+        default:
+            break;
+    }
+}
+
+static void context_detach_fbo_entry(struct wined3d_context *context, struct fbo_entry *entry)
+{
+    entry->attached = FALSE;
+}
+
+void context_resource_unloaded(IWineD3DDeviceImpl *device, IWineD3DResource *resource, WINED3DRESOURCETYPE type)
+{
+    switch (type)
+    {
+        case WINED3DRTYPE_SURFACE:
+            context_enum_surface_fbo_entries(device, (IWineD3DSurfaceImpl *)resource,
+                    context_detach_fbo_entry);
             break;
-        }
 
         default:
             break;
@@ -770,6 +833,7 @@ err:
     context->valid = 0;
 }
 
+/* Do not call while under the GL lock. */
 static void context_validate(struct wined3d_context *context)
 {
     HWND wnd = WindowFromDC(context->hdc);
@@ -785,6 +849,7 @@ static void context_validate(struct wined3d_context *context)
         context_update_window(context);
 }
 
+/* Do not call while under the GL lock. */
 static void context_destroy_gl_resources(struct wined3d_context *context)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
@@ -917,6 +982,7 @@ struct wined3d_context *context_get_current(void)
     return TlsGetValue(wined3d_context_tls_idx);
 }
 
+/* Do not call while under the GL lock. */
 BOOL context_set_current(struct wined3d_context *ctx)
 {
     struct wined3d_context *old = context_get_current();
@@ -1043,7 +1109,7 @@ static void Context_MarkStateDirty(struct wined3d_context *context, DWORD state,
 
 /* This function takes care of WineD3D pixel format selection. */
 static int WineD3D_ChoosePixelFormat(IWineD3DDeviceImpl *This, HDC hdc,
-        const struct wined3d_format_desc *color_format_desc, const struct wined3d_format_desc *ds_format_desc,
+        const struct wined3d_format *color_format, const struct wined3d_format *ds_format,
         BOOL auxBuffers, int numSamples, BOOL findCompatible)
 {
     int iPixelFormat=0;
@@ -1051,11 +1117,14 @@ static int WineD3D_ChoosePixelFormat(IWineD3DDeviceImpl *This, HDC hdc,
     short redBits, greenBits, blueBits, alphaBits, colorBits;
     short depthBits=0, stencilBits=0;
 
-    struct match_type {
+    static const struct
+    {
         BOOL require_aux;
         BOOL exact_alpha;
         BOOL exact_color;
-    } matches[] = {
+    }
+    matches[] =
+    {
         /* First, try without alpha match buffers. MacOS supports aux buffers only
          * on A8R8G8B8, and we prefer better offscreen rendering over an alpha match.
          * Then try without aux buffers - this is the most common cause for not
@@ -1075,17 +1144,17 @@ static int WineD3D_ChoosePixelFormat(IWineD3DDeviceImpl *This, HDC hdc,
     int nCfgs = This->adapter->nCfgs;
 
     TRACE("ColorFormat=%s, DepthStencilFormat=%s, auxBuffers=%d, numSamples=%d, findCompatible=%d\n",
-          debug_d3dformat(color_format_desc->format), debug_d3dformat(ds_format_desc->format),
+          debug_d3dformat(color_format->id), debug_d3dformat(ds_format->id),
           auxBuffers, numSamples, findCompatible);
 
-    if (!getColorBits(color_format_desc, &redBits, &greenBits, &blueBits, &alphaBits, &colorBits))
+    if (!getColorBits(color_format, &redBits, &greenBits, &blueBits, &alphaBits, &colorBits))
     {
         ERR("Unable to get color bits for format %s (%#x)!\n",
-                debug_d3dformat(color_format_desc->format), color_format_desc->format);
+                debug_d3dformat(color_format->id), color_format->id);
         return 0;
     }
 
-    getDepthStencilBits(ds_format_desc, &depthBits, &stencilBits);
+    getDepthStencilBits(ds_format, &depthBits, &stencilBits);
 
     for(matchtry = 0; matchtry < (sizeof(matches) / sizeof(matches[0])) && !iPixelFormat; matchtry++) {
         for(i=0; i<nCfgs; i++) {
@@ -1194,28 +1263,17 @@ static int WineD3D_ChoosePixelFormat(IWineD3DDeviceImpl *This, HDC hdc,
     }
 
     TRACE("Found iPixelFormat=%d for ColorFormat=%s, DepthStencilFormat=%s\n",
-            iPixelFormat, debug_d3dformat(color_format_desc->format), debug_d3dformat(ds_format_desc->format));
+            iPixelFormat, debug_d3dformat(color_format->id), debug_d3dformat(ds_format->id));
     return iPixelFormat;
 }
 
-/*****************************************************************************
- * context_create
- *
- * Creates a new context.
- *
- * * Params:
- *  This: Device to activate the context for
- *  target: Surface this context will render to
- *  win_handle: handle to the window which we are drawing to
- *  pPresentParameters: contains the pixelformats to use for onscreen rendering
- *
- *****************************************************************************/
-struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3DSurfaceImpl *target,
-        const struct wined3d_format_desc *ds_format_desc)
+/* Do not call while under the GL lock. */
+struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain,
+        IWineD3DSurfaceImpl *target, const struct wined3d_format *ds_format)
 {
     IWineD3DDeviceImpl *device = swapchain->device;
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    const struct wined3d_format_desc *color_format_desc;
+    const struct wined3d_format *color_format;
     struct wined3d_context *ret;
     PIXELFORMATDESCRIPTOR pfd;
     BOOL auxBuffers = FALSE;
@@ -1241,7 +1299,7 @@ struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3
         goto out;
     }
 
-    color_format_desc = target->resource.format_desc;
+    color_format = target->resource.format;
 
     /* In case of ORM_BACKBUFFER, make sure to request an alpha component for
      * X4R4G4B4/X8R8G8B8 as we might need it for the backbuffer. */
@@ -1249,10 +1307,10 @@ struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3
     {
         auxBuffers = TRUE;
 
-        if (color_format_desc->format == WINED3DFMT_B4G4R4X4_UNORM)
-            color_format_desc = getFormatDescEntry(WINED3DFMT_B4G4R4A4_UNORM, gl_info);
-        else if (color_format_desc->format == WINED3DFMT_B8G8R8X8_UNORM)
-            color_format_desc = getFormatDescEntry(WINED3DFMT_B8G8R8A8_UNORM, gl_info);
+        if (color_format->id == WINED3DFMT_B4G4R4X4_UNORM)
+            color_format = wined3d_get_format(gl_info, WINED3DFMT_B4G4R4A4_UNORM);
+        else if (color_format->id == WINED3DFMT_B8G8R8X8_UNORM)
+            color_format = wined3d_get_format(gl_info, WINED3DFMT_B8G8R8A8_UNORM);
     }
 
     /* DirectDraw supports 8bit paletted render targets and these are used by
@@ -1261,8 +1319,8 @@ struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3
      * conversion (ab)uses the alpha component for storing the palette index.
      * For this reason we require a format with 8bit alpha, so request
      * A8R8G8B8. */
-    if (color_format_desc->format == WINED3DFMT_P8_UINT)
-        color_format_desc = getFormatDescEntry(WINED3DFMT_B8G8R8A8_UNORM, gl_info);
+    if (color_format->id == WINED3DFMT_P8_UINT)
+        color_format = wined3d_get_format(gl_info, WINED3DFMT_B8G8R8A8_UNORM);
 
     /* D3D only allows multisampling when SwapEffect is set to WINED3DSWAPEFFECT_DISCARD. */
     if (swapchain->presentParms.MultiSampleType && (swapchain->presentParms.SwapEffect == WINED3DSWAPEFFECT_DISCARD))
@@ -1277,14 +1335,14 @@ struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3
     }
 
     /* Try to find a pixel format which matches our requirements. */
-    pixel_format = WineD3D_ChoosePixelFormat(device, hdc, color_format_desc, ds_format_desc,
+    pixel_format = WineD3D_ChoosePixelFormat(device, hdc, color_format, ds_format,
             auxBuffers, numSamples, FALSE /* findCompatible */);
 
     /* Try to locate a compatible format if we weren't able to find anything. */
     if (!pixel_format)
     {
         TRACE("Trying to locate a compatible pixel format because an exact match failed.\n");
-        pixel_format = WineD3D_ChoosePixelFormat(device, hdc, color_format_desc, ds_format_desc,
+        pixel_format = WineD3D_ChoosePixelFormat(device, hdc, color_format, ds_format,
                 auxBuffers, 0 /* numSamples */, TRUE /* findCompatible */);
     }
 
@@ -1369,6 +1427,10 @@ struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3
             gl_info->limits.buffers * sizeof(*ret->blit_targets));
     if (!ret->blit_targets) goto out;
 
+    ret->draw_buffers = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
+            gl_info->limits.buffers * sizeof(*ret->draw_buffers));
+    if (!ret->draw_buffers) goto out;
+
     ret->free_occlusion_query_size = 4;
     ret->free_occlusion_queries = HeapAlloc(GetProcessHeap(), 0,
             ret->free_occlusion_query_size * sizeof(*ret->free_occlusion_queries));
@@ -1482,6 +1544,23 @@ struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3
         checkGLcall("glTexEnvi(GL_POINT_SPRITE_ARB, GL_COORD_REPLACE_ARB, GL_TRUE)");
     }
 
+    if (gl_info->supported[WINED3D_GL_VERSION_2_0])
+    {
+        /* Windows doesn't support to query the glPointParameteri function pointer, so use the
+         * NV_POINT_SPRITE extension.
+         */
+        if (glPointParameteri)
+        {
+            glPointParameteri(GL_POINT_SPRITE_COORD_ORIGIN, GL_UPPER_LEFT);
+            checkGLcall("glPointParameteri(GL_POINT_SPRITE_COORD_ORIGIN, GL_UPPER_LEFT)");
+        }
+        else if (gl_info->supported[NV_POINT_SPRITE])
+        {
+            GL_EXTCALL(glPointParameteriNV(GL_POINT_SPRITE_COORD_ORIGIN, GL_UPPER_LEFT));
+            checkGLcall("glPointParameteriNV(GL_POINT_SPRITE_COORD_ORIGIN, GL_UPPER_LEFT)");
+        }
+    }
+
     if (gl_info->supported[ARB_PROVOKING_VERTEX])
     {
         GL_EXTCALL(glProvokingVertex(GL_FIRST_VERTEX_CONVENTION));
@@ -1502,6 +1581,7 @@ struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3
 out:
     HeapFree(GetProcessHeap(), 0, ret->free_event_queries);
     HeapFree(GetProcessHeap(), 0, ret->free_occlusion_queries);
+    HeapFree(GetProcessHeap(), 0, ret->draw_buffers);
     HeapFree(GetProcessHeap(), 0, ret->blit_targets);
     HeapFree(GetProcessHeap(), 0, ret->pshader_const_dirty);
     HeapFree(GetProcessHeap(), 0, ret->vshader_const_dirty);
@@ -1509,16 +1589,7 @@ out:
     return NULL;
 }
 
-/*****************************************************************************
- * context_destroy
- *
- * Destroys a wined3d context
- *
- * Params:
- *  This: Device to activate the context for
- *  context: Context to destroy
- *
- *****************************************************************************/
+/* Do not call while under the GL lock. */
 void context_destroy(IWineD3DDeviceImpl *This, struct wined3d_context *context)
 {
     BOOL destroy;
@@ -1537,6 +1608,7 @@ void context_destroy(IWineD3DDeviceImpl *This, struct wined3d_context *context)
         destroy = FALSE;
     }
 
+    HeapFree(GetProcessHeap(), 0, context->draw_buffers);
     HeapFree(GetProcessHeap(), 0, context->blit_targets);
     HeapFree(GetProcessHeap(), 0, context->vshader_const_dirty);
     HeapFree(GetProcessHeap(), 0, context->pshader_const_dirty);
@@ -1794,21 +1866,9 @@ static struct wined3d_context *findThreadContextForSwapChain(IWineD3DSwapChain *
     return swapchain_create_context_for_thread(swapchain);
 }
 
-/*****************************************************************************
- * FindContext
- *
- * Finds a context for the current render target and thread
- *
- * Parameters:
- *  target: Render target to find the context for
- *  tid: Thread to activate the context for
- *
- * Returns: The needed context
- *
- *****************************************************************************/
+/* Do not call while under the GL lock. */
 static struct wined3d_context *FindContext(IWineD3DDeviceImpl *This, IWineD3DSurfaceImpl *target)
 {
-    IWineD3DSwapChain *swapchain = NULL;
     struct wined3d_context *current_context = context_get_current();
     DWORD tid = GetCurrentThreadId();
     struct wined3d_context *context;
@@ -1837,11 +1897,13 @@ static struct wined3d_context *FindContext(IWineD3DDeviceImpl *This, IWineD3DSur
         return current_context;
     }
 
-    if (target->Flags & SFLAG_SWAPCHAIN)
+    if (target->container.type == WINED3D_CONTAINER_SWAPCHAIN)
     {
+        IWineD3DSwapChain *swapchain;
+
         TRACE("Rendering onscreen\n");
 
-        swapchain = (IWineD3DSwapChain *)target->container;
+        swapchain = (IWineD3DSwapChain *)target->container.u.swapchain;
         context = findThreadContextForSwapChain(swapchain, tid);
     }
     else
@@ -1871,18 +1933,13 @@ static struct wined3d_context *FindContext(IWineD3DDeviceImpl *This, IWineD3DSur
 }
 
 /* Context activation is done by the caller. */
-static void context_apply_draw_buffer(struct wined3d_context *context, BOOL blit)
+static void context_apply_draw_buffers(struct wined3d_context *context, UINT rt_count, IWineD3DSurfaceImpl **rts)
 {
-    const struct wined3d_gl_info *gl_info = context->gl_info;
-    IWineD3DSurfaceImpl *rt = context->current_rt;
-    IWineD3DDeviceImpl *device;
-
-    device = rt->resource.device;
-    if (!surface_is_offscreen(rt))
+    if (!surface_is_offscreen(rts[0]))
     {
         ENTER_GL();
-        glDrawBuffer(surface_get_gl_buffer(rt));
-        checkGLcall("glDrawBuffers()");
+        glDrawBuffer(surface_get_gl_buffer(rts[0]));
+        checkGLcall("glDrawBuffer()");
         LEAVE_GL();
     }
     else
@@ -1890,36 +1947,31 @@ static void context_apply_draw_buffer(struct wined3d_context *context, BOOL blit
         ENTER_GL();
         if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
         {
-            if (!blit)
-            {
-                unsigned int i;
-
-                for (i = 0; i < gl_info->limits.buffers; ++i)
-                {
-                    if (device->render_targets[i])
-                        device->draw_buffers[i] = GL_COLOR_ATTACHMENT0 + i;
-                    else
-                        device->draw_buffers[i] = GL_NONE;
-                }
+            const struct wined3d_gl_info *gl_info = context->gl_info;
+            unsigned int i;
 
-                if (gl_info->supported[ARB_DRAW_BUFFERS])
-                {
-                    GL_EXTCALL(glDrawBuffersARB(gl_info->limits.buffers, device->draw_buffers));
-                    checkGLcall("glDrawBuffers()");
-                }
+            for (i = 0; i < gl_info->limits.buffers; ++i)
+            {
+                if (i < rt_count && rts[i])
+                    context->draw_buffers[i] = GL_COLOR_ATTACHMENT0 + i;
                 else
-                {
-                    glDrawBuffer(device->draw_buffers[0]);
-                    checkGLcall("glDrawBuffer()");
-                }
-            } else {
-                glDrawBuffer(GL_COLOR_ATTACHMENT0);
+                    context->draw_buffers[i] = GL_NONE;
+            }
+
+            if (gl_info->supported[ARB_DRAW_BUFFERS])
+            {
+                GL_EXTCALL(glDrawBuffersARB(gl_info->limits.buffers, context->draw_buffers));
+                checkGLcall("glDrawBuffers()");
+            }
+            else
+            {
+                glDrawBuffer(context->draw_buffers[0]);
                 checkGLcall("glDrawBuffer()");
             }
         }
         else
         {
-            glDrawBuffer(device->offscreenBuffer);
+            glDrawBuffer(rts[0]->resource.device->offscreenBuffer);
             checkGLcall("glDrawBuffer()");
         }
         LEAVE_GL();
@@ -1937,8 +1989,27 @@ void context_set_draw_buffer(struct wined3d_context *context, GLenum buffer)
 static inline void context_set_render_offscreen(struct wined3d_context *context, const struct StateEntry *StateTable,
         BOOL offscreen)
 {
+    const struct wined3d_gl_info *gl_info = context->gl_info;
+
     if (context->render_offscreen == offscreen) return;
 
+    if (gl_info->supported[WINED3D_GL_VERSION_2_0])
+    {
+        /* Windows doesn't support to query the glPointParameteri function pointer, so use the
+         * NV_POINT_SPRITE extension.
+         */
+        if (glPointParameteri)
+        {
+            glPointParameteri(GL_POINT_SPRITE_COORD_ORIGIN, offscreen ? GL_LOWER_LEFT : GL_UPPER_LEFT);
+            checkGLcall("glPointParameteri(GL_POINT_SPRITE_COORD_ORIGIN, ...)");
+        }
+        else if (gl_info->supported[NV_POINT_SPRITE])
+        {
+            GL_EXTCALL(glPointParameteriNV(GL_POINT_SPRITE_COORD_ORIGIN, offscreen ? GL_LOWER_LEFT : GL_UPPER_LEFT));
+            checkGLcall("glPointParameteriNV(GL_POINT_SPRITE_COORD_ORIGIN, ...)");
+        }
+    }
+
     Context_MarkStateDirty(context, STATE_TRANSFORM(WINED3DTS_PROJECTION), StateTable);
     Context_MarkStateDirty(context, STATE_VDECL, StateTable);
     Context_MarkStateDirty(context, STATE_VIEWPORT, StateTable);
@@ -1947,8 +2018,8 @@ static inline void context_set_render_offscreen(struct wined3d_context *context,
     context->render_offscreen = offscreen;
 }
 
-static BOOL match_depth_stencil_format(const struct wined3d_format_desc *existing,
-        const struct wined3d_format_desc *required)
+static BOOL match_depth_stencil_format(const struct wined3d_format *existing,
+        const struct wined3d_format *required)
 {
     short existing_depth, existing_stencil, required_depth, required_stencil;
 
@@ -1969,10 +2040,10 @@ static void context_validate_onscreen_formats(IWineD3DDeviceImpl *device,
         struct wined3d_context *context, IWineD3DSurfaceImpl *depth_stencil)
 {
     /* Onscreen surfaces are always in a swapchain */
-    IWineD3DSwapChainImpl *swapchain = (IWineD3DSwapChainImpl *)context->current_rt->container;
+    IWineD3DSwapChainImpl *swapchain = context->current_rt->container.u.swapchain;
 
     if (context->render_offscreen || !depth_stencil) return;
-    if (match_depth_stencil_format(swapchain->ds_format, depth_stencil->resource.format_desc)) return;
+    if (match_depth_stencil_format(swapchain->ds_format, depth_stencil->resource.format)) return;
 
     /* TODO: If the requested format would satisfy the needs of the existing one(reverse match),
      * or no onscreen depth buffer was created, the OpenGL drawable could be changed to the new
@@ -1980,7 +2051,7 @@ static void context_validate_onscreen_formats(IWineD3DDeviceImpl *device,
     WARN("Depth stencil format is not supported by WGL, rendering the backbuffer in an FBO\n");
 
     /* The currently active context is the necessary context to access the swapchain's onscreen buffers */
-    IWineD3DSurface_LoadLocation((IWineD3DSurface *)context->current_rt, SFLAG_INTEXTURE, NULL);
+    surface_load_location(context->current_rt, SFLAG_INTEXTURE, NULL);
     swapchain->render_to_fbo = TRUE;
     context_set_render_offscreen(context, device->StateTable, TRUE);
 }
@@ -1998,7 +2069,7 @@ void context_apply_blit_state(struct wined3d_context *context, IWineD3DDeviceImp
             surface_internal_preload(context->current_rt, SRGB_RGB);
 
             ENTER_GL();
-            context_apply_fbo_state_blit(context, GL_FRAMEBUFFER, context->current_rt, NULL);
+            context_apply_fbo_state_blit(context, GL_FRAMEBUFFER, context->current_rt, NULL, SFLAG_INTEXTURE);
             LEAVE_GL();
         }
         else
@@ -2013,7 +2084,7 @@ void context_apply_blit_state(struct wined3d_context *context, IWineD3DDeviceImp
 
     if (context->draw_buffer_dirty)
     {
-        context_apply_draw_buffer(context, TRUE);
+        context_apply_draw_buffers(context, 1, &context->current_rt);
         if (wined3d_settings.offscreen_rendering_mode != ORM_FBO)
             context->draw_buffer_dirty = FALSE;
     }
@@ -2023,30 +2094,40 @@ void context_apply_blit_state(struct wined3d_context *context, IWineD3DDeviceImp
 
 /* Context activation is done by the caller. */
 void context_apply_clear_state(struct wined3d_context *context, IWineD3DDeviceImpl *device,
-        IWineD3DSurfaceImpl *render_target, IWineD3DSurfaceImpl *depth_stencil)
+        UINT rt_count, IWineD3DSurfaceImpl **rts, IWineD3DSurfaceImpl *depth_stencil)
 {
     const struct StateEntry *state_table = device->StateTable;
-    GLenum buffer;
+    UINT i;
 
     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
     {
         context_validate_onscreen_formats(device, context, depth_stencil);
 
         ENTER_GL();
-        context_apply_fbo_state_blit(context, GL_FRAMEBUFFER, render_target, depth_stencil);
+
+        if (surface_is_offscreen(rts[0]))
+        {
+            for (i = 0; i < rt_count; ++i)
+            {
+                context->blit_targets[i] = rts[i];
+            }
+            while (i < context->gl_info->limits.buffers)
+            {
+                context->blit_targets[i] = NULL;
+                ++i;
+            }
+            context_apply_fbo_state(context, GL_FRAMEBUFFER, context->blit_targets, depth_stencil, SFLAG_INTEXTURE);
+        }
+        else
+        {
+            context_apply_fbo_state(context, GL_FRAMEBUFFER, NULL, NULL, SFLAG_INDRAWABLE);
+        }
+
         LEAVE_GL();
     }
 
-    if (!surface_is_offscreen(render_target))
-        buffer = surface_get_gl_buffer(render_target);
-    else if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
-        buffer = GL_COLOR_ATTACHMENT0;
-    else
-        buffer = device->offscreenBuffer;
-
-    ENTER_GL();
-    context_set_draw_buffer(context, buffer);
-    LEAVE_GL();
+    context_apply_draw_buffers(context, rt_count, rts);
+    context->draw_buffer_dirty = TRUE;
 
     if (context->last_was_blit)
     {
@@ -2074,6 +2155,14 @@ void context_apply_draw_state(struct wined3d_context *context, IWineD3DDeviceImp
     const struct StateEntry *state_table = device->StateTable;
     unsigned int i;
 
+    /* Preload resources before FBO setup. Texture preload in particular may
+     * result in changes to the current FBO, due to using e.g. FBO blits for
+     * updating a resource location. */
+    IWineD3DDeviceImpl_FindTexUnitMap(device);
+    device_preload_textures(device);
+    if (isStateDirty(context, STATE_VDECL))
+        device_update_stream_info(device, context->gl_info);
+
     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
     {
         context_validate_onscreen_formats(device, context, device->depth_stencil);
@@ -2081,20 +2170,21 @@ void context_apply_draw_state(struct wined3d_context *context, IWineD3DDeviceImp
         if (!context->render_offscreen)
         {
             ENTER_GL();
-            context_apply_fbo_state(context, GL_FRAMEBUFFER, NULL, NULL);
+            context_apply_fbo_state(context, GL_FRAMEBUFFER, NULL, NULL, SFLAG_INDRAWABLE);
             LEAVE_GL();
         }
         else
         {
             ENTER_GL();
-            context_apply_fbo_state(context, GL_FRAMEBUFFER, device->render_targets, device->depth_stencil);
+            context_apply_fbo_state(context, GL_FRAMEBUFFER, device->render_targets,
+                    device->depth_stencil, SFLAG_INTEXTURE);
             LEAVE_GL();
         }
     }
 
     if (context->draw_buffer_dirty)
     {
-        context_apply_draw_buffer(context, FALSE);
+        context_apply_draw_buffers(context, context->gl_info->limits.buffers, device->render_targets);
         context->draw_buffer_dirty = FALSE;
     }
 
@@ -2103,11 +2193,6 @@ void context_apply_draw_state(struct wined3d_context *context, IWineD3DDeviceImp
         device->frag_pipe->enable_extension((IWineD3DDevice *)device, TRUE);
     }
 
-    IWineD3DDeviceImpl_FindTexUnitMap(device);
-    device_preload_textures(device);
-    if (isStateDirty(context, STATE_VDECL))
-        device_update_stream_info(device, context->gl_info);
-
     ENTER_GL();
     for (i = 0; i < context->numDirtyEntries; ++i)
     {
@@ -2129,10 +2214,8 @@ static void context_setup_target(IWineD3DDeviceImpl *device,
     const struct StateEntry *StateTable = device->StateTable;
 
     if (!target) return;
-    else if (context->current_rt == target) return;
     render_offscreen = surface_is_offscreen(target);
-
-    context_set_render_offscreen(context, StateTable, render_offscreen);
+    if (context->current_rt == target && render_offscreen == old_render_offscreen) return;
 
     /* To compensate the lack of format switching with some offscreen rendering methods and on onscreen buffers
      * the alpha blend state changes with different render target formats. */
@@ -2142,10 +2225,10 @@ static void context_setup_target(IWineD3DDeviceImpl *device,
     }
     else
     {
-        const struct wined3d_format_desc *old = context->current_rt->resource.format_desc;
-        const struct wined3d_format_desc *new = target->resource.format_desc;
+        const struct wined3d_format *old = context->current_rt->resource.format;
+        const struct wined3d_format *new = target->resource.format;
 
-        if (old->format != new->format)
+        if (old->id != new->id)
         {
             /* Disable blending when the alpha mask has changed and when a format doesn't support blending. */
             if ((old->alpha_mask && !new->alpha_mask) || (!old->alpha_mask && new->alpha_mask)
@@ -2153,6 +2236,11 @@ static void context_setup_target(IWineD3DDeviceImpl *device,
             {
                 Context_MarkStateDirty(context, STATE_RENDER(WINED3DRS_ALPHABLENDENABLE), StateTable);
             }
+            /* Update sRGB writing when switching between formats that do/do not support sRGB writing */
+            if ((old->Flags & WINED3DFMT_FLAG_SRGB_WRITE) != (new->Flags & WINED3DFMT_FLAG_SRGB_WRITE))
+            {
+                Context_MarkStateDirty(context, STATE_RENDER(WINED3DRS_SRGBWRITEENABLE), StateTable);
+            }
         }
 
         /* When switching away from an offscreen render target, and we're not
@@ -2165,19 +2253,6 @@ static void context_setup_target(IWineD3DDeviceImpl *device,
         if (wined3d_settings.offscreen_rendering_mode != ORM_FBO
                 && old_render_offscreen && context->current_rt != target)
         {
-            BOOL oldInDraw = device->isInDraw;
-
-            /* surface_internal_preload() requires a context to load the
-             * texture, so it will call context_acquire(). Set isInDraw to true
-             * to signal surface_internal_preload() that it has a context. */
-
-            /* FIXME: This is just broken. There's no guarantee whatsoever
-             * that the currently active context, if any, is appropriate for
-             * reading back the render target. We should probably call
-             * context_set_current(context) here and then rely on
-             * context_acquire() doing the right thing. */
-            device->isInDraw = TRUE;
-
             /* Read the back buffer of the old drawable into the destination texture. */
             if (context->current_rt->texture_name_srgb)
             {
@@ -2188,29 +2263,16 @@ static void context_setup_target(IWineD3DDeviceImpl *device,
                 surface_internal_preload(context->current_rt, SRGB_RGB);
             }
 
-            IWineD3DSurface_ModifyLocation((IWineD3DSurface *)context->current_rt, SFLAG_INDRAWABLE, FALSE);
-
-            device->isInDraw = oldInDraw;
+            surface_modify_location(context->current_rt, SFLAG_INDRAWABLE, FALSE);
         }
     }
 
     context->draw_buffer_dirty = TRUE;
     context->current_rt = target;
+    context_set_render_offscreen(context, StateTable, render_offscreen);
 }
 
-/*****************************************************************************
- * context_acquire
- *
- * Finds a rendering context and drawable matching the device and render
- * target for the current thread, activates them and puts them into the
- * requested state.
- *
- * Params:
- *  This: Device to activate the context for
- *  target: Requested render target
- *  usage: Prepares the context for blitting, drawing or other actions
- *
- *****************************************************************************/
+/* Do not call while under the GL lock. */
 struct wined3d_context *context_acquire(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *target)
 {
     struct wined3d_context *current_context = context_get_current();
index 12acee2..2d2c04c 100644 (file)
@@ -27,6 +27,7 @@
 
 WINE_DEFAULT_DEBUG_CHANNEL(d3d_texture);
 
+/* Do not call while under the GL lock. */
 static void cubetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3DSRGB srgb)
 {
     /* Override the IWineD3DResource Preload method. */
@@ -70,8 +71,8 @@ static void cubetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3
         context = context_acquire(device, NULL);
     }
 
-    if (This->resource.format_desc->format == WINED3DFMT_P8_UINT
-            || This->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM)
+    if (This->resource.format->id == WINED3DFMT_P8_UINT
+            || This->resource.format->id == WINED3DFMT_P8_UINT_A8_UNORM)
     {
         for (i = 0; i < sub_count; ++i)
         {
@@ -81,10 +82,10 @@ static void cubetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3
             {
                 TRACE("Reloading surface %p because the d3d8/9 palette was changed.\n", surface);
                 /* TODO: This is not necessarily needed with hw palettized texture support. */
-                IWineD3DSurface_LoadLocation((IWineD3DSurface *)surface, SFLAG_INSYSMEM, NULL);
+                surface_load_location(surface, SFLAG_INSYSMEM, NULL);
                 /* Make sure the texture is reloaded because of the palette change,
                  * this kills performance though :( */
-                IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INTEXTURE, FALSE);
+                surface_modify_location(surface, SFLAG_INTEXTURE, FALSE);
             }
         }
     }
@@ -127,7 +128,7 @@ static void cubetexture_cleanup(IWineD3DCubeTextureImpl *This)
             surface_set_texture_name(surface, 0, TRUE);
             surface_set_texture_name(surface, 0, FALSE);
             surface_set_texture_target(surface, 0);
-            IWineD3DSurface_SetContainer((IWineD3DSurface *)surface, NULL);
+            surface_set_container(surface, WINED3D_CONTAINER_NONE, NULL);
             IWineD3DSurface_Release((IWineD3DSurface *)surface);
         }
     }
@@ -161,6 +162,7 @@ static ULONG WINAPI IWineD3DCubeTextureImpl_AddRef(IWineD3DCubeTexture *iface) {
     return InterlockedIncrement(&This->resource.ref);
 }
 
+/* Do not call while under the GL lock. */
 static ULONG WINAPI IWineD3DCubeTextureImpl_Release(IWineD3DCubeTexture *iface) {
     IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface;
     ULONG ref;
@@ -198,10 +200,12 @@ static DWORD WINAPI IWineD3DCubeTextureImpl_GetPriority(IWineD3DCubeTexture *ifa
     return resource_get_priority((IWineD3DResource *)iface);
 }
 
+/* Do not call while under the GL lock. */
 static void WINAPI IWineD3DCubeTextureImpl_PreLoad(IWineD3DCubeTexture *iface) {
     cubetexture_internal_preload((IWineD3DBaseTexture *) iface, SRGB_ANY);
 }
 
+/* Do not call while under the GL lock. */
 static void WINAPI IWineD3DCubeTextureImpl_UnLoad(IWineD3DCubeTexture *iface)
 {
     IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface;
@@ -230,8 +234,11 @@ static WINED3DRESOURCETYPE WINAPI IWineD3DCubeTextureImpl_GetType(IWineD3DCubeTe
     return resource_get_type((IWineD3DResource *)iface);
 }
 
-static HRESULT WINAPI IWineD3DCubeTextureImpl_GetParent(IWineD3DCubeTexture *iface, IUnknown **pParent) {
-    return resource_get_parent((IWineD3DResource *)iface, pParent);
+static void * WINAPI IWineD3DCubeTextureImpl_GetParent(IWineD3DCubeTexture *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ((IWineD3DCubeTextureImpl *)iface)->resource.parent;
 }
 
 /* ******************************************************
@@ -299,13 +306,6 @@ static HRESULT WINAPI IWineD3DCubeTextureImpl_BindTexture(IWineD3DCubeTexture *i
     return hr;
 }
 
-static UINT WINAPI IWineD3DCubeTextureImpl_GetTextureDimensions(IWineD3DCubeTexture *iface)
-{
-    TRACE("iface %p.\n", iface);
-
-    return GL_TEXTURE_CUBE_MAP_ARB;
-}
-
 static BOOL WINAPI IWineD3DCubeTextureImpl_IsCondNP2(IWineD3DCubeTexture *iface)
 {
     TRACE("iface %p.\n", iface);
@@ -330,7 +330,9 @@ static HRESULT WINAPI IWineD3DCubeTextureImpl_GetLevelDesc(IWineD3DCubeTexture *
         return WINED3DERR_INVALIDCALL;
     }
 
-    return IWineD3DSurface_GetDesc(surface, desc);
+    IWineD3DSurface_GetDesc(surface, desc);
+
+    return WINED3D_OK;
 }
 
 static HRESULT WINAPI IWineD3DCubeTextureImpl_GetCubeMapSurface(IWineD3DCubeTexture *iface,
@@ -440,7 +442,6 @@ static const IWineD3DCubeTextureVtbl IWineD3DCubeTexture_Vtbl =
     IWineD3DCubeTextureImpl_SetDirty,
     IWineD3DCubeTextureImpl_GetDirty,
     IWineD3DCubeTextureImpl_BindTexture,
-    IWineD3DCubeTextureImpl_GetTextureDimensions,
     IWineD3DCubeTextureImpl_IsCondNP2,
     /* IWineD3DCubeTexture */
     IWineD3DCubeTextureImpl_GetLevelDesc,
@@ -451,11 +452,11 @@ static const IWineD3DCubeTextureVtbl IWineD3DCubeTexture_Vtbl =
 };
 
 HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UINT levels,
-        IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        IWineD3DDeviceImpl *device, DWORD usage, enum wined3d_format_id format_id, WINED3DPOOL pool,
+        void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, gl_info);
+    const struct wined3d_format *format = wined3d_get_format(gl_info, format_id);
     UINT pow2_edge_length;
     unsigned int i, j;
     UINT tmp_w;
@@ -463,7 +464,7 @@ HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UIN
 
     /* TODO: It should only be possible to create textures for formats
      * that are reported as supported. */
-    if (WINED3DFMT_UNKNOWN >= format)
+    if (WINED3DFMT_UNKNOWN >= format_id)
     {
         WARN("(%p) : Texture cannot be created with a format of WINED3DFMT_UNKNOWN.\n", texture);
         return WINED3DERR_INVALIDCALL;
@@ -501,7 +502,7 @@ HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UIN
     texture->lpVtbl = &IWineD3DCubeTexture_Vtbl;
 
     hr = basetexture_init((IWineD3DBaseTextureImpl *)texture, 6, levels,
-            WINED3DRTYPE_CUBETEXTURE, device, 0, usage, format_desc, pool, parent, parent_ops);
+            WINED3DRTYPE_CUBETEXTURE, device, 0, usage, format, pool, parent, parent_ops);
     if (FAILED(hr))
     {
         WARN("Failed to initialize basetexture, returning %#x\n", hr);
@@ -529,6 +530,7 @@ HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UIN
         texture->baseTexture.pow2Matrix[15] = 1.0f;
         texture->baseTexture.pow2Matrix_identity = FALSE;
     }
+    texture->baseTexture.target = GL_TEXTURE_CUBE_MAP_ARB;
 
     /* Generate all the surfaces. */
     tmp_w = edge_length;
@@ -550,7 +552,7 @@ HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UIN
             IWineD3DSurface *surface;
 
             hr = IWineD3DDeviceParent_CreateSurface(device->device_parent, parent, tmp_w, tmp_w,
-                    format, usage, pool, i /* Level */, j, &surface);
+                    format_id, usage, pool, i /* Level */, j, &surface);
             if (FAILED(hr))
             {
                 FIXME("(%p) Failed to create surface, hr %#x.\n", texture, hr);
@@ -558,7 +560,7 @@ HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UIN
                 return hr;
             }
 
-            IWineD3DSurface_SetContainer(surface, (IWineD3DBase *)texture);
+            surface_set_container((IWineD3DSurfaceImpl *)surface, WINED3D_CONTAINER_TEXTURE, (IWineD3DBase *)texture);
             surface_set_texture_target((IWineD3DSurfaceImpl *)surface, cube_targets[j]);
             texture->baseTexture.sub_resources[idx] = (IWineD3DResourceImpl *)surface;
             TRACE("Created surface level %u @ %p.\n", i, surface);
index 7eb9153..97acd5f 100644 (file)
@@ -146,17 +146,17 @@ static WINED3DPRIMITIVETYPE d3d_primitive_type_from_gl(GLenum primitive_type)
 
 static BOOL fixed_get_input(BYTE usage, BYTE usage_idx, unsigned int *regnum)
 {
-    if ((usage == WINED3DDECLUSAGE_POSITION || usage == WINED3DDECLUSAGE_POSITIONT) && usage_idx == 0)
+    if ((usage == WINED3DDECLUSAGE_POSITION || usage == WINED3DDECLUSAGE_POSITIONT) && !usage_idx)
         *regnum = WINED3D_FFP_POSITION;
-    else if (usage == WINED3DDECLUSAGE_BLENDWEIGHT && usage_idx == 0)
+    else if (usage == WINED3DDECLUSAGE_BLENDWEIGHT && !usage_idx)
         *regnum = WINED3D_FFP_BLENDWEIGHT;
-    else if (usage == WINED3DDECLUSAGE_BLENDINDICES && usage_idx == 0)
+    else if (usage == WINED3DDECLUSAGE_BLENDINDICES && !usage_idx)
         *regnum = WINED3D_FFP_BLENDINDICES;
-    else if (usage == WINED3DDECLUSAGE_NORMAL && usage_idx == 0)
+    else if (usage == WINED3DDECLUSAGE_NORMAL && !usage_idx)
         *regnum = WINED3D_FFP_NORMAL;
-    else if (usage == WINED3DDECLUSAGE_PSIZE && usage_idx == 0)
+    else if (usage == WINED3DDECLUSAGE_PSIZE && !usage_idx)
         *regnum = WINED3D_FFP_PSIZE;
-    else if (usage == WINED3DDECLUSAGE_COLOR && usage_idx == 0)
+    else if (usage == WINED3DDECLUSAGE_COLOR && !usage_idx)
         *regnum = WINED3D_FFP_DIFFUSE;
     else if (usage == WINED3DDECLUSAGE_COLOR && usage_idx == 1)
         *regnum = WINED3D_FFP_SPECULAR;
@@ -177,7 +177,7 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
         BOOL use_vshader, struct wined3d_stream_info *stream_info, BOOL *fixup)
 {
     /* We need to deal with frequency data! */
-    IWineD3DVertexDeclarationImpl *declaration = (IWineD3DVertexDeclarationImpl *)This->stateBlock->vertexDecl;
+    IWineD3DVertexDeclarationImpl *declaration = This->stateBlock->state.vertex_declaration;
     unsigned int i;
 
     stream_info->use_map = 0;
@@ -191,6 +191,7 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
     for (i = 0; i < declaration->element_count; ++i)
     {
         const struct wined3d_vertex_declaration_element *element = &declaration->elements[i];
+        struct wined3d_buffer *buffer = This->stateBlock->state.streams[element->input_slot].buffer;
         GLuint buffer_object = 0;
         const BYTE *data = NULL;
         BOOL stride_used;
@@ -200,33 +201,32 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
         TRACE("%p Element %p (%u of %u)\n", declaration->elements,
                 element, i + 1, declaration->element_count);
 
-        if (!This->stateBlock->streamSource[element->input_slot]) continue;
+        if (!buffer) continue;
 
-        stride = This->stateBlock->streamStride[element->input_slot];
-        if (This->stateBlock->streamIsUP)
+        stride = This->stateBlock->state.streams[element->input_slot].stride;
+        if (This->stateBlock->state.user_stream)
         {
-            TRACE("Stream %u is UP, %p\n", element->input_slot, This->stateBlock->streamSource[element->input_slot]);
+            TRACE("Stream %u is UP, %p\n", element->input_slot, buffer);
             buffer_object = 0;
-            data = (BYTE *)This->stateBlock->streamSource[element->input_slot];
+            data = (BYTE *)buffer;
         }
         else
         {
-            TRACE("Stream %u isn't UP, %p\n", element->input_slot, This->stateBlock->streamSource[element->input_slot]);
-            data = buffer_get_memory(This->stateBlock->streamSource[element->input_slot],
-                    &This->adapter->gl_info, &buffer_object);
+            TRACE("Stream %u isn't UP, %p\n", element->input_slot, buffer);
+            data = buffer_get_memory((IWineD3DBuffer *)buffer, &This->adapter->gl_info, &buffer_object);
 
             /* Can't use vbo's if the base vertex index is negative. OpenGL doesn't accept negative offsets
              * (or rather offsets bigger than the vbo, because the pointer is unsigned), so use system memory
              * sources. In most sane cases the pointer - offset will still be > 0, otherwise it will wrap
              * around to some big value. Hope that with the indices, the driver wraps it back internally. If
              * not, drawStridedSlow is needed, including a vertex buffer path. */
-            if (This->stateBlock->loadBaseVertexIndex < 0)
+            if (This->stateBlock->state.load_base_vertex_index < 0)
             {
-                WARN("loadBaseVertexIndex is < 0 (%d), not using vbos\n", This->stateBlock->loadBaseVertexIndex);
+                WARN("load_base_vertex_index is < 0 (%d), not using VBOs.\n",
+                        This->stateBlock->state.load_base_vertex_index);
                 buffer_object = 0;
-                data = buffer_get_sysmem((struct wined3d_buffer *)This->stateBlock->streamSource[element->input_slot],
-                        &This->adapter->gl_info);
-                if ((UINT_PTR)data < -This->stateBlock->loadBaseVertexIndex * stride)
+                data = buffer_get_sysmem(buffer, &This->adapter->gl_info);
+                if ((UINT_PTR)data < -This->stateBlock->state.load_base_vertex_index * stride)
                 {
                     FIXME("System memory vertex data load offset is negative!\n");
                 }
@@ -260,7 +260,7 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
                 /* TODO: Assuming vertexdeclarations are usually used with the
                  * same or a similar shader, it might be worth it to store the
                  * last used output slot and try that one first. */
-                stride_used = vshader_get_input(This->stateBlock->vertexShader,
+                stride_used = vshader_get_input(This->stateBlock->state.vertex_shader,
                         element->usage, element->usage_idx, &idx);
             }
             else
@@ -274,7 +274,7 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
             if (!element->ffp_valid)
             {
                 WARN("Skipping unsupported fixed function element of format %s and usage %s\n",
-                        debug_d3dformat(element->format_desc->format), debug_d3ddeclusage(element->usage));
+                        debug_d3dformat(element->format->id), debug_d3ddeclusage(element->usage));
                 stride_used = FALSE;
             }
             else
@@ -289,16 +289,16 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
                     "input_slot %u, offset %u, stride %u, format %s, buffer_object %u]\n",
                     use_vshader ? "shader": "fixed function", idx,
                     debug_d3ddeclusage(element->usage), element->usage_idx, element->input_slot,
-                    element->offset, stride, debug_d3dformat(element->format_desc->format), buffer_object);
+                    element->offset, stride, debug_d3dformat(element->format->id), buffer_object);
 
-            stream_info->elements[idx].format_desc = element->format_desc;
+            stream_info->elements[idx].format = element->format;
             stream_info->elements[idx].stride = stride;
             stream_info->elements[idx].data = data;
             stream_info->elements[idx].stream_idx = element->input_slot;
             stream_info->elements[idx].buffer_object = buffer_object;
 
             if (!This->adapter->gl_info.supported[ARB_VERTEX_ARRAY_BGRA]
-                    && element->format_desc->format == WINED3DFMT_B8G8R8A8_UNORM)
+                    && element->format->id == WINED3DFMT_B8G8R8A8_UNORM)
             {
                 stream_info->swizzle_map |= 1 << idx;
             }
@@ -307,7 +307,7 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
     }
 
     This->num_buffer_queries = 0;
-    if (!This->stateBlock->streamIsUP)
+    if (!This->stateBlock->state.user_stream)
     {
         WORD map = stream_info->use_map;
 
@@ -316,12 +316,11 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
         {
             struct wined3d_stream_info_element *element;
             struct wined3d_buffer *buffer;
-            struct wined3d_event_query *query;
 
             if (!(map & 1)) continue;
 
             element = &stream_info->elements[i];
-            buffer = (struct wined3d_buffer *)This->stateBlock->streamSource[element->stream_idx];
+            buffer = This->stateBlock->state.streams[element->stream_idx].buffer;
             IWineD3DBuffer_PreLoad((IWineD3DBuffer *)buffer);
 
             /* If PreLoad dropped the buffer object, update the stream info. */
@@ -331,11 +330,8 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
                 element->data = buffer_get_sysmem(buffer, &This->adapter->gl_info) + (ptrdiff_t)element->data;
             }
 
-            query = ((struct wined3d_buffer *) buffer)->query;
-            if(query)
-            {
-                This->buffer_queries[This->num_buffer_queries++] = query;
-            }
+            if (buffer->query)
+                This->buffer_queries[This->num_buffer_queries++] = buffer->query;
         }
     }
 }
@@ -343,8 +339,7 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
 static void stream_info_element_from_strided(const struct wined3d_gl_info *gl_info,
         const struct WineDirect3DStridedData *strided, struct wined3d_stream_info_element *e)
 {
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(strided->format, gl_info);
-    e->format_desc = format_desc;
+    e->format = wined3d_get_format(gl_info, strided->format);
     e->stride = strided->dwStride;
     e->data = strided->lpData;
     e->stream_idx = 0;
@@ -378,10 +373,10 @@ static void device_stream_info_from_strided(const struct wined3d_gl_info *gl_inf
 
     for (i = 0; i < sizeof(stream_info->elements) / sizeof(*stream_info->elements); ++i)
     {
-        if (!stream_info->elements[i].format_desc) continue;
+        if (!stream_info->elements[i].format) continue;
 
         if (!gl_info->supported[ARB_VERTEX_ARRAY_BGRA]
-                && stream_info->elements[i].format_desc->format == WINED3DFMT_B8G8R8A8_UNORM)
+                && stream_info->elements[i].format->id == WINED3DFMT_B8G8R8A8_UNORM)
         {
             stream_info->swizzle_map |= 1 << i;
         }
@@ -413,8 +408,7 @@ static void device_trace_strided_stream_info(const struct wined3d_stream_info *s
 void device_update_stream_info(IWineD3DDeviceImpl *device, const struct wined3d_gl_info *gl_info)
 {
     struct wined3d_stream_info *stream_info = &device->strided_streams;
-    IWineD3DStateBlockImpl *stateblock = device->stateBlock;
-    BOOL vs = stateblock->vertexShader && device->vs_selected_mode != SHADER_NONE;
+    const struct wined3d_state *state = &device->stateBlock->state;
     BOOL fixup = FALSE;
 
     if (device->up_strided)
@@ -427,12 +421,12 @@ void device_update_stream_info(IWineD3DDeviceImpl *device, const struct wined3d_
     else
     {
         TRACE("============================= Vertex Declaration =============================\n");
-        device_stream_info_from_declaration(device, vs, stream_info, &fixup);
+        device_stream_info_from_declaration(device, !!state->vertex_shader, stream_info, &fixup);
     }
 
-    if (vs && !stream_info->position_transformed)
+    if (state->vertex_shader && !stream_info->position_transformed)
     {
-        if (((IWineD3DVertexDeclarationImpl *)stateblock->vertexDecl)->half_float_conv_needed && !fixup)
+        if (state->vertex_declaration->half_float_conv_needed && !fixup)
         {
             TRACE("Using drawStridedSlow with vertex shaders for FLOAT16 conversion.\n");
             device->useDrawStridedSlow = TRUE;
@@ -459,36 +453,36 @@ void device_update_stream_info(IWineD3DDeviceImpl *device, const struct wined3d_
     }
 }
 
-static void device_preload_texture(IWineD3DStateBlockImpl *stateblock, unsigned int idx)
+static void device_preload_texture(const struct wined3d_state *state, unsigned int idx)
 {
     IWineD3DBaseTextureImpl *texture;
     enum WINED3DSRGB srgb;
 
-    if (!(texture = (IWineD3DBaseTextureImpl *)stateblock->textures[idx])) return;
-    srgb = stateblock->samplerState[idx][WINED3DSAMP_SRGBTEXTURE] ? SRGB_SRGB : SRGB_RGB;
+    if (!(texture = state->textures[idx])) return;
+    srgb = state->sampler_states[idx][WINED3DSAMP_SRGBTEXTURE] ? SRGB_SRGB : SRGB_RGB;
     texture->baseTexture.internal_preload((IWineD3DBaseTexture *)texture, srgb);
 }
 
 void device_preload_textures(IWineD3DDeviceImpl *device)
 {
-    IWineD3DStateBlockImpl *stateblock = device->stateBlock;
+    const struct wined3d_state *state = &device->stateBlock->state;
     unsigned int i;
 
-    if (use_vs(stateblock))
+    if (use_vs(state))
     {
         for (i = 0; i < MAX_VERTEX_SAMPLERS; ++i)
         {
-            if (((IWineD3DBaseShaderImpl *)stateblock->vertexShader)->baseShader.reg_maps.sampler_type[i])
-                device_preload_texture(stateblock, MAX_FRAGMENT_SAMPLERS + i);
+            if (state->vertex_shader->baseShader.reg_maps.sampler_type[i])
+                device_preload_texture(state, MAX_FRAGMENT_SAMPLERS + i);
         }
     }
 
-    if (use_ps(stateblock))
+    if (use_ps(state))
     {
         for (i = 0; i < MAX_FRAGMENT_SAMPLERS; ++i)
         {
-            if (((IWineD3DBaseShaderImpl *)stateblock->pixelShader)->baseShader.reg_maps.sampler_type[i])
-                device_preload_texture(stateblock, i);
+            if (state->pixel_shader->baseShader.reg_maps.sampler_type[i])
+                device_preload_texture(state, i);
         }
     }
     else
@@ -498,7 +492,7 @@ void device_preload_textures(IWineD3DDeviceImpl *device)
         for (i = 0; ffu_map; ffu_map >>= 1, ++i)
         {
             if (ffu_map & 1)
-                device_preload_texture(stateblock, i);
+                device_preload_texture(state, i);
         }
     }
 }
@@ -567,16 +561,17 @@ void device_context_remove(IWineD3DDeviceImpl *device, struct wined3d_context *c
 void device_get_draw_rect(IWineD3DDeviceImpl *device, RECT *rect)
 {
     IWineD3DStateBlockImpl *stateblock = device->stateBlock;
-    WINED3DVIEWPORT *vp = &stateblock->viewport;
+    WINED3DVIEWPORT *vp = &stateblock->state.viewport;
 
     SetRect(rect, vp->X, vp->Y, vp->X + vp->Width, vp->Y + vp->Height);
 
-    if (stateblock->renderState[WINED3DRS_SCISSORTESTENABLE])
+    if (stateblock->state.render_states[WINED3DRS_SCISSORTESTENABLE])
     {
-        IntersectRect(rect, rect, &stateblock->scissorRect);
+        IntersectRect(rect, rect, &stateblock->state.scissor_rect);
     }
 }
 
+/* Do not call while under the GL lock. */
 void device_switch_onscreen_ds(IWineD3DDeviceImpl *device,
         struct wined3d_context *context, IWineD3DSurfaceImpl *depth_stencil)
 {
@@ -592,23 +587,250 @@ void device_switch_onscreen_ds(IWineD3DDeviceImpl *device,
     IWineD3DSurface_AddRef((IWineD3DSurface *)device->onscreen_depth_stencil);
 }
 
+static BOOL is_full_clear(IWineD3DSurfaceImpl *target, const RECT *draw_rect, const RECT *clear_rect)
+{
+    /* partial draw rect */
+    if (draw_rect->left || draw_rect->top
+            || draw_rect->right < target->currentDesc.Width
+            || draw_rect->bottom < target->currentDesc.Height)
+        return FALSE;
+
+    /* partial clear rect */
+    if (clear_rect && (clear_rect->left > 0 || clear_rect->top > 0
+            || clear_rect->right < target->currentDesc.Width
+            || clear_rect->bottom < target->currentDesc.Height))
+        return FALSE;
+
+    return TRUE;
+}
+
+static void prepare_ds_clear(IWineD3DSurfaceImpl *ds, struct wined3d_context *context,
+        DWORD location, const RECT *draw_rect, UINT rect_count, const RECT *clear_rect)
+{
+    RECT current_rect, r;
+
+    if (ds->Flags & location)
+        SetRect(&current_rect, 0, 0,
+                ds->ds_current_size.cx,
+                ds->ds_current_size.cy);
+    else
+        SetRectEmpty(&current_rect);
+
+    IntersectRect(&r, draw_rect, &current_rect);
+    if (EqualRect(&r, draw_rect))
+    {
+        /* current_rect âŠ‡ draw_rect, modify only. */
+        surface_modify_ds_location(ds, location, ds->ds_current_size.cx, ds->ds_current_size.cy);
+        return;
+    }
+
+    if (EqualRect(&r, &current_rect))
+    {
+        /* draw_rect âŠ‡ current_rect, test if we're doing a full clear. */
+
+        if (!clear_rect)
+        {
+            /* Full clear, modify only. */
+            surface_modify_ds_location(ds, location, draw_rect->right, draw_rect->bottom);
+            return;
+        }
+
+        IntersectRect(&r, draw_rect, clear_rect);
+        if (EqualRect(&r, draw_rect))
+        {
+            /* clear_rect âŠ‡ draw_rect, modify only. */
+            surface_modify_ds_location(ds, location, draw_rect->right, draw_rect->bottom);
+            return;
+        }
+    }
+
+    /* Full load. */
+    surface_load_ds_location(ds, context, location);
+    surface_modify_ds_location(ds, location, ds->ds_current_size.cx, ds->ds_current_size.cy);
+}
+
+/* Do not call while under the GL lock. */
+HRESULT device_clear_render_targets(IWineD3DDeviceImpl *device, UINT rt_count, IWineD3DSurfaceImpl **rts,
+        UINT rect_count, const RECT *rects, const RECT *draw_rect, DWORD flags,
+        const WINED3DCOLORVALUE *color, float depth, DWORD stencil)
+{
+    const RECT *clear_rect = (rect_count > 0 && rects) ? (const RECT *)rects : NULL;
+    IWineD3DSurfaceImpl *depth_stencil = device->depth_stencil;
+    IWineD3DSurfaceImpl *target = rts[0];
+    UINT drawable_width, drawable_height;
+    struct wined3d_context *context;
+    GLbitfield clear_mask = 0;
+    unsigned int i;
+
+    /* When we're clearing parts of the drawable, make sure that the target surface is well up to date in the
+     * drawable. After the clear we'll mark the drawable up to date, so we have to make sure that this is true
+     * for the cleared parts, and the untouched parts.
+     *
+     * If we're clearing the whole target there is no need to copy it into the drawable, it will be overwritten
+     * anyway. If we're not clearing the color buffer we don't have to copy either since we're not going to set
+     * the drawable up to date. We have to check all settings that limit the clear area though. Do not bother
+     * checking all this if the dest surface is in the drawable anyway. */
+    if (flags & WINED3DCLEAR_TARGET && !is_full_clear(target, draw_rect, clear_rect))
+    {
+        for (i = 0; i < rt_count; ++i)
+        {
+            if (rts[i]) surface_load_location(rts[i], SFLAG_INDRAWABLE, NULL);
+        }
+    }
+
+    context = context_acquire(device, target);
+    if (!context->valid)
+    {
+        context_release(context);
+        WARN("Invalid context, skipping clear.\n");
+        return WINED3D_OK;
+    }
+
+    context_apply_clear_state(context, device, rt_count, rts, depth_stencil);
+
+    target->get_drawable_size(context, &drawable_width, &drawable_height);
+
+    ENTER_GL();
+
+    /* Only set the values up once, as they are not changing. */
+    if (flags & WINED3DCLEAR_STENCIL)
+    {
+        if (context->gl_info->supported[EXT_STENCIL_TWO_SIDE])
+        {
+            glDisable(GL_STENCIL_TEST_TWO_SIDE_EXT);
+            IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_TWOSIDEDSTENCILMODE));
+        }
+        glStencilMask(~0U);
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_STENCILWRITEMASK));
+        glClearStencil(stencil);
+        checkGLcall("glClearStencil");
+        clear_mask = clear_mask | GL_STENCIL_BUFFER_BIT;
+    }
+
+    if (flags & WINED3DCLEAR_ZBUFFER)
+    {
+        DWORD location = context->render_offscreen ? SFLAG_DS_OFFSCREEN : SFLAG_DS_ONSCREEN;
+
+        if (location == SFLAG_DS_ONSCREEN && depth_stencil != device->onscreen_depth_stencil)
+        {
+            LEAVE_GL();
+            device_switch_onscreen_ds(device, context, depth_stencil);
+            ENTER_GL();
+        }
+        prepare_ds_clear(depth_stencil, context, location, draw_rect, rect_count, clear_rect);
+        surface_modify_location(depth_stencil, SFLAG_INDRAWABLE, TRUE);
+
+        glDepthMask(GL_TRUE);
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_ZWRITEENABLE));
+        glClearDepth(depth);
+        checkGLcall("glClearDepth");
+        clear_mask = clear_mask | GL_DEPTH_BUFFER_BIT;
+    }
+
+    if (flags & WINED3DCLEAR_TARGET)
+    {
+        for (i = 0; i < rt_count; ++i)
+        {
+            if (rts[i]) surface_modify_location(rts[i], SFLAG_INDRAWABLE, TRUE);
+        }
+
+        glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE));
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE1));
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE2));
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE3));
+        glClearColor(color->r, color->g, color->b, color->a);
+        checkGLcall("glClearColor");
+        clear_mask = clear_mask | GL_COLOR_BUFFER_BIT;
+    }
+
+    if (!clear_rect)
+    {
+        if (context->render_offscreen)
+        {
+            glScissor(draw_rect->left, draw_rect->top,
+                    draw_rect->right - draw_rect->left, draw_rect->bottom - draw_rect->top);
+        }
+        else
+        {
+            glScissor(draw_rect->left, drawable_height - draw_rect->bottom,
+                        draw_rect->right - draw_rect->left, draw_rect->bottom - draw_rect->top);
+        }
+        checkGLcall("glScissor");
+        glClear(clear_mask);
+        checkGLcall("glClear");
+    }
+    else
+    {
+        RECT current_rect;
+
+        /* Now process each rect in turn. */
+        for (i = 0; i < rect_count; ++i)
+        {
+            /* Note that GL uses lower left, width/height. */
+            IntersectRect(&current_rect, draw_rect, &clear_rect[i]);
+
+            TRACE("clear_rect[%u] %s, current_rect %s.\n", i,
+                    wine_dbgstr_rect(&clear_rect[i]),
+                    wine_dbgstr_rect(&current_rect));
+
+            /* Tests show that rectangles where x1 > x2 or y1 > y2 are ignored silently.
+             * The rectangle is not cleared, no error is returned, but further rectanlges are
+             * still cleared if they are valid. */
+            if (current_rect.left > current_rect.right || current_rect.top > current_rect.bottom)
+            {
+                TRACE("Rectangle with negative dimensions, ignoring.\n");
+                continue;
+            }
+
+            if (context->render_offscreen)
+            {
+                glScissor(current_rect.left, current_rect.top,
+                        current_rect.right - current_rect.left, current_rect.bottom - current_rect.top);
+            }
+            else
+            {
+                glScissor(current_rect.left, drawable_height - current_rect.bottom,
+                          current_rect.right - current_rect.left, current_rect.bottom - current_rect.top);
+            }
+            checkGLcall("glScissor");
+
+            glClear(clear_mask);
+            checkGLcall("glClear");
+        }
+    }
+
+    LEAVE_GL();
+
+    if (wined3d_settings.strict_draw_ordering || (target->container.type == WINED3D_CONTAINER_SWAPCHAIN
+            && target->container.u.swapchain->front_buffer == target))
+        wglFlush(); /* Flush to ensure ordering across contexts. */
+
+    context_release(context);
+
+    return WINED3D_OK;
+}
+
+
 /**********************************************************
  * IUnknown parts follows
  **********************************************************/
 
-static HRESULT WINAPI IWineD3DDeviceImpl_QueryInterface(IWineD3DDevice *iface,REFIID riid,LPVOID *ppobj)
+static HRESULT WINAPI IWineD3DDeviceImpl_QueryInterface(IWineD3DDevice *iface, REFIID riid, void **object)
 {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
 
-    TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(riid),ppobj);
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IWineD3DBase)
-        || IsEqualGUID(riid, &IID_IWineD3DDevice)) {
+    if (IsEqualGUID(riid, &IID_IWineD3DDevice)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
         IUnknown_AddRef(iface);
-        *ppobj = This;
+        *object = iface;
         return S_OK;
     }
-    *ppobj = NULL;
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
     return E_NOINTERFACE;
 }
 
@@ -664,18 +886,8 @@ static ULONG WINAPI IWineD3DDeviceImpl_Release(IWineD3DDevice *iface) {
     return refCount;
 }
 
-/**********************************************************
- * IWineD3DDevice implementation follows
- **********************************************************/
-static HRESULT WINAPI IWineD3DDeviceImpl_GetParent(IWineD3DDevice *iface, IUnknown **pParent) {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    *pParent = This->parent;
-    IUnknown_AddRef(This->parent);
-    return WINED3D_OK;
-}
-
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateBuffer(IWineD3DDevice *iface, struct wined3d_buffer_desc *desc,
-        const void *data, IUnknown *parent, const struct wined3d_parent_ops *parent_ops, IWineD3DBuffer **buffer)
+        const void *data, void *parent, const struct wined3d_parent_ops *parent_ops, IWineD3DBuffer **buffer)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     struct wined3d_buffer *object;
@@ -710,8 +922,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateBuffer(IWineD3DDevice *iface, str
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateVertexBuffer(IWineD3DDevice *iface,
-        UINT Size, DWORD Usage, WINED3DPOOL Pool, IWineD3DBuffer **ppVertexBuffer,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        UINT Size, DWORD Usage, WINED3DPOOL Pool, void *parent,
+        const struct wined3d_parent_ops *parent_ops, IWineD3DBuffer **ppVertexBuffer)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     struct wined3d_buffer *object;
@@ -754,8 +966,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateVertexBuffer(IWineD3DDevice *ifac
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateIndexBuffer(IWineD3DDevice *iface,
-        UINT Length, DWORD Usage, WINED3DPOOL Pool, IWineD3DBuffer **ppIndexBuffer,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        UINT Length, DWORD Usage, WINED3DPOOL Pool, void *parent,
+        const struct wined3d_parent_ops *parent_ops, IWineD3DBuffer **ppIndexBuffer)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     struct wined3d_buffer *object;
@@ -790,7 +1002,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateIndexBuffer(IWineD3DDevice *iface
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateStateBlock(IWineD3DDevice *iface,
-        WINED3DSTATEBLOCKTYPE type, IWineD3DStateBlock **stateblock, IUnknown *parent)
+        WINED3DSTATEBLOCKTYPE type, IWineD3DStateBlock **stateblock)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DStateBlockImpl *object;
@@ -818,9 +1030,9 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateStateBlock(IWineD3DDevice *iface,
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateSurface(IWineD3DDevice *iface, UINT Width, UINT Height,
-        WINED3DFORMAT Format, BOOL Lockable, BOOL Discard, UINT Level, IWineD3DSurface **ppSurface,
-        DWORD Usage, WINED3DPOOL Pool, WINED3DMULTISAMPLE_TYPE MultiSample, DWORD MultisampleQuality,
-        WINED3DSURFTYPE Impl, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        enum wined3d_format_id Format, BOOL Lockable, BOOL Discard, UINT Level, DWORD Usage, WINED3DPOOL Pool,
+        WINED3DMULTISAMPLE_TYPE MultiSample, DWORD MultisampleQuality, WINED3DSURFTYPE Impl,
+        void *parent, const struct wined3d_parent_ops *parent_ops, IWineD3DSurface **surface)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DSurfaceImpl *object;
@@ -829,7 +1041,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateSurface(IWineD3DDevice *iface, UI
     TRACE("iface %p, width %u, height %u, format %s (%#x), lockable %#x, discard %#x, level %u\n",
             iface, Width, Height, debug_d3dformat(Format), Format, Lockable, Discard, Level);
     TRACE("surface %p, usage %s (%#x), pool %s (%#x), multisample_type %#x, multisample_quality %u\n",
-            ppSurface, debug_d3dusage(Usage), Usage, debug_d3dpool(Pool), Pool, MultiSample, MultisampleQuality);
+            surface, debug_d3dusage(Usage), Usage, debug_d3dpool(Pool), Pool, MultiSample, MultisampleQuality);
     TRACE("surface_type %#x, parent %p, parent_ops %p.\n", Impl, parent, parent_ops);
 
     if (Impl == SURFACE_OPENGL && !This->adapter)
@@ -856,13 +1068,13 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateSurface(IWineD3DDevice *iface, UI
 
     TRACE("(%p) : Created surface %p\n", This, object);
 
-    *ppSurface = (IWineD3DSurface *)object;
+    *surface = (IWineD3DSurface *)object;
 
     return hr;
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateRendertargetView(IWineD3DDevice *iface,
-        IWineD3DResource *resource, IUnknown *parent, IWineD3DRendertargetView **rendertarget_view)
+        IWineD3DResource *resource, void *parent, IWineD3DRendertargetView **rendertarget_view)
 {
     struct wined3d_rendertarget_view *object;
 
@@ -885,8 +1097,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateRendertargetView(IWineD3DDevice *
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateTexture(IWineD3DDevice *iface,
-        UINT Width, UINT Height, UINT Levels, DWORD Usage, WINED3DFORMAT Format, WINED3DPOOL Pool,
-        IWineD3DTexture **ppTexture, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        UINT Width, UINT Height, UINT Levels, DWORD Usage, enum wined3d_format_id Format, WINED3DPOOL Pool,
+        void *parent, const struct wined3d_parent_ops *parent_ops, IWineD3DTexture **ppTexture)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DTextureImpl *object;
@@ -921,8 +1133,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateTexture(IWineD3DDevice *iface,
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateVolumeTexture(IWineD3DDevice *iface,
-        UINT Width, UINT Height, UINT Depth, UINT Levels, DWORD Usage, WINED3DFORMAT Format, WINED3DPOOL Pool,
-        IWineD3DVolumeTexture **ppVolumeTexture, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        UINT Width, UINT Height, UINT Depth, UINT Levels, DWORD Usage, enum wined3d_format_id Format, WINED3DPOOL Pool,
+        void *parent, const struct wined3d_parent_ops *parent_ops, IWineD3DVolumeTexture **ppVolumeTexture)
 {
     IWineD3DDeviceImpl        *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DVolumeTextureImpl *object;
@@ -955,8 +1167,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateVolumeTexture(IWineD3DDevice *ifa
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateVolume(IWineD3DDevice *iface, UINT Width, UINT Height,
-        UINT Depth, DWORD Usage, WINED3DFORMAT Format, WINED3DPOOL Pool, IWineD3DVolume **ppVolume,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        UINT Depth, DWORD Usage, enum wined3d_format_id Format, WINED3DPOOL Pool, void *parent,
+        const struct wined3d_parent_ops *parent_ops, IWineD3DVolume **ppVolume)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DVolumeImpl *object;
@@ -988,8 +1200,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateVolume(IWineD3DDevice *iface, UIN
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateCubeTexture(IWineD3DDevice *iface, UINT EdgeLength, UINT Levels,
-        DWORD Usage, WINED3DFORMAT Format, WINED3DPOOL Pool, IWineD3DCubeTexture **ppCubeTexture,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        DWORD Usage, enum wined3d_format_id Format, WINED3DPOOL Pool, void *parent,
+        const struct wined3d_parent_ops *parent_ops, IWineD3DCubeTexture **ppCubeTexture)
 {
     IWineD3DDeviceImpl      *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DCubeTextureImpl *object; /** NOTE: impl ref allowed since this is a create function **/
@@ -1019,13 +1231,13 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateCubeTexture(IWineD3DDevice *iface
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateQuery(IWineD3DDevice *iface,
-        WINED3DQUERYTYPE type, IWineD3DQuery **query, IUnknown *parent)
+        WINED3DQUERYTYPE type, IWineD3DQuery **query)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DQueryImpl *object;
     HRESULT hr;
 
-    TRACE("iface %p, type %#x, query %p, parent %p.\n", iface, type, query, parent);
+    TRACE("iface %p, type %#x, query %p.\n", iface, type, query);
 
     object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
     if (!object)
@@ -1034,7 +1246,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateQuery(IWineD3DDevice *iface,
         return E_OUTOFMEMORY;
     }
 
-    hr = query_init(object, This, type, parent);
+    hr = query_init(object, This, type);
     if (FAILED(hr))
     {
         WARN("Failed to initialize query, hr %#x.\n", hr);
@@ -1048,9 +1260,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateQuery(IWineD3DDevice *iface,
     return WINED3D_OK;
 }
 
+/* Do not call while under the GL lock. */
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateSwapChain(IWineD3DDevice *iface,
-        WINED3DPRESENT_PARAMETERS *present_parameters, IWineD3DSwapChain **swapchain,
-        IUnknown *parent, WINED3DSURFTYPE surface_type)
+        WINED3DPRESENT_PARAMETERS *present_parameters, WINED3DSURFTYPE surface_type,
+        void *parent, IWineD3DSwapChain **swapchain)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DSwapChainImpl *object;
@@ -1105,8 +1318,8 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_GetSwapChain(IWineD3DDevice *iface, U
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateVertexDeclaration(IWineD3DDevice *iface,
-        IWineD3DVertexDeclaration **declaration, IUnknown *parent, const struct wined3d_parent_ops *parent_ops,
-        const WINED3DVERTEXELEMENT *elements, UINT element_count)
+        const WINED3DVERTEXELEMENT *elements, UINT element_count, void *parent,
+        const struct wined3d_parent_ops *parent_ops, IWineD3DVertexDeclaration **declaration)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DVertexDeclarationImpl *object = NULL;
@@ -1145,14 +1358,14 @@ struct wined3d_fvf_convert_state
 };
 
 static void append_decl_element(struct wined3d_fvf_convert_state *state,
-        WINED3DFORMAT format, WINED3DDECLUSAGE usage, UINT usage_idx)
+        enum wined3d_format_id format_id, WINED3DDECLUSAGE usage, UINT usage_idx)
 {
     WINED3DVERTEXELEMENT *elements = state->elements;
-    const struct wined3d_format_desc *format_desc;
+    const struct wined3d_format *format;
     UINT offset = state->offset;
     UINT idx = state->idx;
 
-    elements[idx].format = format;
+    elements[idx].format = format_id;
     elements[idx].input_slot = 0;
     elements[idx].offset = offset;
     elements[idx].output_slot = 0;
@@ -1160,8 +1373,8 @@ static void append_decl_element(struct wined3d_fvf_convert_state *state,
     elements[idx].usage = usage;
     elements[idx].usage_idx = usage_idx;
 
-    format_desc = getFormatDescEntry(format, state->gl_info);
-    state->offset += format_desc->component_count * format_desc->component_size;
+    format = wined3d_get_format(state->gl_info, format_id);
+    state->offset += format->component_count * format->component_size;
     ++state->idx;
 }
 
@@ -1169,16 +1382,16 @@ static unsigned int ConvertFvfToDeclaration(IWineD3DDeviceImpl *This, /* For the
         DWORD fvf, WINED3DVERTEXELEMENT **ppVertexElements)
 {
     const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
-    BOOL has_pos = (fvf & WINED3DFVF_POSITION_MASK) != 0;
+    BOOL has_pos = !!(fvf & WINED3DFVF_POSITION_MASK);
     BOOL has_blend = (fvf & WINED3DFVF_XYZB5) > WINED3DFVF_XYZRHW;
     BOOL has_blend_idx = has_blend &&
        (((fvf & WINED3DFVF_XYZB5) == WINED3DFVF_XYZB5) ||
         (fvf & WINED3DFVF_LASTBETA_D3DCOLOR) ||
         (fvf & WINED3DFVF_LASTBETA_UBYTE4));
-    BOOL has_normal = (fvf & WINED3DFVF_NORMAL) != 0;
-    BOOL has_psize = (fvf & WINED3DFVF_PSIZE) != 0;
-    BOOL has_diffuse = (fvf & WINED3DFVF_DIFFUSE) != 0;
-    BOOL has_specular = (fvf & WINED3DFVF_SPECULAR) !=0;
+    BOOL has_normal = !!(fvf & WINED3DFVF_NORMAL);
+    BOOL has_psize = !!(fvf & WINED3DFVF_PSIZE);
+    BOOL has_diffuse = !!(fvf & WINED3DFVF_DIFFUSE);
+    BOOL has_specular = !!(fvf & WINED3DFVF_SPECULAR);
 
     DWORD num_textures = (fvf & WINED3DFVF_TEXCOUNT_MASK) >> WINED3DFVF_TEXCOUNT_SHIFT;
     DWORD texcoords = (fvf & 0xFFFF0000) >> 16;
@@ -1274,8 +1487,8 @@ static unsigned int ConvertFvfToDeclaration(IWineD3DDeviceImpl *This, /* For the
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateVertexDeclarationFromFVF(IWineD3DDevice *iface,
-        IWineD3DVertexDeclaration **declaration, IUnknown *parent,
-        const struct wined3d_parent_ops *parent_ops, DWORD fvf)
+        DWORD fvf, void *parent, const struct wined3d_parent_ops *parent_ops,
+        IWineD3DVertexDeclaration **declaration)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
     WINED3DVERTEXELEMENT *elements;
@@ -1287,20 +1500,23 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateVertexDeclarationFromFVF(IWineD3D
     size = ConvertFvfToDeclaration(This, fvf, &elements);
     if (size == ~0U) return E_OUTOFMEMORY;
 
-    hr = IWineD3DDevice_CreateVertexDeclaration(iface, declaration, parent, parent_ops, elements, size);
+    hr = IWineD3DDeviceImpl_CreateVertexDeclaration(iface, elements, size, parent, parent_ops, declaration);
     HeapFree(GetProcessHeap(), 0, elements);
     return hr;
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateVertexShader(IWineD3DDevice *iface,
         const DWORD *pFunction, const struct wined3d_shader_signature *output_signature,
-        IWineD3DVertexShader **ppVertexShader, IUnknown *parent,
-        const struct wined3d_parent_ops *parent_ops)
+        void *parent, const struct wined3d_parent_ops *parent_ops,
+        IWineD3DVertexShader **ppVertexShader)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DVertexShaderImpl *object;
     HRESULT hr;
 
+    if (This->vs_selected_mode == SHADER_NONE)
+        return WINED3DERR_INVALIDCALL;
+
     object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
     if (!object)
     {
@@ -1324,8 +1540,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateVertexShader(IWineD3DDevice *ifac
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreateGeometryShader(IWineD3DDevice *iface,
         const DWORD *byte_code, const struct wined3d_shader_signature *output_signature,
-        IWineD3DGeometryShader **shader, IUnknown *parent,
-        const struct wined3d_parent_ops *parent_ops)
+        void *parent, const struct wined3d_parent_ops *parent_ops,
+        IWineD3DGeometryShader **shader)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     struct wined3d_geometryshader *object;
@@ -1354,13 +1570,16 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreateGeometryShader(IWineD3DDevice *if
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreatePixelShader(IWineD3DDevice *iface,
         const DWORD *pFunction, const struct wined3d_shader_signature *output_signature,
-        IWineD3DPixelShader **ppPixelShader, IUnknown *parent,
-        const struct wined3d_parent_ops *parent_ops)
+        void *parent, const struct wined3d_parent_ops *parent_ops,
+        IWineD3DPixelShader **ppPixelShader)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DPixelShaderImpl *object;
     HRESULT hr;
 
+    if (This->ps_selected_mode == SHADER_NONE)
+        return WINED3DERR_INVALIDCALL;
+
     object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
     if (!object)
     {
@@ -1383,14 +1602,14 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreatePixelShader(IWineD3DDevice *iface
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_CreatePalette(IWineD3DDevice *iface, DWORD Flags,
-        const PALETTEENTRY *PalEnt, IWineD3DPalette **Palette, IUnknown *Parent)
+        const PALETTEENTRY *PalEnt, void *parent, IWineD3DPalette **Palette)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
     IWineD3DPaletteImpl *object;
     HRESULT hr;
 
     TRACE("iface %p, flags %#x, entries %p, palette %p, parent %p.\n",
-            iface, Flags, PalEnt, Palette, Parent);
+            iface, Flags, PalEnt, Palette, parent);
 
     object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
     if (!object)
@@ -1399,7 +1618,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_CreatePalette(IWineD3DDevice *iface, DW
         return E_OUTOFMEMORY;
     }
 
-    hr = wined3d_palette_init(object, This, Flags, PalEnt, Parent);
+    hr = wined3d_palette_init(object, This, Flags, PalEnt, parent);
     if (FAILED(hr))
     {
         WARN("Failed to initialize palette, hr %#x.\n", hr);
@@ -1439,10 +1658,11 @@ static void IWineD3DDeviceImpl_LoadLogo(IWineD3DDeviceImpl *This, const char *fi
     }
 
     hr = IWineD3DDevice_CreateSurface((IWineD3DDevice *)This, bm.bmWidth, bm.bmHeight, WINED3DFMT_B5G6R5_UNORM, TRUE,
-            FALSE, 0, &This->logo_surface, 0, WINED3DPOOL_DEFAULT, WINED3DMULTISAMPLE_NONE, 0, SURFACE_OPENGL,
-            NULL, &wined3d_null_parent_ops);
-    if(FAILED(hr)) {
-        ERR("Wine logo requested, but failed to create surface\n");
+            FALSE, 0, 0, WINED3DPOOL_DEFAULT, WINED3DMULTISAMPLE_NONE, 0, SURFACE_OPENGL, NULL,
+            &wined3d_null_parent_ops, &This->logo_surface);
+    if (FAILED(hr))
+    {
+        ERR("Wine logo requested, but failed to create surface, hr %#x.\n", hr);
         goto out;
     }
 
@@ -1455,9 +1675,12 @@ static void IWineD3DDeviceImpl_LoadLogo(IWineD3DDeviceImpl *This, const char *fi
         colorkey.dwColorSpaceLowValue = 0;
         colorkey.dwColorSpaceHighValue = 0;
         IWineD3DSurface_SetColorKey(This->logo_surface, WINEDDCKEY_SRCBLT, &colorkey);
-    } else {
+    }
+    else
+    {
+        const WINED3DCOLORVALUE c = {1.0f, 1.0f, 1.0f, 1.0f};
         /* Fill the surface with a white color to show that wined3d is there */
-        IWineD3DDevice_ColorFill((IWineD3DDevice *) This, This->logo_surface, NULL, 0xffffffff);
+        IWineD3DDevice_ColorFill((IWineD3DDevice *)This, This->logo_surface, NULL, &c);
     }
 
 out:
@@ -1568,12 +1791,9 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Init3D(IWineD3DDevice *iface,
     if(!This->adapter->opengl) return WINED3DERR_INVALIDCALL;
 
     TRACE("(%p) : Creating stateblock\n", This);
-    /* Creating the startup stateBlock - Note Special Case: 0 => Don't fill in yet! */
-    hr = IWineD3DDevice_CreateStateBlock(iface,
-                                         WINED3DSBT_INIT,
-                                         (IWineD3DStateBlock **)&This->stateBlock,
-                                         NULL);
-    if (WINED3D_OK != hr) {   /* Note: No parent needed for initial internal stateblock */
+    hr = IWineD3DDevice_CreateStateBlock(iface, WINED3DSBT_INIT, (IWineD3DStateBlock **)&This->stateBlock);
+    if (FAILED(hr))
+    {
         WARN("Failed to create stateblock\n");
         goto err_out;
     }
@@ -1583,12 +1803,11 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Init3D(IWineD3DDevice *iface,
 
     This->render_targets = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
             sizeof(*This->render_targets) * gl_info->limits.buffers);
-    This->draw_buffers = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
-            sizeof(GLenum) * gl_info->limits.buffers);
 
     This->NumberOfPalettes = 1;
     This->palettes = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(PALETTEENTRY*));
-    if(!This->palettes || !This->render_targets || !This->draw_buffers) {
+    if (!This->palettes || !This->render_targets)
+    {
         ERR("Out of memory!\n");
         hr = E_OUTOFMEMORY;
         goto err_out;
@@ -1674,7 +1893,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Init3D(IWineD3DDevice *iface,
     /* Set up some starting GL setup */
 
     /* Setup all the devices defaults */
-    IWineD3DStateBlock_InitStartupStateBlock((IWineD3DStateBlock *)This->stateBlock);
+    stateblock_init_default_state(This->stateBlock);
 
     context = context_acquire(This, swapchain->front_buffer);
 
@@ -1727,7 +1946,6 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Init3D(IWineD3DDevice *iface,
 
 err_out:
     HeapFree(GetProcessHeap(), 0, This->render_targets);
-    HeapFree(GetProcessHeap(), 0, This->draw_buffers);
     HeapFree(GetProcessHeap(), 0, This->swapchains);
     This->NumberOfSwapChains = 0;
     if(This->palettes) {
@@ -1889,13 +2107,19 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Uninit3D(IWineD3DDevice *iface,
         This->onscreen_depth_stencil = NULL;
     }
 
-    TRACE("Releasing the depth stencil buffer at %p\n", This->depth_stencil);
-    if (This->depth_stencil && IWineD3DSurface_Release((IWineD3DSurface *)This->depth_stencil))
+    if (This->depth_stencil)
     {
-        if (This->auto_depth_stencil != This->depth_stencil)
-            FIXME("(%p) Something is still holding the depth/stencil buffer.\n",This);
+        IWineD3DSurfaceImpl *ds = This->depth_stencil;
+
+        TRACE("Releasing depth/stencil buffer %p.\n", ds);
+
+        This->depth_stencil = NULL;
+        if (IWineD3DSurface_Release((IWineD3DSurface *)ds)
+                && ds != This->auto_depth_stencil)
+        {
+            ERR("Something is still holding a reference to depth/stencil buffer %p.\n", ds);
+        }
     }
-    This->depth_stencil = NULL;
 
     TRACE("Releasing the render target at %p\n", This->render_targets[0]);
     IWineD3DSurface_Release((IWineD3DSurface *)This->render_targets[0]);
@@ -1931,9 +2155,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Uninit3D(IWineD3DDevice *iface,
     This->NumberOfPalettes = 0;
 
     HeapFree(GetProcessHeap(), 0, This->render_targets);
-    HeapFree(GetProcessHeap(), 0, This->draw_buffers);
     This->render_targets = NULL;
-    This->draw_buffers = NULL;
 
     This->d3d_initialized = FALSE;
 
@@ -1974,7 +2196,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetDisplayMode(IWineD3DDevice *iface, U
         const WINED3DDISPLAYMODE* pMode) {
     DEVMODEW devmode;
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(pMode->Format, &This->adapter->gl_info);
+    const struct wined3d_format *format = wined3d_get_format(&This->adapter->gl_info, pMode->Format);
     LONG ret;
     RECT clip_rc;
 
@@ -1989,26 +2211,24 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetDisplayMode(IWineD3DDevice *iface, U
     memset(&devmode, 0, sizeof(devmode));
     devmode.dmSize = sizeof(devmode);
     devmode.dmFields = DM_BITSPERPEL | DM_PELSWIDTH | DM_PELSHEIGHT;
-    devmode.dmBitsPerPel = format_desc->byte_count * 8;
+    devmode.dmBitsPerPel = format->byte_count * CHAR_BIT;
     devmode.dmPelsWidth  = pMode->Width;
     devmode.dmPelsHeight = pMode->Height;
 
     devmode.dmDisplayFrequency = pMode->RefreshRate;
-    if (pMode->RefreshRate != 0)  {
+    if (pMode->RefreshRate)
         devmode.dmFields |= DM_DISPLAYFREQUENCY;
-    }
 
     /* Only change the mode if necessary */
-    if( (This->ddraw_width == pMode->Width) &&
-        (This->ddraw_height == pMode->Height) &&
-        (This->ddraw_format == pMode->Format) &&
-        (pMode->RefreshRate == 0) ) {
+    if (This->ddraw_width == pMode->Width && This->ddraw_height == pMode->Height
+            && This->ddraw_format == pMode->Format && !pMode->RefreshRate)
         return WINED3D_OK;
-    }
 
     ret = ChangeDisplaySettingsExW(NULL, &devmode, NULL, CDS_FULLSCREEN, NULL);
-    if (ret != DISP_CHANGE_SUCCESSFUL) {
-        if(devmode.dmDisplayFrequency != 0) {
+    if (ret != DISP_CHANGE_SUCCESSFUL)
+    {
+        if (devmode.dmDisplayFrequency)
+        {
             WARN("ChangeDisplaySettingsExW failed, trying without the refresh rate\n");
             devmode.dmFields &= ~DM_DISPLAYFREQUENCY;
             devmode.dmDisplayFrequency = 0;
@@ -2056,8 +2276,12 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetStreamSource(IWineD3DDevice *iface,
         IWineD3DBuffer *pStreamData, UINT OffsetInBytes, UINT Stride)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    struct wined3d_stream_state *stream;
     IWineD3DBuffer *oldSrc;
 
+    TRACE("iface %p, stream_idx %u, buffer %p, offset %u, stride %u.\n",
+            iface, StreamNumber, pStreamData, OffsetInBytes, Stride);
+
     if (StreamNumber >= MAX_STREAMS) {
         WARN("Stream out of range %d\n", StreamNumber);
         return WINED3DERR_INVALIDCALL;
@@ -2066,22 +2290,24 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetStreamSource(IWineD3DDevice *iface,
         return WINED3DERR_INVALIDCALL;
     }
 
-    oldSrc = This->updateStateBlock->streamSource[StreamNumber];
-    TRACE("(%p) : StreamNo: %u, OldStream (%p), NewStream (%p), OffsetInBytes %u, NewStride %u\n", This, StreamNumber, oldSrc, pStreamData, OffsetInBytes, Stride);
+    stream = &This->updateStateBlock->state.streams[StreamNumber];
+    oldSrc = (IWineD3DBuffer *)stream->buffer;
 
     This->updateStateBlock->changed.streamSource |= 1 << StreamNumber;
 
-    if(oldSrc == pStreamData &&
-       This->updateStateBlock->streamStride[StreamNumber] == Stride &&
-       This->updateStateBlock->streamOffset[StreamNumber] == OffsetInBytes) {
+    if (oldSrc == pStreamData
+            && stream->stride == Stride
+            && stream->offset == OffsetInBytes)
+    {
        TRACE("Application is setting the old values over, nothing to do\n");
        return WINED3D_OK;
     }
 
-    This->updateStateBlock->streamSource[StreamNumber]         = pStreamData;
-    if (pStreamData) {
-        This->updateStateBlock->streamStride[StreamNumber]     = Stride;
-        This->updateStateBlock->streamOffset[StreamNumber]     = OffsetInBytes;
+    stream->buffer = (struct wined3d_buffer *)pStreamData;
+    if (pStreamData)
+    {
+        stream->stride = Stride;
+        stream->offset = OffsetInBytes;
     }
 
     /* Handle recording of state blocks */
@@ -2092,11 +2318,13 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetStreamSource(IWineD3DDevice *iface,
         return WINED3D_OK;
     }
 
-    if (pStreamData != NULL) {
+    if (pStreamData)
+    {
         InterlockedIncrement(&((struct wined3d_buffer *)pStreamData)->bind_count);
         IWineD3DBuffer_AddRef(pStreamData);
     }
-    if (oldSrc != NULL) {
+    if (oldSrc)
+    {
         InterlockedDecrement(&((struct wined3d_buffer *)oldSrc)->bind_count);
         IWineD3DBuffer_Release(oldSrc);
     }
@@ -2110,68 +2338,76 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetStreamSource(IWineD3DDevice *iface,
         UINT StreamNumber, IWineD3DBuffer **pStream, UINT *pOffset, UINT *pStride)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    struct wined3d_stream_state *stream;
 
-    TRACE("(%p) : StreamNo: %u, Stream (%p), Offset %u, Stride %u\n", This, StreamNumber,
-           This->stateBlock->streamSource[StreamNumber],
-           This->stateBlock->streamOffset[StreamNumber],
-           This->stateBlock->streamStride[StreamNumber]);
+    TRACE("iface %p, stream_idx %u, buffer %p, offset %p, stride %p.\n",
+            iface, StreamNumber, pStream, pOffset, pStride);
 
-    if (StreamNumber >= MAX_STREAMS) {
+    if (StreamNumber >= MAX_STREAMS)
+    {
         WARN("Stream out of range %d\n", StreamNumber);
         return WINED3DERR_INVALIDCALL;
     }
-    *pStream = This->stateBlock->streamSource[StreamNumber];
-    *pStride = This->stateBlock->streamStride[StreamNumber];
-    if (pOffset) {
-        *pOffset = This->stateBlock->streamOffset[StreamNumber];
-    }
 
-    if (*pStream != NULL) {
-        IWineD3DBuffer_AddRef(*pStream); /* We have created a new reference to the VB */
-    }
+    stream = &This->stateBlock->state.streams[StreamNumber];
+    *pStream = (IWineD3DBuffer *)stream->buffer;
+    *pStride = stream->stride;
+    if (pOffset) *pOffset = stream->offset;
+
+    if (*pStream) IWineD3DBuffer_AddRef(*pStream);
+
     return WINED3D_OK;
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_SetStreamSourceFreq(IWineD3DDevice *iface,  UINT StreamNumber, UINT Divider) {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    UINT oldFlags = This->updateStateBlock->streamFlags[StreamNumber];
-    UINT oldFreq = This->updateStateBlock->streamFreq[StreamNumber];
+    struct wined3d_stream_state *stream;
+    UINT oldFlags, oldFreq;
+
+    TRACE("iface %p, stream_idx %u, divider %#x.\n", iface, StreamNumber, Divider);
 
-    /* Verify input at least in d3d9 this is invalid*/
-    if( (Divider & WINED3DSTREAMSOURCE_INSTANCEDATA) && (Divider & WINED3DSTREAMSOURCE_INDEXEDDATA)){
+    /* Verify input at least in d3d9 this is invalid. */
+    if ((Divider & WINED3DSTREAMSOURCE_INSTANCEDATA) && (Divider & WINED3DSTREAMSOURCE_INDEXEDDATA))
+    {
         WARN("INSTANCEDATA and INDEXEDDATA were set, returning D3DERR_INVALIDCALL\n");
         return WINED3DERR_INVALIDCALL;
     }
-    if( (Divider & WINED3DSTREAMSOURCE_INSTANCEDATA) && StreamNumber == 0 ){
+    if ((Divider & WINED3DSTREAMSOURCE_INSTANCEDATA) && !StreamNumber)
+    {
         WARN("INSTANCEDATA used on stream 0, returning D3DERR_INVALIDCALL\n");
         return WINED3DERR_INVALIDCALL;
     }
-    if( Divider == 0 ){
+    if (!Divider)
+    {
         WARN("Divider is 0, returning D3DERR_INVALIDCALL\n");
         return WINED3DERR_INVALIDCALL;
     }
 
-    TRACE("(%p) StreamNumber(%d), Divider(%d)\n", This, StreamNumber, Divider);
-    This->updateStateBlock->streamFlags[StreamNumber] = Divider & (WINED3DSTREAMSOURCE_INSTANCEDATA  | WINED3DSTREAMSOURCE_INDEXEDDATA );
+    stream = &This->updateStateBlock->state.streams[StreamNumber];
+    oldFlags = stream->flags;
+    oldFreq = stream->frequency;
+
+    stream->flags = Divider & (WINED3DSTREAMSOURCE_INSTANCEDATA | WINED3DSTREAMSOURCE_INDEXEDDATA);
+    stream->frequency = Divider & 0x7FFFFF;
 
     This->updateStateBlock->changed.streamFreq |= 1 << StreamNumber;
-    This->updateStateBlock->streamFreq[StreamNumber]          = Divider & 0x7FFFFF;
 
-    if(This->updateStateBlock->streamFreq[StreamNumber] != oldFreq ||
-       This->updateStateBlock->streamFlags[StreamNumber] != oldFlags) {
+    if (stream->frequency != oldFreq || stream->flags != oldFlags)
         IWineD3DDeviceImpl_MarkStateDirty(This, STATE_STREAMSRC);
-    }
 
     return WINED3D_OK;
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_GetStreamSourceFreq(IWineD3DDevice *iface,  UINT StreamNumber, UINT* Divider) {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    struct wined3d_stream_state *stream;
+
+    TRACE("iface %p, stream_idx %u, divider %p.\n", iface, StreamNumber, Divider);
 
-    TRACE("(%p) StreamNumber(%d), Divider(%p)\n", This, StreamNumber, Divider);
-    *Divider = This->updateStateBlock->streamFreq[StreamNumber] | This->updateStateBlock->streamFlags[StreamNumber];
+    stream = &This->updateStateBlock->state.streams[StreamNumber];
+    *Divider = stream->flags | stream->frequency;
 
-    TRACE("(%p) : returning %d\n", This, *Divider);
+    TRACE("Returning %#x.\n", *Divider);
 
     return WINED3D_OK;
 }
@@ -2189,7 +2425,7 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_SetTransform(IWineD3DDevice *iface, W
     if (This->isRecordingState) {
         TRACE("Recording... not performing anything\n");
         This->updateStateBlock->changed.transform[d3dts >> 5] |= 1 << (d3dts & 0x1f);
-        This->updateStateBlock->transforms[d3dts] = *lpmatrix;
+        This->updateStateBlock->state.transforms[d3dts] = *lpmatrix;
         return WINED3D_OK;
     }
 
@@ -2201,11 +2437,14 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_SetTransform(IWineD3DDevice *iface, W
      *
      * From here on we assume that the new matrix is different, wherever it matters.
      */
-    if (!memcmp(&This->stateBlock->transforms[d3dts].u.m[0][0], lpmatrix, sizeof(WINED3DMATRIX))) {
+    if (!memcmp(&This->stateBlock->state.transforms[d3dts].u.m[0][0], lpmatrix, sizeof(*lpmatrix)))
+    {
         TRACE("The app is setting the same matrix over again\n");
         return WINED3D_OK;
-    } else {
-        conv_mat(lpmatrix, &This->stateBlock->transforms[d3dts].u.m[0][0]);
+    }
+    else
+    {
+        conv_mat(lpmatrix, &This->stateBlock->state.transforms[d3dts].u.m[0][0]);
     }
 
     /*
@@ -2222,14 +2461,22 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_SetTransform(IWineD3DDevice *iface, W
         /* Handled by the state manager */
     }
 
-    IWineD3DDeviceImpl_MarkStateDirty(This, STATE_TRANSFORM(d3dts));
+    if (d3dts < WINED3DTS_WORLDMATRIX(This->adapter->gl_info.limits.blends))
+        IWineD3DDeviceImpl_MarkStateDirty(This, STATE_TRANSFORM(d3dts));
+
     return WINED3D_OK;
 
 }
-static HRESULT WINAPI IWineD3DDeviceImpl_GetTransform(IWineD3DDevice *iface, WINED3DTRANSFORMSTATETYPE State, WINED3DMATRIX* pMatrix) {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    TRACE("(%p) : for Transform State %s\n", This, debug_d3dtstype(State));
-    *pMatrix = This->stateBlock->transforms[State];
+
+static HRESULT WINAPI IWineD3DDeviceImpl_GetTransform(IWineD3DDevice *iface,
+        WINED3DTRANSFORMSTATETYPE state, WINED3DMATRIX *matrix)
+{
+    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)iface;
+
+    TRACE("iface %p, state %s, matrix %p.\n", iface, debug_d3dtstype(state), matrix);
+
+    *matrix = device->stateBlock->state.transforms[state];
+
     return WINED3D_OK;
 }
 
@@ -2247,8 +2494,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_MultiplyTransform(IWineD3DDevice *iface
 
     if (State <= HIGHEST_TRANSFORMSTATE)
     {
-        mat = &This->updateStateBlock->transforms[State];
-    } else {
+        mat = &This->updateStateBlock->state.transforms[State];
+    }
+    else
+    {
         FIXME("Unhandled transform state!!\n");
     }
 
@@ -2308,7 +2557,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetLight(IWineD3DDevice *iface, DWORD I
         return WINED3DERR_INVALIDCALL;
     }
 
-    LIST_FOR_EACH(e, &This->updateStateBlock->lightMap[Hi])
+    LIST_FOR_EACH(e, &This->updateStateBlock->state.light_map[Hi])
     {
         object = LIST_ENTRY(e, struct wined3d_light_info, entry);
         if(object->OriginalIndex == Index) break;
@@ -2322,7 +2571,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetLight(IWineD3DDevice *iface, DWORD I
             ERR("Out of memory error when allocating a light\n");
             return E_OUTOFMEMORY;
         }
-        list_add_head(&This->updateStateBlock->lightMap[Hi], &object->entry);
+        list_add_head(&This->updateStateBlock->state.light_map[Hi], &object->entry);
         object->glIndex = -1;
         object->OriginalIndex = Index;
     }
@@ -2380,7 +2629,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetLight(IWineD3DDevice *iface, DWORD I
          * however spot lights are rather rarely used in games (if ever used at all).
          * furthermore if still used, probably nobody pays attention to such details.
          */
-        if (pLight->Falloff == 0) {
+        if (!pLight->Falloff)
+        {
             /* Falloff = 0 is easy, because d3d's and opengl's spot light equations have the
              * falloff resp. exponent parameter as an exponent, so the spot light lighting
              * will always be 1.0 for both of them, and we don't have to care for the
@@ -2396,7 +2646,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetLight(IWineD3DDevice *iface, DWORD I
         {
             object->exponent = 128.0f;
         }
-        object->cutoff = pLight->Phi*90/M_PI;
+        object->cutoff = (float) (pLight->Phi*90/M_PI);
 
         /* FIXME: Range */
         break;
@@ -2420,14 +2670,15 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetLight(IWineD3DDevice *iface, DWORD I
     struct list *e;
     TRACE("(%p) : Idx(%d), pLight(%p)\n", This, Index, pLight);
 
-    LIST_FOR_EACH(e, &This->stateBlock->lightMap[Hi])
+    LIST_FOR_EACH(e, &This->stateBlock->state.light_map[Hi])
     {
         lightInfo = LIST_ENTRY(e, struct wined3d_light_info, entry);
         if(lightInfo->OriginalIndex == Index) break;
         lightInfo = NULL;
     }
 
-    if (lightInfo == NULL) {
+    if (!lightInfo)
+    {
         TRACE("Light information requested but light not defined\n");
         return WINED3DERR_INVALIDCALL;
     }
@@ -2448,7 +2699,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetLightEnable(IWineD3DDevice *iface, D
     struct list *e;
     TRACE("(%p) : Idx(%d), enable? %d\n", This, Index, Enable);
 
-    LIST_FOR_EACH(e, &This->updateStateBlock->lightMap[Hi])
+    LIST_FOR_EACH(e, &This->updateStateBlock->state.light_map[Hi])
     {
         lightInfo = LIST_ENTRY(e, struct wined3d_light_info, entry);
         if(lightInfo->OriginalIndex == Index) break;
@@ -2457,19 +2708,20 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetLightEnable(IWineD3DDevice *iface, D
     TRACE("Found light: %p\n", lightInfo);
 
     /* Special case - enabling an undefined light creates one with a strict set of parms! */
-    if (lightInfo == NULL) {
-
+    if (!lightInfo)
+    {
         TRACE("Light enabled requested but light not defined, so defining one!\n");
         IWineD3DDeviceImpl_SetLight(iface, Index, &WINED3D_default_light);
 
         /* Search for it again! Should be fairly quick as near head of list */
-        LIST_FOR_EACH(e, &This->updateStateBlock->lightMap[Hi])
+        LIST_FOR_EACH(e, &This->updateStateBlock->state.light_map[Hi])
         {
             lightInfo = LIST_ENTRY(e, struct wined3d_light_info, entry);
             if(lightInfo->OriginalIndex == Index) break;
             lightInfo = NULL;
         }
-        if (lightInfo == NULL) {
+        if (!lightInfo)
+        {
             FIXME("Adding default lights has failed dismally\n");
             return WINED3DERR_INVALIDCALL;
         }
@@ -2481,7 +2733,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetLightEnable(IWineD3DDevice *iface, D
                 IWineD3DDeviceImpl_MarkStateDirty(This, STATE_ACTIVELIGHT(lightInfo->glIndex));
             }
 
-            This->updateStateBlock->activeLights[lightInfo->glIndex] = NULL;
+            This->updateStateBlock->state.lights[lightInfo->glIndex] = NULL;
             lightInfo->glIndex = -1;
         } else {
             TRACE("Light already disabled, nothing to do\n");
@@ -2495,9 +2747,11 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetLightEnable(IWineD3DDevice *iface, D
         } else {
             int i;
             /* Find a free gl light */
-            for(i = 0; i < This->maxConcurrentLights; i++) {
-                if(This->updateStateBlock->activeLights[i] == NULL) {
-                    This->updateStateBlock->activeLights[i] = lightInfo;
+            for (i = 0; i < This->maxConcurrentLights; ++i)
+            {
+                if (!This->updateStateBlock->state.lights[i])
+                {
+                    This->updateStateBlock->state.lights[i] = lightInfo;
                     lightInfo->glIndex = i;
                     break;
                 }
@@ -2532,14 +2786,15 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetLightEnable(IWineD3DDevice *iface, D
     UINT Hi = LIGHTMAP_HASHFUNC(Index);
     TRACE("(%p) : for idx(%d)\n", This, Index);
 
-    LIST_FOR_EACH(e, &This->stateBlock->lightMap[Hi])
+    LIST_FOR_EACH(e, &This->stateBlock->state.light_map[Hi])
     {
         lightInfo = LIST_ENTRY(e, struct wined3d_light_info, entry);
         if(lightInfo->OriginalIndex == Index) break;
         lightInfo = NULL;
     }
 
-    if (lightInfo == NULL) {
+    if (!lightInfo)
+    {
         TRACE("Light enabled state requested but light not defined\n");
         return WINED3DERR_INVALIDCALL;
     }
@@ -2564,18 +2819,19 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetClipPlane(IWineD3DDevice *iface, DWO
 
     This->updateStateBlock->changed.clipplane |= 1 << Index;
 
-    if(This->updateStateBlock->clipplane[Index][0] == pPlane[0] &&
-       This->updateStateBlock->clipplane[Index][1] == pPlane[1] &&
-       This->updateStateBlock->clipplane[Index][2] == pPlane[2] &&
-       This->updateStateBlock->clipplane[Index][3] == pPlane[3]) {
+    if (This->updateStateBlock->state.clip_planes[Index][0] == pPlane[0]
+            && This->updateStateBlock->state.clip_planes[Index][1] == pPlane[1]
+            && This->updateStateBlock->state.clip_planes[Index][2] == pPlane[2]
+            && This->updateStateBlock->state.clip_planes[Index][3] == pPlane[3])
+    {
         TRACE("Application is setting old values over, nothing to do\n");
         return WINED3D_OK;
     }
 
-    This->updateStateBlock->clipplane[Index][0] = pPlane[0];
-    This->updateStateBlock->clipplane[Index][1] = pPlane[1];
-    This->updateStateBlock->clipplane[Index][2] = pPlane[2];
-    This->updateStateBlock->clipplane[Index][3] = pPlane[3];
+    This->updateStateBlock->state.clip_planes[Index][0] = pPlane[0];
+    This->updateStateBlock->state.clip_planes[Index][1] = pPlane[1];
+    This->updateStateBlock->state.clip_planes[Index][2] = pPlane[2];
+    This->updateStateBlock->state.clip_planes[Index][3] = pPlane[3];
 
     /* Handle recording of state blocks */
     if (This->isRecordingState) {
@@ -2599,10 +2855,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetClipPlane(IWineD3DDevice *iface, DWO
         return WINED3DERR_INVALIDCALL;
     }
 
-    pPlane[0] = This->stateBlock->clipplane[Index][0];
-    pPlane[1] = This->stateBlock->clipplane[Index][1];
-    pPlane[2] = This->stateBlock->clipplane[Index][2];
-    pPlane[3] = This->stateBlock->clipplane[Index][3];
+    pPlane[0] = (float)This->stateBlock->state.clip_planes[Index][0];
+    pPlane[1] = (float)This->stateBlock->state.clip_planes[Index][1];
+    pPlane[2] = (float)This->stateBlock->state.clip_planes[Index][2];
+    pPlane[3] = (float)This->stateBlock->state.clip_planes[Index][3];
     return WINED3D_OK;
 }
 
@@ -2613,22 +2869,24 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetClipPlane(IWineD3DDevice *iface, DWO
 static HRESULT  WINAPI  IWineD3DDeviceImpl_SetClipStatus(IWineD3DDevice *iface, CONST WINED3DCLIPSTATUS* pClipStatus) {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     FIXME("(%p) : stub\n", This);
-    if (NULL == pClipStatus) {
-      return WINED3DERR_INVALIDCALL;
-    }
-    This->updateStateBlock->clip_status.ClipUnion = pClipStatus->ClipUnion;
-    This->updateStateBlock->clip_status.ClipIntersection = pClipStatus->ClipIntersection;
+
+    if (!pClipStatus)
+        return WINED3DERR_INVALIDCALL;
+
+    This->updateStateBlock->state.clip_status.ClipUnion = pClipStatus->ClipUnion;
+    This->updateStateBlock->state.clip_status.ClipIntersection = pClipStatus->ClipIntersection;
     return WINED3D_OK;
 }
 
 static HRESULT  WINAPI  IWineD3DDeviceImpl_GetClipStatus(IWineD3DDevice *iface, WINED3DCLIPSTATUS* pClipStatus) {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     FIXME("(%p) : stub\n", This);
-    if (NULL == pClipStatus) {
-      return WINED3DERR_INVALIDCALL;
-    }
-    pClipStatus->ClipUnion = This->updateStateBlock->clip_status.ClipUnion;
-    pClipStatus->ClipIntersection = This->updateStateBlock->clip_status.ClipIntersection;
+
+    if (!pClipStatus)
+        return WINED3DERR_INVALIDCALL;
+
+    pClipStatus->ClipUnion = This->updateStateBlock->state.clip_status.ClipUnion;
+    pClipStatus->ClipIntersection = This->updateStateBlock->state.clip_status.ClipIntersection;
     return WINED3D_OK;
 }
 
@@ -2639,7 +2897,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetMaterial(IWineD3DDevice *iface, CONS
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
 
     This->updateStateBlock->changed.material = TRUE;
-    This->updateStateBlock->material = *pMaterial;
+    This->updateStateBlock->state.material = *pMaterial;
 
     /* Handle recording of state blocks */
     if (This->isRecordingState) {
@@ -2653,7 +2911,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetMaterial(IWineD3DDevice *iface, CONS
 
 static HRESULT WINAPI IWineD3DDeviceImpl_GetMaterial(IWineD3DDevice *iface, WINED3DMATERIAL* pMaterial) {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    *pMaterial = This->updateStateBlock->material;
+    *pMaterial = This->updateStateBlock->state.material;
     TRACE("(%p) : Diffuse (%f,%f,%f,%f)\n", This, pMaterial->Diffuse.r, pMaterial->Diffuse.g,
         pMaterial->Diffuse.b, pMaterial->Diffuse.a);
     TRACE("(%p) : Ambient (%f,%f,%f,%f)\n", This, pMaterial->Ambient.r, pMaterial->Ambient.g,
@@ -2671,17 +2929,17 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetMaterial(IWineD3DDevice *iface, WINE
  * Get / Set Indices
  *****/
 static HRESULT WINAPI IWineD3DDeviceImpl_SetIndexBuffer(IWineD3DDevice *iface,
-        IWineD3DBuffer *pIndexData, WINED3DFORMAT fmt)
+        IWineD3DBuffer *pIndexData, enum wined3d_format_id fmt)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DBuffer *oldIdxs;
 
     TRACE("(%p) : Setting to %p\n", This, pIndexData);
-    oldIdxs = This->updateStateBlock->pIndexData;
+    oldIdxs = (IWineD3DBuffer *)This->updateStateBlock->state.index_buffer;
 
     This->updateStateBlock->changed.indices = TRUE;
-    This->updateStateBlock->pIndexData = pIndexData;
-    This->updateStateBlock->IndexFmt = fmt;
+    This->updateStateBlock->state.index_buffer = (struct wined3d_buffer *)pIndexData;
+    This->updateStateBlock->state.index_format = fmt;
 
     /* Handle recording of state blocks */
     if (This->isRecordingState) {
@@ -2710,7 +2968,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetIndexBuffer(IWineD3DDevice *iface, I
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
 
-    *ppIndexData = This->stateBlock->pIndexData;
+    *ppIndexData = (IWineD3DBuffer *)This->stateBlock->state.index_buffer;
 
     /* up ref count on ppindexdata */
     if (*ppIndexData) {
@@ -2729,12 +2987,13 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetBaseVertexIndex(IWineD3DDevice *ifac
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     TRACE("(%p)->(%d)\n", This, BaseIndex);
 
-    if(This->updateStateBlock->baseVertexIndex == BaseIndex) {
+    if (This->updateStateBlock->state.base_vertex_index == BaseIndex)
+    {
         TRACE("Application is setting the old value over, nothing to do\n");
         return WINED3D_OK;
     }
 
-    This->updateStateBlock->baseVertexIndex = BaseIndex;
+    This->updateStateBlock->state.base_vertex_index = BaseIndex;
 
     if (This->isRecordingState) {
         TRACE("Recording... not performing anything\n");
@@ -2749,7 +3008,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetBaseVertexIndex(IWineD3DDevice *ifac
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     TRACE("(%p) : base_index %p\n", This, base_index);
 
-    *base_index = This->stateBlock->baseVertexIndex;
+    *base_index = This->stateBlock->state.base_vertex_index;
 
     TRACE("Returning %u\n", *base_index);
 
@@ -2764,7 +3023,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetViewport(IWineD3DDevice *iface, CONS
 
     TRACE("(%p)\n", This);
     This->updateStateBlock->changed.viewport = TRUE;
-    This->updateStateBlock->viewport = *pViewport;
+    This->updateStateBlock->state.viewport = *pViewport;
 
     /* Handle recording of state blocks */
     if (This->isRecordingState) {
@@ -2783,23 +3042,20 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetViewport(IWineD3DDevice *iface, CONS
 static HRESULT WINAPI IWineD3DDeviceImpl_GetViewport(IWineD3DDevice *iface, WINED3DVIEWPORT* pViewport) {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     TRACE("(%p)\n", This);
-    *pViewport = This->stateBlock->viewport;
+    *pViewport = This->stateBlock->state.viewport;
     return WINED3D_OK;
 }
 
-/*****
- * Get / Set Render States
- * TODO: Verify against dx9 definitions
- *****/
-static HRESULT WINAPI IWineD3DDeviceImpl_SetRenderState(IWineD3DDevice *iface, WINED3DRENDERSTATETYPE State, DWORD Value) {
-
-    IWineD3DDeviceImpl  *This     = (IWineD3DDeviceImpl *)iface;
-    DWORD oldValue = This->stateBlock->renderState[State];
+static HRESULT WINAPI IWineD3DDeviceImpl_SetRenderState(IWineD3DDevice *iface,
+        WINED3DRENDERSTATETYPE State, DWORD Value)
+{
+    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    DWORD oldValue = This->stateBlock->state.render_states[State];
 
-    TRACE("(%p)->state = %s(%d), value = %d\n", This, debug_d3drenderstate(State), State, Value);
+    TRACE("iface %p, state %s (%#x), value %#x.\n", iface, debug_d3drenderstate(State), State, Value);
 
     This->updateStateBlock->changed.renderState[State >> 5] |= 1 << (State & 0x1f);
-    This->updateStateBlock->renderState[State] = Value;
+    This->updateStateBlock->state.render_states[State] = Value;
 
     /* Handle recording of state blocks */
     if (This->isRecordingState) {
@@ -2817,10 +3073,14 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetRenderState(IWineD3DDevice *iface, W
     return WINED3D_OK;
 }
 
-static HRESULT WINAPI IWineD3DDeviceImpl_GetRenderState(IWineD3DDevice *iface, WINED3DRENDERSTATETYPE State, DWORD *pValue) {
+static HRESULT WINAPI IWineD3DDeviceImpl_GetRenderState(IWineD3DDevice *iface,
+        WINED3DRENDERSTATETYPE State, DWORD *pValue)
+{
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    TRACE("(%p) for State %d = %d\n", This, State, This->stateBlock->renderState[State]);
-    *pValue = This->stateBlock->renderState[State];
+
+    TRACE("iface %p, state %s (%#x), value %p.\n", iface, debug_d3drenderstate(State), State, pValue);
+
+    *pValue = This->stateBlock->state.render_states[State];
     return WINED3D_OK;
 }
 
@@ -2840,27 +3100,14 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetSamplerState(IWineD3DDevice *iface,
         Sampler -= (WINED3DVERTEXTEXTURESAMPLER0 - MAX_FRAGMENT_SAMPLERS);
     }
 
-    if (Sampler >= sizeof(This->stateBlock->samplerState)/sizeof(This->stateBlock->samplerState[0])) {
+    if (Sampler >= sizeof(This->stateBlock->state.sampler_states) / sizeof(*This->stateBlock->state.sampler_states))
+    {
         ERR("Current Sampler overflows sampleState0 array (sampler %d)\n", Sampler);
         return WINED3D_OK; /* Windows accepts overflowing this array ... we do not. */
     }
-    /**
-    * SetSampler is designed to allow for more than the standard up to 8 textures
-    *  and Geforce has stopped supporting more than 6 standard textures in openGL.
-    * So I have to use ARB for Gforce. (maybe if the sampler > 4 then use ARB?)
-    *
-    * http://developer.nvidia.com/object/General_FAQ.html#t6
-    *
-    * There are two new settings for GForce
-    * the sampler one:
-    * GL_MAX_TEXTURE_IMAGE_UNITS_ARB
-    * and the texture one:
-    * GL_MAX_TEXTURE_COORDS_ARB.
-    * Ok GForce say it's ok to use glTexParameter/glGetTexParameter(...).
-     ******************/
-
-    oldValue = This->stateBlock->samplerState[Sampler][Type];
-    This->updateStateBlock->samplerState[Sampler][Type]         = Value;
+
+    oldValue = This->stateBlock->state.sampler_states[Sampler][Type];
+    This->updateStateBlock->state.sampler_states[Sampler][Type] = Value;
     This->updateStateBlock->changed.samplerState[Sampler] |= 1 << Type;
 
     /* Handle recording of state blocks */
@@ -2889,11 +3136,12 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetSamplerState(IWineD3DDevice *iface,
         Sampler -= (WINED3DVERTEXTEXTURESAMPLER0 - MAX_FRAGMENT_SAMPLERS);
     }
 
-    if (Sampler >= sizeof(This->stateBlock->samplerState)/sizeof(This->stateBlock->samplerState[0])) {
+    if (Sampler >= sizeof(This->stateBlock->state.sampler_states) / sizeof(*This->stateBlock->state.sampler_states))
+    {
         ERR("Current Sampler overflows sampleState0 array (sampler %d)\n", Sampler);
         return WINED3D_OK; /* Windows accepts overflowing this array ... we do not. */
     }
-    *Value = This->stateBlock->samplerState[Sampler][Type];
+    *Value = This->stateBlock->state.sampler_states[Sampler][Type];
     TRACE("(%p) : Returning %#x\n", This, *Value);
 
     return WINED3D_OK;
@@ -2903,11 +3151,12 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetScissorRect(IWineD3DDevice *iface, C
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
 
     This->updateStateBlock->changed.scissorRect = TRUE;
-    if(EqualRect(&This->updateStateBlock->scissorRect, pRect)) {
-        TRACE("App is setting the old scissor rectangle over, nothing to do\n");
+    if (EqualRect(&This->updateStateBlock->state.scissor_rect, pRect))
+    {
+        TRACE("App is setting the old scissor rectangle over, nothing to do.\n");
         return WINED3D_OK;
     }
-    CopyRect(&This->updateStateBlock->scissorRect, pRect);
+    CopyRect(&This->updateStateBlock->state.scissor_rect, pRect);
 
     if(This->isRecordingState) {
         TRACE("Recording... not performing anything\n");
@@ -2922,21 +3171,21 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetScissorRect(IWineD3DDevice *iface, C
 static HRESULT WINAPI IWineD3DDeviceImpl_GetScissorRect(IWineD3DDevice *iface, RECT* pRect) {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
 
-    *pRect = This->updateStateBlock->scissorRect;
+    *pRect = This->updateStateBlock->state.scissor_rect;
     TRACE("(%p)Returning a Scissor Rect of %d:%d-%d:%d\n", This, pRect->left, pRect->top, pRect->right, pRect->bottom);
     return WINED3D_OK;
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_SetVertexDeclaration(IWineD3DDevice* iface, IWineD3DVertexDeclaration* pDecl) {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
-    IWineD3DVertexDeclaration *oldDecl = This->updateStateBlock->vertexDecl;
+    IWineD3DVertexDeclaration *oldDecl = (IWineD3DVertexDeclaration *)This->updateStateBlock->state.vertex_declaration;
 
     TRACE("(%p) : pDecl=%p\n", This, pDecl);
 
     if (pDecl) IWineD3DVertexDeclaration_AddRef(pDecl);
     if (oldDecl) IWineD3DVertexDeclaration_Release(oldDecl);
 
-    This->updateStateBlock->vertexDecl = pDecl;
+    This->updateStateBlock->state.vertex_declaration = (IWineD3DVertexDeclarationImpl *)pDecl;
     This->updateStateBlock->changed.vertexDecl = TRUE;
 
     if (This->isRecordingState) {
@@ -2957,16 +3206,17 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetVertexDeclaration(IWineD3DDevice* if
 
     TRACE("(%p) : ppDecl=%p\n", This, ppDecl);
 
-    *ppDecl = This->stateBlock->vertexDecl;
-    if (NULL != *ppDecl) IWineD3DVertexDeclaration_AddRef(*ppDecl);
+    *ppDecl = (IWineD3DVertexDeclaration *)This->stateBlock->state.vertex_declaration;
+    if (*ppDecl) IWineD3DVertexDeclaration_AddRef(*ppDecl);
     return WINED3D_OK;
 }
 
-static HRESULT WINAPI IWineD3DDeviceImpl_SetVertexShader(IWineD3DDevice *iface, IWineD3DVertexShader* pShader) {
-    IWineD3DDeviceImpl *This        = (IWineD3DDeviceImpl *)iface;
-    IWineD3DVertexShader* oldShader = This->updateStateBlock->vertexShader;
+static HRESULT WINAPI IWineD3DDeviceImpl_SetVertexShader(IWineD3DDevice *iface, IWineD3DVertexShader *pShader)
+{
+    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    IWineD3DVertexShader *oldShader = (IWineD3DVertexShader *)This->updateStateBlock->state.vertex_shader;
 
-    This->updateStateBlock->vertexShader         = pShader;
+    This->updateStateBlock->state.vertex_shader = (IWineD3DVertexShaderImpl *)pShader;
     This->updateStateBlock->changed.vertexShader = TRUE;
 
     if (This->isRecordingState) {
@@ -2989,18 +3239,18 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetVertexShader(IWineD3DDevice *iface,
     return WINED3D_OK;
 }
 
-static HRESULT WINAPI IWineD3DDeviceImpl_GetVertexShader(IWineD3DDevice *iface, IWineD3DVertexShader** ppShader) {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+static IWineD3DVertexShader * WINAPI IWineD3DDeviceImpl_GetVertexShader(IWineD3DDevice *iface)
+{
+    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)iface;
+    IWineD3DVertexShader *shader;
 
-    if (NULL == ppShader) {
-        return WINED3DERR_INVALIDCALL;
-    }
-    *ppShader = This->stateBlock->vertexShader;
-    if( NULL != *ppShader)
-        IWineD3DVertexShader_AddRef(*ppShader);
+    TRACE("iface %p.\n", iface);
 
-    TRACE("(%p) : returning %p\n", This, *ppShader);
-    return WINED3D_OK;
+    shader = (IWineD3DVertexShader *)device->stateBlock->state.vertex_shader;
+    if (shader) IWineD3DVertexShader_AddRef(shader);
+
+    TRACE("Returning %p.\n", shader);
+    return shader;
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_SetVertexShaderConstantB(
@@ -3017,7 +3267,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetVertexShaderConstantB(
 
     if (!srcData || start >= MAX_CONST_B) return WINED3DERR_INVALIDCALL;
 
-    memcpy(&This->updateStateBlock->vertexShaderConstantB[start], srcData, cnt * sizeof(BOOL));
+    memcpy(&This->updateStateBlock->state.vs_consts_b[start], srcData, cnt * sizeof(BOOL));
     for (i = 0; i < cnt; i++)
         TRACE("Set BOOL constant %u to %s\n", start + i, srcData[i]? "true":"false");
 
@@ -3042,10 +3292,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetVertexShaderConstantB(
     TRACE("(iface %p, dstData %p, start %d, count %d)\n",
             iface, dstData, start, count);
 
-    if (dstData == NULL || cnt < 0)
+    if (!dstData || cnt < 0)
         return WINED3DERR_INVALIDCALL;
 
-    memcpy(dstData, &This->stateBlock->vertexShaderConstantB[start], cnt * sizeof(BOOL));
+    memcpy(dstData, &This->stateBlock->state.vs_consts_b[start], cnt * sizeof(BOOL));
     return WINED3D_OK;
 }
 
@@ -3063,7 +3313,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetVertexShaderConstantI(
 
     if (!srcData || start >= MAX_CONST_I) return WINED3DERR_INVALIDCALL;
 
-    memcpy(&This->updateStateBlock->vertexShaderConstantI[start * 4], srcData, cnt * sizeof(int) * 4);
+    memcpy(&This->updateStateBlock->state.vs_consts_i[start * 4], srcData, cnt * sizeof(int) * 4);
     for (i = 0; i < cnt; i++)
         TRACE("Set INT constant %u to { %d, %d, %d, %d }\n", start + i,
            srcData[i*4], srcData[i*4+1], srcData[i*4+2], srcData[i*4+3]);
@@ -3089,10 +3339,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetVertexShaderConstantI(
     TRACE("(iface %p, dstData %p, start %d, count %d)\n",
             iface, dstData, start, count);
 
-    if (dstData == NULL || ((signed int) MAX_CONST_I - (signed int) start) <= 0)
+    if (!dstData || ((signed int)MAX_CONST_I - (signed int)start) <= 0)
         return WINED3DERR_INVALIDCALL;
 
-    memcpy(dstData, &This->stateBlock->vertexShaderConstantI[start * 4], cnt * sizeof(int) * 4);
+    memcpy(dstData, &This->stateBlock->state.vs_consts_i[start * 4], cnt * sizeof(int) * 4);
     return WINED3D_OK;
 }
 
@@ -3109,10 +3359,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetVertexShaderConstantF(
             iface, srcData, start, count);
 
     /* Specifically test start > limit to catch MAX_UINT overflows when adding start + count */
-    if (srcData == NULL || start + count > This->d3d_vshader_constantF || start > This->d3d_vshader_constantF)
+    if (!srcData || start + count > This->d3d_vshader_constantF || start > This->d3d_vshader_constantF)
         return WINED3DERR_INVALIDCALL;
 
-    memcpy(&This->updateStateBlock->vertexShaderConstantF[start * 4], srcData, count * sizeof(float) * 4);
+    memcpy(&This->updateStateBlock->state.vs_consts_f[start * 4], srcData, count * sizeof(float) * 4);
     if(TRACE_ON(d3d)) {
         for (i = 0; i < count; i++)
             TRACE("Set FLOAT constant %u to { %f, %f, %f, %f }\n", start + i,
@@ -3143,10 +3393,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetVertexShaderConstantF(
     TRACE("(iface %p, dstData %p, start %d, count %d)\n",
             iface, dstData, start, count);
 
-    if (dstData == NULL || cnt < 0)
+    if (!dstData || cnt < 0)
         return WINED3DERR_INVALIDCALL;
 
-    memcpy(dstData, &This->stateBlock->vertexShaderConstantF[start * 4], cnt * sizeof(float) * 4);
+    memcpy(dstData, &This->stateBlock->state.vs_consts_f[start * 4], cnt * sizeof(float) * 4);
     return WINED3D_OK;
 }
 
@@ -3180,15 +3430,17 @@ static void device_update_fixed_function_usage_map(IWineD3DDeviceImpl *This) {
     int i;
 
     This->fixed_function_usage_map = 0;
-    for (i = 0; i < MAX_TEXTURES; ++i) {
-        WINED3DTEXTUREOP color_op = This->stateBlock->textureState[i][WINED3DTSS_COLOROP];
-        WINED3DTEXTUREOP alpha_op = This->stateBlock->textureState[i][WINED3DTSS_ALPHAOP];
-        DWORD color_arg1 = This->stateBlock->textureState[i][WINED3DTSS_COLORARG1] & WINED3DTA_SELECTMASK;
-        DWORD color_arg2 = This->stateBlock->textureState[i][WINED3DTSS_COLORARG2] & WINED3DTA_SELECTMASK;
-        DWORD color_arg3 = This->stateBlock->textureState[i][WINED3DTSS_COLORARG0] & WINED3DTA_SELECTMASK;
-        DWORD alpha_arg1 = This->stateBlock->textureState[i][WINED3DTSS_ALPHAARG1] & WINED3DTA_SELECTMASK;
-        DWORD alpha_arg2 = This->stateBlock->textureState[i][WINED3DTSS_ALPHAARG2] & WINED3DTA_SELECTMASK;
-        DWORD alpha_arg3 = This->stateBlock->textureState[i][WINED3DTSS_ALPHAARG0] & WINED3DTA_SELECTMASK;
+    for (i = 0; i < MAX_TEXTURES; ++i)
+    {
+        const struct wined3d_state *state = &This->stateBlock->state;
+        WINED3DTEXTUREOP color_op = state->texture_states[i][WINED3DTSS_COLOROP];
+        WINED3DTEXTUREOP alpha_op = state->texture_states[i][WINED3DTSS_ALPHAOP];
+        DWORD color_arg1 = state->texture_states[i][WINED3DTSS_COLORARG1] & WINED3DTA_SELECTMASK;
+        DWORD color_arg2 = state->texture_states[i][WINED3DTSS_COLORARG2] & WINED3DTA_SELECTMASK;
+        DWORD color_arg3 = state->texture_states[i][WINED3DTSS_COLORARG0] & WINED3DTA_SELECTMASK;
+        DWORD alpha_arg1 = state->texture_states[i][WINED3DTSS_ALPHAARG1] & WINED3DTA_SELECTMASK;
+        DWORD alpha_arg2 = state->texture_states[i][WINED3DTSS_ALPHAARG2] & WINED3DTA_SELECTMASK;
+        DWORD alpha_arg3 = state->texture_states[i][WINED3DTSS_ALPHAARG0] & WINED3DTA_SELECTMASK;
 
         if (color_op == WINED3DTOP_DISABLE) {
             /* Not used, and disable higher stages */
@@ -3219,7 +3471,7 @@ static void device_map_fixed_function_samplers(IWineD3DDeviceImpl *This, const s
     ffu_map = This->fixed_function_usage_map;
 
     if (This->max_ffp_textures == gl_info->limits.texture_stages
-            || This->stateBlock->lowest_disabled_stage <= This->max_ffp_textures)
+            || This->stateBlock->state.lowest_disabled_stage <= This->max_ffp_textures)
     {
         for (i = 0; ffu_map; ffu_map >>= 1, ++i)
         {
@@ -3253,7 +3505,7 @@ static void device_map_fixed_function_samplers(IWineD3DDeviceImpl *This, const s
 static void device_map_psamplers(IWineD3DDeviceImpl *This, const struct wined3d_gl_info *gl_info)
 {
     const WINED3DSAMPLER_TEXTURE_TYPE *sampler_type =
-            ((IWineD3DPixelShaderImpl *)This->stateBlock->pixelShader)->baseShader.reg_maps.sampler_type;
+            This->stateBlock->state.pixel_shader->baseShader.reg_maps.sampler_type;
     unsigned int i;
 
     for (i = 0; i < MAX_FRAGMENT_SAMPLERS; ++i) {
@@ -3269,8 +3521,8 @@ static void device_map_psamplers(IWineD3DDeviceImpl *This, const struct wined3d_
     }
 }
 
-static BOOL device_unit_free_for_vs(IWineD3DDeviceImpl *This, const DWORD *pshader_sampler_tokens,
-        const DWORD *vshader_sampler_tokens, DWORD unit)
+static BOOL device_unit_free_for_vs(IWineD3DDeviceImpl *This, const WINED3DSAMPLER_TEXTURE_TYPE *pshader_sampler_tokens,
+        const WINED3DSAMPLER_TEXTURE_TYPE *vshader_sampler_tokens, DWORD unit)
 {
     DWORD current_mapping = This->rev_tex_unit_map[unit];
 
@@ -3296,13 +3548,14 @@ static BOOL device_unit_free_for_vs(IWineD3DDeviceImpl *This, const DWORD *pshad
 static void device_map_vsamplers(IWineD3DDeviceImpl *This, BOOL ps, const struct wined3d_gl_info *gl_info)
 {
     const WINED3DSAMPLER_TEXTURE_TYPE *vshader_sampler_type =
-            ((IWineD3DVertexShaderImpl *)This->stateBlock->vertexShader)->baseShader.reg_maps.sampler_type;
+            This->stateBlock->state.vertex_shader->baseShader.reg_maps.sampler_type;
     const WINED3DSAMPLER_TEXTURE_TYPE *pshader_sampler_type = NULL;
     int start = min(MAX_COMBINED_SAMPLERS, gl_info->limits.combined_samplers) - 1;
     int i;
 
-    if (ps) {
-        IWineD3DPixelShaderImpl *pshader = (IWineD3DPixelShaderImpl *)This->stateBlock->pixelShader;
+    if (ps)
+    {
+        IWineD3DPixelShaderImpl *pshader = This->stateBlock->state.pixel_shader;
 
         /* Note that we only care if a sampler is sampled or not, not the sampler's specific type.
          * Otherwise we'd need to call shader_update_samplers() here for 1.x pixelshaders. */
@@ -3338,8 +3591,9 @@ static void device_map_vsamplers(IWineD3DDeviceImpl *This, BOOL ps, const struct
 void IWineD3DDeviceImpl_FindTexUnitMap(IWineD3DDeviceImpl *This)
 {
     const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
-    BOOL vs = use_vs(This->stateBlock);
-    BOOL ps = use_ps(This->stateBlock);
+    const struct wined3d_state *state = &This->stateBlock->state;
+    BOOL vs = use_vs(state);
+    BOOL ps = use_ps(state);
     /*
      * Rules are:
      * -> Pixel shaders need a 1:1 map. In theory the shader input could be mapped too, but
@@ -3353,10 +3607,11 @@ void IWineD3DDeviceImpl_FindTexUnitMap(IWineD3DDeviceImpl *This)
     if (vs) device_map_vsamplers(This, ps, gl_info);
 }
 
-static HRESULT WINAPI IWineD3DDeviceImpl_SetPixelShader(IWineD3DDevice *iface, IWineD3DPixelShader *pShader) {
-    IWineD3DDeviceImpl *This        = (IWineD3DDeviceImpl *)iface;
-    IWineD3DPixelShader *oldShader  = This->updateStateBlock->pixelShader;
-    This->updateStateBlock->pixelShader         = pShader;
+static HRESULT WINAPI IWineD3DDeviceImpl_SetPixelShader(IWineD3DDevice *iface, IWineD3DPixelShader *pShader)
+{
+    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    IWineD3DPixelShader *oldShader = (IWineD3DPixelShader *)This->updateStateBlock->state.pixel_shader;
+    This->updateStateBlock->state.pixel_shader = (IWineD3DPixelShaderImpl *)pShader;
     This->updateStateBlock->changed.pixelShader = TRUE;
 
     /* Handle recording of state blocks */
@@ -3385,20 +3640,18 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetPixelShader(IWineD3DDevice *iface, I
     return WINED3D_OK;
 }
 
-static HRESULT WINAPI IWineD3DDeviceImpl_GetPixelShader(IWineD3DDevice *iface, IWineD3DPixelShader **ppShader) {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+static IWineD3DPixelShader * WINAPI IWineD3DDeviceImpl_GetPixelShader(IWineD3DDevice *iface)
+{
+    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)iface;
+    IWineD3DPixelShader *shader;
 
-    if (NULL == ppShader) {
-        WARN("(%p) : PShader is NULL, returning INVALIDCALL\n", This);
-        return WINED3DERR_INVALIDCALL;
-    }
+    TRACE("iface %p.\n", iface);
 
-    *ppShader =  This->stateBlock->pixelShader;
-    if (NULL != *ppShader) {
-        IWineD3DPixelShader_AddRef(*ppShader);
-    }
-    TRACE("(%p) : returning %p\n", This, *ppShader);
-    return WINED3D_OK;
+    shader = (IWineD3DPixelShader *)device->stateBlock->state.pixel_shader;
+    if (shader) IWineD3DPixelShader_AddRef(shader);
+
+    TRACE("Returning %p.\n", shader);
+    return shader;
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_SetPixelShaderConstantB(
@@ -3415,7 +3668,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetPixelShaderConstantB(
 
     if (!srcData || start >= MAX_CONST_B) return WINED3DERR_INVALIDCALL;
 
-    memcpy(&This->updateStateBlock->pixelShaderConstantB[start], srcData, cnt * sizeof(BOOL));
+    memcpy(&This->updateStateBlock->state.ps_consts_b[start], srcData, cnt * sizeof(BOOL));
     for (i = 0; i < cnt; i++)
         TRACE("Set BOOL constant %u to %s\n", start + i, srcData[i]? "true":"false");
 
@@ -3440,10 +3693,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetPixelShaderConstantB(
     TRACE("(iface %p, dstData %p, start %d, count %d)\n",
             iface, dstData, start, count);
 
-    if (dstData == NULL || cnt < 0)
+    if (!dstData || cnt < 0)
         return WINED3DERR_INVALIDCALL;
 
-    memcpy(dstData, &This->stateBlock->pixelShaderConstantB[start], cnt * sizeof(BOOL));
+    memcpy(dstData, &This->stateBlock->state.ps_consts_b[start], cnt * sizeof(BOOL));
     return WINED3D_OK;
 }
 
@@ -3461,7 +3714,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetPixelShaderConstantI(
 
     if (!srcData || start >= MAX_CONST_I) return WINED3DERR_INVALIDCALL;
 
-    memcpy(&This->updateStateBlock->pixelShaderConstantI[start * 4], srcData, cnt * sizeof(int) * 4);
+    memcpy(&This->updateStateBlock->state.ps_consts_i[start * 4], srcData, cnt * sizeof(int) * 4);
     for (i = 0; i < cnt; i++)
         TRACE("Set INT constant %u to { %d, %d, %d, %d }\n", start + i,
            srcData[i*4], srcData[i*4+1], srcData[i*4+2], srcData[i*4+3]);
@@ -3487,10 +3740,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetPixelShaderConstantI(
     TRACE("(iface %p, dstData %p, start %d, count %d)\n",
             iface, dstData, start, count);
 
-    if (dstData == NULL || cnt < 0)
+    if (!dstData || cnt < 0)
         return WINED3DERR_INVALIDCALL;
 
-    memcpy(dstData, &This->stateBlock->pixelShaderConstantI[start * 4], cnt * sizeof(int) * 4);
+    memcpy(dstData, &This->stateBlock->state.ps_consts_i[start * 4], cnt * sizeof(int) * 4);
     return WINED3D_OK;
 }
 
@@ -3507,10 +3760,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetPixelShaderConstantF(
             iface, srcData, start, count);
 
     /* Specifically test start > limit to catch MAX_UINT overflows when adding start + count */
-    if (srcData == NULL || start + count > This->d3d_pshader_constantF || start > This->d3d_pshader_constantF)
+    if (!srcData || start + count > This->d3d_pshader_constantF || start > This->d3d_pshader_constantF)
         return WINED3DERR_INVALIDCALL;
 
-    memcpy(&This->updateStateBlock->pixelShaderConstantF[start * 4], srcData, count * sizeof(float) * 4);
+    memcpy(&This->updateStateBlock->state.ps_consts_f[start * 4], srcData, count * sizeof(float) * 4);
     if(TRACE_ON(d3d)) {
         for (i = 0; i < count; i++)
             TRACE("Set FLOAT constant %u to { %f, %f, %f, %f }\n", start + i,
@@ -3541,14 +3794,15 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetPixelShaderConstantF(
     TRACE("(iface %p, dstData %p, start %d, count %d)\n",
             iface, dstData, start, count);
 
-    if (dstData == NULL || cnt < 0)
+    if (!dstData || cnt < 0)
         return WINED3DERR_INVALIDCALL;
 
-    memcpy(dstData, &This->stateBlock->pixelShaderConstantF[start * 4], cnt * sizeof(float) * 4);
+    memcpy(dstData, &This->stateBlock->state.ps_consts_f[start * 4], cnt * sizeof(float) * 4);
     return WINED3D_OK;
 }
 
 /* Context activation is done by the caller. */
+/* Do not call while under the GL lock. */
 #define copy_and_next(dest, src, size) memcpy(dest, src, size); dest += (size)
 static HRESULT process_vertices_strided(IWineD3DDeviceImpl *This, DWORD dwDestIndex, DWORD dwCount,
         const struct wined3d_stream_info *stream_info, struct wined3d_buffer *dest, DWORD dwFlags,
@@ -3573,9 +3827,6 @@ static HRESULT process_vertices_strided(IWineD3DDeviceImpl *This, DWORD dwDestIn
         return WINED3DERR_INVALIDCALL;
     }
 
-    /* We might access VBOs from this code, so hold the lock */
-    ENTER_GL();
-
     if (!dest->resource.allocatedMemory)
         buffer_get_sysmem(dest, gl_info);
 
@@ -3604,11 +3855,8 @@ static HRESULT process_vertices_strided(IWineD3DDeviceImpl *This, DWORD dwDestIn
         dest_conv = dest_conv_addr;
     }
 
-    /* Should I clip?
-     * a) WINED3DRS_CLIPPING is enabled
-     * b) WINED3DVOP_CLIP is passed
-     */
-    if(This->stateBlock->renderState[WINED3DRS_CLIPPING]) {
+    if (This->stateBlock->state.render_states[WINED3DRS_CLIPPING])
+    {
         static BOOL warned = FALSE;
         /*
          * The clipping code is not quite correct. Some things need
@@ -3878,22 +4126,27 @@ static HRESULT process_vertices_strided(IWineD3DDeviceImpl *This, DWORD dwDestIn
         }
     }
 
-    if(dest_conv) {
+    if (dest_conv)
+    {
+        ENTER_GL();
+
         GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, dest->buffer_object));
         checkGLcall("glBindBufferARB(GL_ARRAY_BUFFER_ARB)");
         GL_EXTCALL(glBufferSubDataARB(GL_ARRAY_BUFFER_ARB, dwDestIndex * get_flexible_vertex_size(DestFVF),
                                       dwCount * get_flexible_vertex_size(DestFVF),
                                       dest_conv_addr));
         checkGLcall("glBufferSubDataARB(GL_ARRAY_BUFFER_ARB)");
+
+        LEAVE_GL();
+
         HeapFree(GetProcessHeap(), 0, dest_conv_addr);
     }
 
-    LEAVE_GL();
-
     return WINED3D_OK;
 }
 #undef copy_and_next
 
+/* Do not call while under the GL lock. */
 static HRESULT WINAPI IWineD3DDeviceImpl_ProcessVertices(IWineD3DDevice *iface, UINT SrcStartIndex, UINT DestIndex,
         UINT VertexCount, IWineD3DBuffer *pDestBuffer, IWineD3DVertexDeclaration *pVertexDecl, DWORD Flags,
         DWORD DestFVF)
@@ -3902,7 +4155,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_ProcessVertices(IWineD3DDevice *iface,
     struct wined3d_stream_info stream_info;
     const struct wined3d_gl_info *gl_info;
     struct wined3d_context *context;
-    BOOL vbo = FALSE, streamWasUP = This->stateBlock->streamIsUP;
+    BOOL vbo = FALSE, streamWasUP = This->stateBlock->state.user_stream;
     HRESULT hr;
 
     TRACE("(%p)->(%d,%d,%d,%p,%p,%d\n", This, SrcStartIndex, DestIndex, VertexCount, pDestBuffer, pVertexDecl, Flags);
@@ -3918,9 +4171,9 @@ static HRESULT WINAPI IWineD3DDeviceImpl_ProcessVertices(IWineD3DDevice *iface,
     /* ProcessVertices reads from vertex buffers, which have to be assigned. DrawPrimitive and DrawPrimitiveUP
      * control the streamIsUP flag, thus restore it afterwards.
      */
-    This->stateBlock->streamIsUP = FALSE;
+    This->stateBlock->state.user_stream = FALSE;
     device_stream_info_from_declaration(This, FALSE, &stream_info, &vbo);
-    This->stateBlock->streamIsUP = streamWasUP;
+    This->stateBlock->state.user_stream = streamWasUP;
 
     if(vbo || SrcStartIndex) {
         unsigned int i;
@@ -3938,7 +4191,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_ProcessVertices(IWineD3DDevice *iface,
             e = &stream_info.elements[i];
             if (e->buffer_object)
             {
-                struct wined3d_buffer *vb = (struct wined3d_buffer *)This->stateBlock->streamSource[e->stream_idx];
+                struct wined3d_buffer *vb = This->stateBlock->state.streams[e->stream_idx].buffer;
                 e->buffer_object = 0;
                 e->data = (BYTE *)((ULONG_PTR)e->data + (ULONG_PTR)buffer_get_sysmem(vb, gl_info));
                 ENTER_GL();
@@ -3962,13 +4215,20 @@ static HRESULT WINAPI IWineD3DDeviceImpl_ProcessVertices(IWineD3DDevice *iface,
  * Get / Set Texture Stage States
  * TODO: Verify against dx9 definitions
  *****/
-static HRESULT WINAPI IWineD3DDeviceImpl_SetTextureStageState(IWineD3DDevice *iface, DWORD Stage, WINED3DTEXTURESTAGESTATETYPE Type, DWORD Value) {
+static HRESULT WINAPI IWineD3DDeviceImpl_SetTextureStageState(IWineD3DDevice *iface, DWORD Stage, WINED3DTEXTURESTAGESTATETYPE Type, DWORD Value)
+{
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    DWORD oldValue = This->updateStateBlock->textureState[Stage][Type];
     const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
+    DWORD oldValue;
 
     TRACE("(%p) : Stage=%d, Type=%s(%d), Value=%d\n", This, Stage, debug_d3dtexturestate(Type), Type, Value);
 
+    if (Type > WINED3D_HIGHEST_TEXTURE_STATE)
+    {
+        WARN("Invalid Type %d passed.\n", Type);
+        return WINED3D_OK;
+    }
+
     if (Stage >= gl_info->limits.texture_stages)
     {
         WARN("Attempting to set stage %u which is higher than the max stage %u, ignoring.\n",
@@ -3976,8 +4236,9 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTextureStageState(IWineD3DDevice *if
         return WINED3D_OK;
     }
 
+    oldValue = This->updateStateBlock->state.texture_states[Stage][Type];
     This->updateStateBlock->changed.textureState[Stage] |= 1 << Type;
-    This->updateStateBlock->textureState[Stage][Type]         = Value;
+    This->updateStateBlock->state.texture_states[Stage][Type] = Value;
 
     if (This->isRecordingState) {
         TRACE("Recording... not performing anything\n");
@@ -3990,8 +4251,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTextureStageState(IWineD3DDevice *if
         return WINED3D_OK;
     }
 
-    if(Stage > This->stateBlock->lowest_disabled_stage &&
-       This->StateTable[STATE_TEXTURESTAGE(0, Type)].representative == STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP)) {
+    if (Stage > This->stateBlock->state.lowest_disabled_stage
+            && This->StateTable[STATE_TEXTURESTAGE(0, Type)].representative
+            == STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP))
+    {
         /* Colorop change above lowest disabled stage? That won't change anything in the gl setup
          * Changes in other states are important on disabled stages too
          */
@@ -4007,11 +4270,12 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTextureStageState(IWineD3DDevice *if
              *
              * The current stage is dirtified below.
              */
-            for(i = Stage + 1; i < This->stateBlock->lowest_disabled_stage; i++) {
+            for (i = Stage + 1; i < This->stateBlock->state.lowest_disabled_stage; ++i)
+            {
                 TRACE("Additionally dirtifying stage %u\n", i);
                 IWineD3DDeviceImpl_MarkStateDirty(This, STATE_TEXTURESTAGE(i, WINED3DTSS_COLOROP));
             }
-            This->stateBlock->lowest_disabled_stage = Stage;
+            This->stateBlock->state.lowest_disabled_stage = Stage;
             TRACE("New lowest disabled: %u\n", Stage);
         } else if(Value != WINED3DTOP_DISABLE && oldValue == WINED3DTOP_DISABLE) {
             /* Previously disabled stage enabled. Stages above it may need enabling
@@ -4023,13 +4287,12 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTextureStageState(IWineD3DDevice *if
 
             for (i = Stage + 1; i < This->adapter->gl_info.limits.texture_stages; ++i)
             {
-                if(This->updateStateBlock->textureState[i][WINED3DTSS_COLOROP] == WINED3DTOP_DISABLE) {
+                if (This->updateStateBlock->state.texture_states[i][WINED3DTSS_COLOROP] == WINED3DTOP_DISABLE)
                     break;
-                }
                 TRACE("Additionally dirtifying stage %u due to enable\n", i);
                 IWineD3DDeviceImpl_MarkStateDirty(This, STATE_TEXTURESTAGE(i, WINED3DTSS_COLOROP));
             }
-            This->stateBlock->lowest_disabled_stage = i;
+            This->stateBlock->state.lowest_disabled_stage = i;
             TRACE("New lowest disabled: %u\n", i);
         }
     }
@@ -4039,10 +4302,22 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTextureStageState(IWineD3DDevice *if
     return WINED3D_OK;
 }
 
-static HRESULT WINAPI IWineD3DDeviceImpl_GetTextureStageState(IWineD3DDevice *iface, DWORD Stage, WINED3DTEXTURESTAGESTATETYPE Type, DWORD* pValue) {
+static HRESULT WINAPI IWineD3DDeviceImpl_GetTextureStageState(IWineD3DDevice *iface, DWORD Stage, WINED3DTEXTURESTAGESTATETYPE Type, DWORD *pValue)
+{
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    TRACE("(%p) : requesting Stage %d, Type %d getting %d\n", This, Stage, Type, This->updateStateBlock->textureState[Stage][Type]);
-    *pValue = This->updateStateBlock->textureState[Stage][Type];
+
+    TRACE("iface %p, stage %u, state %s, value %p.\n",
+            iface, Stage, debug_d3dtexturestate(Type), pValue);
+
+    if (Type > WINED3D_HIGHEST_TEXTURE_STATE)
+    {
+        WARN("Invalid Type %d passed.\n", Type);
+        return WINED3D_OK;
+    }
+
+    *pValue = This->updateStateBlock->state.texture_states[Stage][Type];
+    TRACE("Returning %#x.\n", *pValue);
+
     return WINED3D_OK;
 }
 
@@ -4062,7 +4337,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTexture(IWineD3DDevice *iface,
         stage -= (WINED3DVERTEXTEXTURESAMPLER0 - MAX_FRAGMENT_SAMPLERS);
 
     /* Windows accepts overflowing this array... we do not. */
-    if (stage >= sizeof(This->stateBlock->textures) / sizeof(*This->stateBlock->textures))
+    if (stage >= sizeof(This->stateBlock->state.textures) / sizeof(*This->stateBlock->state.textures))
     {
         WARN("Ignoring invalid stage %u.\n", stage);
         return WINED3D_OK;
@@ -4077,7 +4352,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTexture(IWineD3DDevice *iface,
 
     This->updateStateBlock->changed.textures |= 1 << stage;
 
-    prev = This->updateStateBlock->textures[stage];
+    prev = (IWineD3DBaseTexture *)This->updateStateBlock->state.textures[stage];
     TRACE("Previous texture %p.\n", prev);
 
     if (texture == prev)
@@ -4087,7 +4362,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTexture(IWineD3DDevice *iface,
     }
 
     TRACE("Setting new texture to %p.\n", texture);
-    This->updateStateBlock->textures[stage] = texture;
+    This->updateStateBlock->state.textures[stage] = (IWineD3DBaseTextureImpl *)texture;
 
     if (This->isRecordingState)
     {
@@ -4103,14 +4378,12 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTexture(IWineD3DDevice *iface,
     {
         IWineD3DBaseTextureImpl *t = (IWineD3DBaseTextureImpl *)texture;
         LONG bind_count = InterlockedIncrement(&t->baseTexture.bindCount);
-        UINT dimensions = IWineD3DBaseTexture_GetTextureDimensions(texture);
+        GLenum dimensions = t->baseTexture.target;
 
         IWineD3DBaseTexture_AddRef(texture);
 
-        if (!prev || dimensions != IWineD3DBaseTexture_GetTextureDimensions(prev))
-        {
+        if (!prev || dimensions != ((IWineD3DBaseTextureImpl *)prev)->baseTexture.target)
             IWineD3DDeviceImpl_MarkStateDirty(This, STATE_PIXELSHADER);
-        }
 
         if (!prev && stage < gl_info->limits.texture_stages)
         {
@@ -4146,7 +4419,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetTexture(IWineD3DDevice *iface,
             TRACE("Searching for other stages the texture is bound to.\n");
             for (i = 0; i < MAX_COMBINED_SAMPLERS; ++i)
             {
-                if (This->updateStateBlock->textures[i] == prev)
+                if (This->updateStateBlock->state.textures[i] == t)
                 {
                     TRACE("Texture is also bound to stage %u.\n", i);
                     t->baseTexture.sampler = i;
@@ -4170,12 +4443,13 @@ static HRESULT WINAPI IWineD3DDeviceImpl_GetTexture(IWineD3DDevice *iface, DWORD
         Stage -= (WINED3DVERTEXTEXTURESAMPLER0 - MAX_FRAGMENT_SAMPLERS);
     }
 
-    if (Stage >= sizeof(This->stateBlock->textures)/sizeof(This->stateBlock->textures[0])) {
+    if (Stage >= sizeof(This->stateBlock->state.textures) / sizeof(*This->stateBlock->state.textures))
+    {
         ERR("Current stage overflows textures array (stage %d)\n", Stage);
         return WINED3D_OK; /* Windows accepts overflowing this array ... we do not. */
     }
 
-    *ppTexture=This->stateBlock->textures[Stage];
+    *ppTexture = (IWineD3DBaseTexture *)This->stateBlock->state.textures[Stage];
     if (*ppTexture)
         IWineD3DBaseTexture_AddRef(*ppTexture);
 
@@ -4264,7 +4538,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_BeginStateBlock(IWineD3DDevice *iface)
 
     if (This->isRecordingState) return WINED3DERR_INVALIDCALL;
 
-    hr = IWineD3DDeviceImpl_CreateStateBlock(iface, WINED3DSBT_RECORDED, &stateblock, NULL);
+    hr = IWineD3DDeviceImpl_CreateStateBlock(iface, WINED3DSBT_RECORDED, &stateblock);
     if (FAILED(hr)) return hr;
 
     IWineD3DStateBlock_Release((IWineD3DStateBlock*)This->updateStateBlock);
@@ -4350,7 +4624,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Present(IWineD3DDevice *iface,
     for(i = 0 ; i < swapchains ; i ++) {
 
         IWineD3DDeviceImpl_GetSwapChain(iface, i, &swapChain);
-        TRACE("presentinng chain %d, %p\n", i, swapChain);
+        TRACE("Presenting chain %d, %p.\n", i, swapChain);
         IWineD3DSwapChain_Present(swapChain, pSourceRect, pDestRect, hDestWindowOverride, pDirtyRegion, 0);
         IWineD3DSwapChain_Release(swapChain);
     }
@@ -4358,239 +4632,28 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Present(IWineD3DDevice *iface,
     return WINED3D_OK;
 }
 
-static BOOL is_full_clear(IWineD3DSurfaceImpl *target, const RECT *draw_rect, const RECT *clear_rect)
-{
-    /* partial draw rect */
-    if (draw_rect->left || draw_rect->top
-            || draw_rect->right < target->currentDesc.Width
-            || draw_rect->bottom < target->currentDesc.Height)
-        return FALSE;
-
-    /* partial clear rect */
-    if (clear_rect && (clear_rect->left > 0 || clear_rect->top > 0
-            || clear_rect->right < target->currentDesc.Width
-            || clear_rect->bottom < target->currentDesc.Height))
-        return FALSE;
-
-    return TRUE;
-}
-
-static void prepare_ds_clear(IWineD3DSurfaceImpl *ds, struct wined3d_context *context,
-        DWORD location, const RECT *draw_rect, UINT rect_count, const RECT *clear_rect)
+/* Do not call while under the GL lock. */
+static HRESULT WINAPI IWineD3DDeviceImpl_Clear(IWineD3DDevice *iface, DWORD rect_count,
+        const RECT *rects, DWORD flags, WINED3DCOLOR color, float depth, DWORD stencil)
 {
-    RECT current_rect, r;
-
-    if (ds->Flags & location)
-        SetRect(&current_rect, 0, 0,
-                ds->ds_current_size.cx,
-                ds->ds_current_size.cy);
-    else
-        SetRectEmpty(&current_rect);
-
-    IntersectRect(&r, draw_rect, &current_rect);
-    if (EqualRect(&r, draw_rect))
-    {
-        /* current_rect âŠ‡ draw_rect, modify only. */
-        surface_modify_ds_location(ds, location, ds->ds_current_size.cx, ds->ds_current_size.cy);
-        return;
-    }
-
-    if (EqualRect(&r, &current_rect))
-    {
-        /* draw_rect âŠ‡ current_rect, test if we're doing a full clear. */
-
-        if (!clear_rect)
-        {
-            /* Full clear, modify only. */
-            surface_modify_ds_location(ds, location, draw_rect->right, draw_rect->bottom);
-            return;
-        }
-
-        IntersectRect(&r, draw_rect, clear_rect);
-        if (EqualRect(&r, draw_rect))
-        {
-            /* clear_rect âŠ‡ draw_rect, modify only. */
-            surface_modify_ds_location(ds, location, draw_rect->right, draw_rect->bottom);
-            return;
-        }
-    }
-
-    /* Full load. */
-    surface_load_ds_location(ds, context, location);
-    surface_modify_ds_location(ds, location, ds->ds_current_size.cx, ds->ds_current_size.cy);
-}
-
-/* Not called from the VTable (internal subroutine) */
-HRESULT IWineD3DDeviceImpl_ClearSurface(IWineD3DDeviceImpl *This, IWineD3DSurfaceImpl *target, DWORD Count,
-        const WINED3DRECT *pRects, DWORD Flags, WINED3DCOLOR Color, float Z, DWORD Stencil)
-{
-    const RECT *clear_rect = (Count > 0 && pRects) ? (const RECT *)pRects : NULL;
-    IWineD3DSurfaceImpl *depth_stencil = This->depth_stencil;
-    GLbitfield     glMask = 0;
-    unsigned int   i;
-    UINT drawable_width, drawable_height;
-    struct wined3d_context *context;
+    const WINED3DCOLORVALUE c = {D3DCOLOR_R(color), D3DCOLOR_G(color), D3DCOLOR_B(color), D3DCOLOR_A(color)};
+    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)iface;
     RECT draw_rect;
 
-    device_get_draw_rect(This, &draw_rect);
-
-    /* When we're clearing parts of the drawable, make sure that the target surface is well up to date in the
-     * drawable. After the clear we'll mark the drawable up to date, so we have to make sure that this is true
-     * for the cleared parts, and the untouched parts.
-     *
-     * If we're clearing the whole target there is no need to copy it into the drawable, it will be overwritten
-     * anyway. If we're not clearing the color buffer we don't have to copy either since we're not going to set
-     * the drawable up to date. We have to check all settings that limit the clear area though. Do not bother
-     * checking all this if the dest surface is in the drawable anyway.
-     */
-    if (Flags & WINED3DCLEAR_TARGET && !(target->Flags & SFLAG_INDRAWABLE))
-    {
-        if (!is_full_clear(target, &draw_rect, clear_rect))
-            IWineD3DSurface_LoadLocation((IWineD3DSurface *)target, SFLAG_INDRAWABLE, NULL);
-    }
-
-    context = context_acquire(This, target);
-    if (!context->valid)
-    {
-        context_release(context);
-        WARN("Invalid context, skipping clear.\n");
-        return WINED3D_OK;
-    }
-
-    context_apply_clear_state(context, This, target, depth_stencil);
+    TRACE("iface %p, rect_count %u, rects %p, flags %#x, color 0x%08x, depth %.8e, stencil %u.\n",
+            iface, rect_count, rects, flags, color, depth, stencil);
 
-    target->get_drawable_size(context, &drawable_width, &drawable_height);
-
-    ENTER_GL();
-
-    /* Only set the values up once, as they are not changing */
-    if (Flags & WINED3DCLEAR_STENCIL)
-    {
-        if (context->gl_info->supported[EXT_STENCIL_TWO_SIDE])
-        {
-            glDisable(GL_STENCIL_TEST_TWO_SIDE_EXT);
-            IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_TWOSIDEDSTENCILMODE));
-        }
-        glStencilMask(~0U);
-        IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_STENCILWRITEMASK));
-        glClearStencil(Stencil);
-        checkGLcall("glClearStencil");
-        glMask = glMask | GL_STENCIL_BUFFER_BIT;
-    }
-
-    if (Flags & WINED3DCLEAR_ZBUFFER)
-    {
-        DWORD location = context->render_offscreen ? SFLAG_DS_OFFSCREEN : SFLAG_DS_ONSCREEN;
-
-        if (location == SFLAG_DS_ONSCREEN && depth_stencil != This->onscreen_depth_stencil)
-            device_switch_onscreen_ds(This, context, depth_stencil);
-        prepare_ds_clear(depth_stencil, context, location, &draw_rect, Count, clear_rect);
-        IWineD3DSurface_ModifyLocation((IWineD3DSurface *)depth_stencil, SFLAG_INDRAWABLE, TRUE);
-
-        glDepthMask(GL_TRUE);
-        IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_ZWRITEENABLE));
-        glClearDepth(Z);
-        checkGLcall("glClearDepth");
-        glMask = glMask | GL_DEPTH_BUFFER_BIT;
-    }
-
-    if (Flags & WINED3DCLEAR_TARGET)
-    {
-        IWineD3DSurface_ModifyLocation((IWineD3DSurface *)target, SFLAG_INDRAWABLE, TRUE);
-
-        glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
-        IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_COLORWRITEENABLE));
-        IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_COLORWRITEENABLE1));
-        IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_COLORWRITEENABLE2));
-        IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_COLORWRITEENABLE3));
-        glClearColor(D3DCOLOR_R(Color), D3DCOLOR_G(Color), D3DCOLOR_B(Color), D3DCOLOR_A(Color));
-        checkGLcall("glClearColor");
-        glMask = glMask | GL_COLOR_BUFFER_BIT;
-    }
-
-    if (!clear_rect)
-    {
-        if (context->render_offscreen)
-        {
-            glScissor(draw_rect.left, draw_rect.top,
-                    draw_rect.right - draw_rect.left, draw_rect.bottom - draw_rect.top);
-        }
-        else
-        {
-            glScissor(draw_rect.left, drawable_height - draw_rect.bottom,
-                        draw_rect.right - draw_rect.left, draw_rect.bottom - draw_rect.top);
-        }
-        checkGLcall("glScissor");
-        glClear(glMask);
-        checkGLcall("glClear");
-    }
-    else
-    {
-        RECT current_rect;
-
-        /* Now process each rect in turn. */
-        for (i = 0; i < Count; ++i)
-        {
-            /* Note gl uses lower left, width/height */
-            IntersectRect(&current_rect, &draw_rect, &clear_rect[i]);
-
-            TRACE("clear_rect[%u] %s, current_rect %s.\n", i,
-                    wine_dbgstr_rect(&clear_rect[i]),
-                    wine_dbgstr_rect(&current_rect));
-
-            /* Tests show that rectangles where x1 > x2 or y1 > y2 are ignored silently.
-             * The rectangle is not cleared, no error is returned, but further rectanlges are
-             * still cleared if they are valid. */
-            if (current_rect.left > current_rect.right || current_rect.top > current_rect.bottom)
-            {
-                TRACE("Rectangle with negative dimensions, ignoring.\n");
-                continue;
-            }
-
-            if (context->render_offscreen)
-            {
-                glScissor(current_rect.left, current_rect.top,
-                        current_rect.right - current_rect.left, current_rect.bottom - current_rect.top);
-            }
-            else
-            {
-                glScissor(current_rect.left, drawable_height - current_rect.bottom,
-                          current_rect.right - current_rect.left, current_rect.bottom - current_rect.top);
-            }
-            checkGLcall("glScissor");
-
-            glClear(glMask);
-            checkGLcall("glClear");
-        }
-    }
-
-    LEAVE_GL();
-
-    if (wined3d_settings.strict_draw_ordering || ((target->Flags & SFLAG_SWAPCHAIN)
-            && ((IWineD3DSwapChainImpl *)target->container)->front_buffer == target))
-        wglFlush(); /* Flush to ensure ordering across contexts. */
-
-    context_release(context);
-
-    return WINED3D_OK;
-}
-
-static HRESULT WINAPI IWineD3DDeviceImpl_Clear(IWineD3DDevice *iface, DWORD Count,
-        const WINED3DRECT *pRects, DWORD Flags, WINED3DCOLOR Color, float Z, DWORD Stencil)
-{
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-
-    TRACE("(%p) Count (%d), pRects (%p), Flags (%x), Color (0x%08x), Z (%f), Stencil (%d)\n", This,
-          Count, pRects, Flags, Color, Z, Stencil);
-
-    if (Flags & (WINED3DCLEAR_ZBUFFER | WINED3DCLEAR_STENCIL) && !This->depth_stencil)
+    if (flags & (WINED3DCLEAR_ZBUFFER | WINED3DCLEAR_STENCIL) && !device->depth_stencil)
     {
         WARN("Clearing depth and/or stencil without a depth stencil buffer attached, returning WINED3DERR_INVALIDCALL\n");
         /* TODO: What about depth stencil buffers without stencil bits? */
         return WINED3DERR_INVALIDCALL;
     }
 
-    return IWineD3DDeviceImpl_ClearSurface(This, This->render_targets[0], Count, pRects, Flags, Color, Z, Stencil);
+    device_get_draw_rect(device, &draw_rect);
+
+    return device_clear_render_targets(device, device->adapter->gl_info.limits.buffers,
+            device->render_targets, rect_count, rects, &draw_rect, flags, &c, depth, stencil);
 }
 
 /*****
@@ -4605,7 +4668,7 @@ static void WINAPI IWineD3DDeviceImpl_SetPrimitiveType(IWineD3DDevice *iface,
     TRACE("iface %p, primitive_type %s\n", iface, debug_d3dprimitivetype(primitive_type));
 
     This->updateStateBlock->changed.primitive_type = TRUE;
-    This->updateStateBlock->gl_primitive_type = gl_primitive_type_from_d3d(primitive_type);
+    This->updateStateBlock->state.gl_primitive_type = gl_primitive_type_from_d3d(primitive_type);
 }
 
 static void WINAPI IWineD3DDeviceImpl_GetPrimitiveType(IWineD3DDevice *iface,
@@ -4615,7 +4678,7 @@ static void WINAPI IWineD3DDeviceImpl_GetPrimitiveType(IWineD3DDevice *iface,
 
     TRACE("iface %p, primitive_type %p\n", iface, primitive_type);
 
-    *primitive_type = d3d_primitive_type_from_gl(This->stateBlock->gl_primitive_type);
+    *primitive_type = d3d_primitive_type_from_gl(This->stateBlock->state.gl_primitive_type);
 
     TRACE("Returning %s\n", debug_d3dprimitivetype(*primitive_type));
 }
@@ -4626,19 +4689,22 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawPrimitive(IWineD3DDevice *iface, UI
 
     TRACE("(%p) : start %u, count %u\n", This, StartVertex, vertex_count);
 
-    if(!This->stateBlock->vertexDecl) {
+    if (!This->stateBlock->state.vertex_declaration)
+    {
         WARN("(%p) : Called without a valid vertex declaration set\n", This);
         return WINED3DERR_INVALIDCALL;
     }
 
     /* The index buffer is not needed here, but restore it, otherwise it is hell to keep track of */
-    if(This->stateBlock->streamIsUP) {
+    if (This->stateBlock->state.user_stream)
+    {
         IWineD3DDeviceImpl_MarkStateDirty(This, STATE_INDEXBUFFER);
-        This->stateBlock->streamIsUP = FALSE;
+        This->stateBlock->state.user_stream = FALSE;
     }
 
-    if(This->stateBlock->loadBaseVertexIndex != 0) {
-        This->stateBlock->loadBaseVertexIndex = 0;
+    if (This->stateBlock->state.load_base_vertex_index)
+    {
+        This->stateBlock->state.load_base_vertex_index = 0;
         IWineD3DDeviceImpl_MarkStateDirty(This, STATE_STREAMSRC);
     }
     /* Account for the loading offset due to index buffers. Instead of reloading all sources correct it with the startvertex parameter */
@@ -4648,13 +4714,14 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawPrimitive(IWineD3DDevice *iface, UI
 
 static HRESULT WINAPI IWineD3DDeviceImpl_DrawIndexedPrimitive(IWineD3DDevice *iface, UINT startIndex, UINT index_count)
 {
-    IWineD3DDeviceImpl  *This = (IWineD3DDeviceImpl *)iface;
+    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    struct wined3d_buffer *index_buffer;
     UINT                 idxStride = 2;
-    IWineD3DBuffer *pIB;
     GLuint vbo;
 
-    pIB = This->stateBlock->pIndexData;
-    if (!pIB) {
+    index_buffer = This->stateBlock->state.index_buffer;
+    if (!index_buffer)
+    {
         /* D3D9 returns D3DERR_INVALIDCALL when DrawIndexedPrimitive is called
          * without an index buffer set. (The first time at least...)
          * D3D8 simply dies, but I doubt it can do much harm to return
@@ -4663,32 +4730,34 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawIndexedPrimitive(IWineD3DDevice *if
         return WINED3DERR_INVALIDCALL;
     }
 
-    if(!This->stateBlock->vertexDecl) {
+    if (!This->stateBlock->state.vertex_declaration)
+    {
         WARN("(%p) : Called without a valid vertex declaration set\n", This);
         return WINED3DERR_INVALIDCALL;
     }
 
-    if(This->stateBlock->streamIsUP) {
+    if (This->stateBlock->state.user_stream)
+    {
         IWineD3DDeviceImpl_MarkStateDirty(This, STATE_INDEXBUFFER);
-        This->stateBlock->streamIsUP = FALSE;
+        This->stateBlock->state.user_stream = FALSE;
     }
-    vbo = ((struct wined3d_buffer *) pIB)->buffer_object;
+    vbo = index_buffer->buffer_object;
 
     TRACE("(%p) : startIndex %u, index count %u.\n", This, startIndex, index_count);
 
-    if (This->stateBlock->IndexFmt == WINED3DFMT_R16_UINT) {
+    if (This->stateBlock->state.index_format == WINED3DFMT_R16_UINT)
         idxStride = 2;
-    } else {
+    else
         idxStride = 4;
-    }
 
-    if(This->stateBlock->loadBaseVertexIndex != This->stateBlock->baseVertexIndex) {
-        This->stateBlock->loadBaseVertexIndex = This->stateBlock->baseVertexIndex;
+    if (This->stateBlock->state.load_base_vertex_index != This->stateBlock->state.base_vertex_index)
+    {
+        This->stateBlock->state.load_base_vertex_index = This->stateBlock->state.base_vertex_index;
         IWineD3DDeviceImpl_MarkStateDirty(This, STATE_STREAMSRC);
     }
 
     drawPrimitive(iface, index_count, startIndex, idxStride,
-            vbo ? NULL : ((struct wined3d_buffer *)pIB)->resource.allocatedMemory);
+            vbo ? NULL : index_buffer->resource.allocatedMemory);
 
     return WINED3D_OK;
 }
@@ -4697,24 +4766,27 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawPrimitiveUP(IWineD3DDevice *iface,
         const void *pVertexStreamZeroData, UINT VertexStreamZeroStride)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    struct wined3d_stream_state *stream;
     IWineD3DBuffer *vb;
 
     TRACE("(%p) : vertex count %u, pVtxData %p, stride %u\n",
             This, vertex_count, pVertexStreamZeroData, VertexStreamZeroStride);
 
-    if(!This->stateBlock->vertexDecl) {
+    if (!This->stateBlock->state.vertex_declaration)
+    {
         WARN("(%p) : Called without a valid vertex declaration set\n", This);
         return WINED3DERR_INVALIDCALL;
     }
 
     /* Note in the following, it's not this type, but that's the purpose of streamIsUP */
-    vb = This->stateBlock->streamSource[0];
-    This->stateBlock->streamSource[0] = (IWineD3DBuffer *)pVertexStreamZeroData;
+    stream = &This->stateBlock->state.streams[0];
+    vb = (IWineD3DBuffer *)stream->buffer;
+    stream->buffer = (struct wined3d_buffer *)pVertexStreamZeroData;
     if (vb) IWineD3DBuffer_Release(vb);
-    This->stateBlock->streamOffset[0] = 0;
-    This->stateBlock->streamStride[0] = VertexStreamZeroStride;
-    This->stateBlock->streamIsUP = TRUE;
-    This->stateBlock->loadBaseVertexIndex = 0;
+    stream->offset = 0;
+    stream->stride = VertexStreamZeroStride;
+    This->stateBlock->state.user_stream = TRUE;
+    This->stateBlock->state.load_base_vertex_index = 0;
 
     /* TODO: Only mark dirty if drawing from a different UP address */
     IWineD3DDeviceImpl_MarkStateDirty(This, STATE_STREAMSRC);
@@ -4722,8 +4794,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawPrimitiveUP(IWineD3DDevice *iface,
     drawPrimitive(iface, vertex_count, 0 /* start_idx */, 0 /* indxSize*/, NULL /* indxData */);
 
     /* MSDN specifies stream zero settings must be set to NULL */
-    This->stateBlock->streamStride[0] = 0;
-    This->stateBlock->streamSource[0] = NULL;
+    stream->buffer = NULL;
+    stream->stride = 0;
 
     /* stream zero settings set to null at end, as per the msdn. No need to mark dirty here, the app has to set
      * the new stream sources or use UP drawing again
@@ -4732,18 +4804,20 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawPrimitiveUP(IWineD3DDevice *iface,
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_DrawIndexedPrimitiveUP(IWineD3DDevice *iface,
-        UINT index_count, const void *pIndexData, WINED3DFORMAT IndexDataFormat,
+        UINT index_count, const void *pIndexData, enum wined3d_format_id IndexDataFormat,
         const void *pVertexStreamZeroData, UINT VertexStreamZeroStride)
 {
     int                 idxStride;
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    struct wined3d_stream_state *stream;
     IWineD3DBuffer *vb;
     IWineD3DBuffer *ib;
 
     TRACE("(%p) : index count %u, pidxdata %p, IdxFmt %u, pVtxdata %p, stride=%u.\n",
             This, index_count, pIndexData, IndexDataFormat, pVertexStreamZeroData, VertexStreamZeroStride);
 
-    if(!This->stateBlock->vertexDecl) {
+    if (!This->stateBlock->state.vertex_declaration)
+    {
         WARN("(%p) : Called without a valid vertex declaration set\n", This);
         return WINED3DERR_INVALIDCALL;
     }
@@ -4754,17 +4828,17 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawIndexedPrimitiveUP(IWineD3DDevice *
         idxStride = 4;
     }
 
-    /* Note in the following, it's not this type, but that's the purpose of streamIsUP */
-    vb = This->stateBlock->streamSource[0];
-    This->stateBlock->streamSource[0] = (IWineD3DBuffer *)pVertexStreamZeroData;
+    stream = &This->stateBlock->state.streams[0];
+    vb = (IWineD3DBuffer *)stream->buffer;
+    stream->buffer = (struct wined3d_buffer *)pVertexStreamZeroData;
     if (vb) IWineD3DBuffer_Release(vb);
-    This->stateBlock->streamIsUP = TRUE;
-    This->stateBlock->streamOffset[0] = 0;
-    This->stateBlock->streamStride[0] = VertexStreamZeroStride;
+    stream->offset = 0;
+    stream->stride = VertexStreamZeroStride;
+    This->stateBlock->state.user_stream = TRUE;
 
     /* Set to 0 as per msdn. Do it now due to the stream source loading during drawPrimitive */
-    This->stateBlock->baseVertexIndex = 0;
-    This->stateBlock->loadBaseVertexIndex = 0;
+    This->stateBlock->state.base_vertex_index = 0;
+    This->stateBlock->state.load_base_vertex_index = 0;
     /* Mark the state dirty until we have nicer tracking of the stream source pointers */
     IWineD3DDeviceImpl_MarkStateDirty(This, STATE_VDECL);
     IWineD3DDeviceImpl_MarkStateDirty(This, STATE_INDEXBUFFER);
@@ -4772,12 +4846,13 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawIndexedPrimitiveUP(IWineD3DDevice *
     drawPrimitive(iface, index_count, 0 /* start_idx */, idxStride, pIndexData);
 
     /* MSDN specifies stream zero settings and index buffer must be set to NULL */
-    This->stateBlock->streamSource[0] = NULL;
-    This->stateBlock->streamStride[0] = 0;
-    ib = This->stateBlock->pIndexData;
-    if(ib) {
+    stream->buffer = NULL;
+    stream->stride = 0;
+    ib = (IWineD3DBuffer *)This->stateBlock->state.index_buffer;
+    if (ib)
+    {
         IWineD3DBuffer_Release(ib);
-        This->stateBlock->pIndexData = NULL;
+        This->stateBlock->state.index_buffer = NULL;
     }
     /* No need to mark the stream source state dirty here. Either the app calls UP drawing again, or it has to call
      * SetStreamSource to specify a vertex buffer
@@ -4797,7 +4872,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawPrimitiveStrided(IWineD3DDevice *if
      */
     IWineD3DDeviceImpl_MarkStateDirty(This, STATE_VDECL);
     IWineD3DDeviceImpl_MarkStateDirty(This, STATE_INDEXBUFFER);
-    This->stateBlock->baseVertexIndex = 0;
+    This->stateBlock->state.base_vertex_index = 0;
     This->up_strided = DrawPrimStrideData;
     drawPrimitive(iface, vertex_count, 0, 0, NULL);
     This->up_strided = NULL;
@@ -4806,7 +4881,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawPrimitiveStrided(IWineD3DDevice *if
 
 static HRESULT WINAPI IWineD3DDeviceImpl_DrawIndexedPrimitiveStrided(IWineD3DDevice *iface,
         UINT vertex_count, const WineDirect3DVertexStridedData *DrawPrimStrideData,
-        UINT NumVertices, const void *pIndexData, WINED3DFORMAT IndexDataFormat)
+        UINT NumVertices, const void *pIndexData, enum wined3d_format_id IndexDataFormat)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
     DWORD idxSize = (IndexDataFormat == WINED3DFMT_R32_UINT ? 4 : 2);
@@ -4817,8 +4892,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawIndexedPrimitiveStrided(IWineD3DDev
      */
     IWineD3DDeviceImpl_MarkStateDirty(This, STATE_VDECL);
     IWineD3DDeviceImpl_MarkStateDirty(This, STATE_INDEXBUFFER);
-    This->stateBlock->streamIsUP = TRUE;
-    This->stateBlock->baseVertexIndex = 0;
+    This->stateBlock->state.user_stream = TRUE;
+    This->stateBlock->state.base_vertex_index = 0;
     This->up_strided = DrawPrimStrideData;
     drawPrimitive(iface, vertex_count, 0 /* start_idx */, idxSize, pIndexData);
     This->up_strided = NULL;
@@ -4982,14 +5057,20 @@ static HRESULT WINAPI IWineD3DDeviceImpl_UpdateTexture(IWineD3DDevice *iface,
     return WINED3D_OK;
 }
 
-static HRESULT  WINAPI  IWineD3DDeviceImpl_GetFrontBufferData(IWineD3DDevice *iface,UINT iSwapChain, IWineD3DSurface *pDestSurface) {
-    IWineD3DSwapChain *swapChain;
+static HRESULT WINAPI IWineD3DDeviceImpl_GetFrontBufferData(IWineD3DDevice *iface,
+        UINT swapchain_idx, IWineD3DSurface *dst_surface)
+{
+    IWineD3DSwapChain *swapchain;
     HRESULT hr;
-    hr = IWineD3DDeviceImpl_GetSwapChain(iface, iSwapChain, &swapChain);
-    if(hr == WINED3D_OK) {
-        hr = IWineD3DSwapChain_GetFrontBufferData(swapChain, pDestSurface);
-                IWineD3DSwapChain_Release(swapChain);
-    }
+
+    TRACE("iface %p, swapchain_idx %u, dst_surface %p.\n", iface, swapchain_idx, dst_surface);
+
+    hr = IWineD3DDeviceImpl_GetSwapChain(iface, swapchain_idx, &swapchain);
+    if (FAILED(hr)) return hr;
+
+    hr = IWineD3DSwapChain_GetFrontBufferData(swapchain, dst_surface);
+    IWineD3DSwapChain_Release(swapchain);
+
     return hr;
 }
 
@@ -5000,29 +5081,35 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_ValidateDevice(IWineD3DDevice *iface,
 
     TRACE("(%p) : %p\n", This, pNumPasses);
 
-    for(i = 0; i < MAX_COMBINED_SAMPLERS; i++) {
-        if(This->stateBlock->samplerState[i][WINED3DSAMP_MINFILTER] == WINED3DTEXF_NONE) {
+    for (i = 0; i < MAX_COMBINED_SAMPLERS; ++i)
+    {
+        if (This->stateBlock->state.sampler_states[i][WINED3DSAMP_MINFILTER] == WINED3DTEXF_NONE)
+        {
             WARN("Sampler state %u has minfilter D3DTEXF_NONE, returning D3DERR_UNSUPPORTEDTEXTUREFILTER\n", i);
             return WINED3DERR_UNSUPPORTEDTEXTUREFILTER;
         }
-        if(This->stateBlock->samplerState[i][WINED3DSAMP_MAGFILTER] == WINED3DTEXF_NONE) {
+        if (This->stateBlock->state.sampler_states[i][WINED3DSAMP_MAGFILTER] == WINED3DTEXF_NONE)
+        {
             WARN("Sampler state %u has magfilter D3DTEXF_NONE, returning D3DERR_UNSUPPORTEDTEXTUREFILTER\n", i);
             return WINED3DERR_UNSUPPORTEDTEXTUREFILTER;
         }
 
-        texture = (IWineD3DBaseTextureImpl *) This->stateBlock->textures[i];
-        if (!texture || texture->resource.format_desc->Flags & WINED3DFMT_FLAG_FILTERING) continue;
+        texture = This->stateBlock->state.textures[i];
+        if (!texture || texture->resource.format->Flags & WINED3DFMT_FLAG_FILTERING) continue;
 
-        if(This->stateBlock->samplerState[i][WINED3DSAMP_MAGFILTER] != WINED3DTEXF_POINT) {
+        if (This->stateBlock->state.sampler_states[i][WINED3DSAMP_MAGFILTER] != WINED3DTEXF_POINT)
+        {
             WARN("Non-filterable texture and mag filter enabled on samper %u, returning E_FAIL\n", i);
             return E_FAIL;
         }
-        if(This->stateBlock->samplerState[i][WINED3DSAMP_MINFILTER] != WINED3DTEXF_POINT) {
+        if (This->stateBlock->state.sampler_states[i][WINED3DSAMP_MINFILTER] != WINED3DTEXF_POINT)
+        {
             WARN("Non-filterable texture and min filter enabled on samper %u, returning E_FAIL\n", i);
             return E_FAIL;
         }
-        if(This->stateBlock->samplerState[i][WINED3DSAMP_MIPFILTER] != WINED3DTEXF_NONE &&
-           This->stateBlock->samplerState[i][WINED3DSAMP_MIPFILTER] != WINED3DTEXF_POINT /* sic! */) {
+        if (This->stateBlock->state.sampler_states[i][WINED3DSAMP_MIPFILTER] != WINED3DTEXF_NONE
+                && This->stateBlock->state.sampler_states[i][WINED3DSAMP_MIPFILTER] != WINED3DTEXF_POINT)
+        {
             WARN("Non-filterable texture and mip filter enabled on samper %u, returning E_FAIL\n", i);
             return E_FAIL;
         }
@@ -5041,9 +5128,9 @@ static void dirtify_p8_texture_samplers(IWineD3DDeviceImpl *device)
 
     for (i = 0; i < MAX_COMBINED_SAMPLERS; ++i)
     {
-        IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl*)device->stateBlock->textures[i];
-        if (texture && (texture->resource.format_desc->format == WINED3DFMT_P8_UINT
-                || texture->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM))
+        IWineD3DBaseTextureImpl *texture = device->stateBlock->state.textures[i];
+        if (texture && (texture->resource.format->id == WINED3DFMT_P8_UINT
+                || texture->resource.format->id == WINED3DFMT_P8_UINT_A8_UNORM))
         {
             IWineD3DDeviceImpl_MarkStateDirty(device, STATE_SAMPLER(i));
         }
@@ -5136,7 +5223,9 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_SetCurrentTexturePalette(IWineD3DDevi
 
 static HRESULT  WINAPI  IWineD3DDeviceImpl_GetCurrentTexturePalette(IWineD3DDevice *iface, UINT* PaletteNumber) {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    if (PaletteNumber == NULL) {
+
+    if (!PaletteNumber)
+    {
         WARN("(%p) : returning Invalid Call\n", This);
         return WINED3DERR_INVALIDCALL;
     }
@@ -5229,8 +5318,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_UpdateSurface(IWineD3DDevice *iface,
     IWineD3DSurfaceImpl *src_impl = (IWineD3DSurfaceImpl *)src_surface;
     IWineD3DSurfaceImpl *dst_impl = (IWineD3DSurfaceImpl *)dst_surface;
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    const struct wined3d_format_desc *src_format;
-    const struct wined3d_format_desc *dst_format;
+    const struct wined3d_format *src_format;
+    const struct wined3d_format *dst_format;
     const struct wined3d_gl_info *gl_info;
     struct wined3d_context *context;
     const unsigned char *data;
@@ -5239,7 +5328,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_UpdateSurface(IWineD3DDevice *iface,
     UINT src_w, src_h;
     UINT dst_x, dst_y;
     DWORD sampler;
-    struct wined3d_format_desc desc;
+    struct wined3d_format format;
 
     TRACE("iface %p, src_surface %p, src_rect %s, dst_surface %p, dst_point %s.\n",
             iface, src_surface, wine_dbgstr_rect(src_rect),
@@ -5252,10 +5341,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_UpdateSurface(IWineD3DDevice *iface,
         return WINED3DERR_INVALIDCALL;
     }
 
-    src_format = src_impl->resource.format_desc;
-    dst_format = dst_impl->resource.format_desc;
+    src_format = src_impl->resource.format;
+    dst_format = dst_impl->resource.format;
 
-    if (src_format->format != dst_format->format)
+    if (src_format->id != dst_format->id)
     {
         WARN("Source and destination surfaces should have the same format.\n");
         return WINED3DERR_INVALIDCALL;
@@ -5268,8 +5357,8 @@ static HRESULT WINAPI IWineD3DDeviceImpl_UpdateSurface(IWineD3DDevice *iface,
      * surface to the destination's sysmem copy. If surface conversion is
      * needed, use BltFast instead to copy in sysmem and use regular surface
      * loading. */
-    d3dfmt_get_conv(dst_impl, FALSE, TRUE, &desc, &convert);
-    if (convert != NO_CONVERSION || desc.convert)
+    d3dfmt_get_conv(dst_impl, FALSE, TRUE, &format, &convert);
+    if (convert != NO_CONVERSION || format.convert)
         return IWineD3DSurface_BltFast(dst_surface, dst_x, dst_y, src_surface, src_rect, 0);
 
     context = context_acquire(This, NULL);
@@ -5296,9 +5385,9 @@ static HRESULT WINAPI IWineD3DDeviceImpl_UpdateSurface(IWineD3DDevice *iface,
 
     if (dst_format->Flags & WINED3DFMT_FLAG_COMPRESSED)
     {
-        UINT row_length = (update_w / src_format->block_width) * src_format->block_byte_count;
-        UINT row_count = update_h / src_format->block_height;
-        UINT src_pitch = IWineD3DSurface_GetPitch(src_surface);
+        UINT row_length = wined3d_format_calculate_size(src_format, 1, update_w, 1);
+        UINT row_count = (update_h + src_format->block_height - 1) / src_format->block_height;
+        UINT src_pitch = wined3d_format_calculate_size(src_format, 1, src_w, 1);
 
         if (src_rect)
         {
@@ -5353,7 +5442,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_UpdateSurface(IWineD3DDevice *iface,
     LEAVE_GL();
     context_release(context);
 
-    IWineD3DSurface_ModifyLocation(dst_surface, SFLAG_INTEXTURE, TRUE);
+    surface_modify_location(dst_impl, SFLAG_INTEXTURE, TRUE);
     sampler = This->rev_tex_unit_map[0];
     if (sampler != WINED3D_UNMAPPED_STAGE)
     {
@@ -5409,9 +5498,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawRectPatch(IWineD3DDevice *iface, UI
         patch = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*patch));
     }
 
-    if(pNumSegs[0] != patch->numSegs[0] || pNumSegs[1] != patch->numSegs[1] ||
-       pNumSegs[2] != patch->numSegs[2] || pNumSegs[3] != patch->numSegs[3] ||
-       (pRectPatchInfo && memcmp(pRectPatchInfo, &patch->RectPatchInfo, sizeof(*pRectPatchInfo)) != 0) ) {
+    if (pNumSegs[0] != patch->numSegs[0] || pNumSegs[1] != patch->numSegs[1]
+            || pNumSegs[2] != patch->numSegs[2] || pNumSegs[3] != patch->numSegs[3]
+            || (pRectPatchInfo && memcmp(pRectPatchInfo, &patch->RectPatchInfo, sizeof(*pRectPatchInfo))))
+    {
         HRESULT hr;
         TRACE("Tesselation density or patch info changed, retesselating\n");
 
@@ -5436,10 +5526,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DrawRectPatch(IWineD3DDevice *iface, UI
     }
 
     This->currentPatch = patch;
-    old_primitive_type = This->stateBlock->gl_primitive_type;
-    This->stateBlock->gl_primitive_type = GL_TRIANGLES;
+    old_primitive_type = This->stateBlock->state.gl_primitive_type;
+    This->stateBlock->state.gl_primitive_type = GL_TRIANGLES;
     IWineD3DDevice_DrawPrimitiveStrided(iface, patch->numSegs[0] * patch->numSegs[1] * 2 * 3, &patch->strided);
-    This->stateBlock->gl_primitive_type = old_primitive_type;
+    This->stateBlock->state.gl_primitive_type = old_primitive_type;
     This->currentPatch = NULL;
 
     /* Destroy uncached patches */
@@ -5483,83 +5573,30 @@ static HRESULT WINAPI IWineD3DDeviceImpl_DeletePatch(IWineD3DDevice *iface, UINT
     return WINED3DERR_INVALIDCALL;
 }
 
-static void color_fill_fbo(IWineD3DDevice *iface, IWineD3DSurfaceImpl *surface,
-        const WINED3DRECT *rect, const float color[4])
-{
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
-    struct wined3d_context *context;
-
-    if (rect) IWineD3DSurface_LoadLocation((IWineD3DSurface *)surface, SFLAG_INDRAWABLE, NULL);
-    IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INDRAWABLE, TRUE);
-
-    context = context_acquire(This, surface);
-    context_apply_clear_state(context, This, surface, NULL);
-
-    ENTER_GL();
-
-    if (rect)
-    {
-        if (surface_is_offscreen(surface))
-            glScissor(rect->x1, rect->y1, rect->x2 - rect->x1, rect->y2 - rect->y1);
-        else
-            glScissor(rect->x1, surface->currentDesc.Height - rect->y2,
-                    rect->x2 - rect->x1, rect->y2 - rect->y1);
-        checkGLcall("glScissor");
-    }
-    else
-    {
-        glDisable(GL_SCISSOR_TEST);
-    }
-
-    glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
-    IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_COLORWRITEENABLE));
-    IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_COLORWRITEENABLE1));
-    IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_COLORWRITEENABLE2));
-    IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_COLORWRITEENABLE3));
-
-    glClearColor(color[0], color[1], color[2], color[3]);
-    glClear(GL_COLOR_BUFFER_BIT);
-    checkGLcall("glClear");
-
-    LEAVE_GL();
-
-    if (wined3d_settings.strict_draw_ordering) wglFlush(); /* Flush to ensure ordering across contexts. */
-
-    context_release(context);
-}
-
+/* Do not call while under the GL lock. */
 static HRESULT WINAPI IWineD3DDeviceImpl_ColorFill(IWineD3DDevice *iface,
-        IWineD3DSurface *pSurface, const WINED3DRECT *pRect, WINED3DCOLOR color)
+        IWineD3DSurface *surface, const RECT *rect, const WINED3DCOLORVALUE *color)
 {
-    IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *) pSurface;
-    WINEDDBLTFX BltFx;
+    IWineD3DSurfaceImpl *s = (IWineD3DSurfaceImpl *)surface;
 
-    TRACE("iface %p, surface %p, rect %p, color 0x%08x.\n", iface, pSurface, pRect, color);
+    TRACE("iface %p, surface %p, rect %s, color {%.8e, %.8e, %.8e, %.8e}.\n",
+            iface, surface, wine_dbgstr_rect(rect),
+            color->r, color->g, color->b, color->a);
 
-    if (surface->resource.pool != WINED3DPOOL_DEFAULT && surface->resource.pool != WINED3DPOOL_SYSTEMMEM) {
+    if (s->resource.pool != WINED3DPOOL_DEFAULT && s->resource.pool != WINED3DPOOL_SYSTEMMEM)
+    {
         FIXME("call to colorfill with non WINED3DPOOL_DEFAULT or WINED3DPOOL_SYSTEMMEM surface\n");
         return WINED3DERR_INVALIDCALL;
     }
 
-    if (wined3d_settings.offscreen_rendering_mode == ORM_FBO) {
-        const float c[4] = {D3DCOLOR_R(color), D3DCOLOR_G(color), D3DCOLOR_B(color), D3DCOLOR_A(color)};
-        color_fill_fbo(iface, surface, pRect, c);
-        return WINED3D_OK;
-    } else {
-        /* Just forward this to the DirectDraw blitting engine */
-        memset(&BltFx, 0, sizeof(BltFx));
-        BltFx.dwSize = sizeof(BltFx);
-        BltFx.u5.dwFillColor = color_convert_argb_to_fmt(color, surface->resource.format_desc->format);
-        return IWineD3DSurface_Blt(pSurface, (const RECT *)pRect, NULL, NULL,
-                WINEDDBLT_COLORFILL, &BltFx, WINED3DTEXF_POINT);
-    }
+    return surface_color_fill(s, rect, color);
 }
 
+/* Do not call while under the GL lock. */
 static void WINAPI IWineD3DDeviceImpl_ClearRendertargetView(IWineD3DDevice *iface,
-        IWineD3DRendertargetView *rendertarget_view, const float color[4])
+        IWineD3DRendertargetView *rendertarget_view, const WINED3DCOLORVALUE *color)
 {
     IWineD3DResource *resource;
-    IWineD3DSurfaceImpl *surface;
     HRESULT hr;
 
     hr = IWineD3DRendertargetView_GetResource(rendertarget_view, &resource);
@@ -5576,349 +5613,122 @@ static void WINAPI IWineD3DDeviceImpl_ClearRendertargetView(IWineD3DDevice *ifac
         return;
     }
 
-    surface = (IWineD3DSurfaceImpl *)resource;
-
-    if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
-    {
-        color_fill_fbo(iface, surface, NULL, color);
-    }
-    else
-    {
-        WINEDDBLTFX BltFx;
-        WINED3DCOLOR c;
-
-        WARN("Converting to WINED3DCOLOR, this might give incorrect results\n");
-
-        c = ((DWORD)(color[2] * 255.0f));
-        c |= ((DWORD)(color[1] * 255.0f)) << 8;
-        c |= ((DWORD)(color[0] * 255.0f)) << 16;
-        c |= ((DWORD)(color[3] * 255.0f)) << 24;
-
-        /* Just forward this to the DirectDraw blitting engine */
-        memset(&BltFx, 0, sizeof(BltFx));
-        BltFx.dwSize = sizeof(BltFx);
-        BltFx.u5.dwFillColor = color_convert_argb_to_fmt(c, surface->resource.format_desc->format);
-        hr = IWineD3DSurface_Blt((IWineD3DSurface *)surface, NULL, NULL, NULL,
-                WINEDDBLT_COLORFILL, &BltFx, WINED3DTEXF_POINT);
-        if (FAILED(hr))
-        {
-            ERR("Blt failed, hr %#x\n", hr);
-        }
-    }
+    hr = surface_color_fill((IWineD3DSurfaceImpl *)resource, NULL, color);
+    if (FAILED(hr)) ERR("Color fill failed, hr %#x.\n", hr);
 
     IWineD3DResource_Release(resource);
 }
 
 /* rendertarget and depth stencil functions */
-static HRESULT  WINAPI  IWineD3DDeviceImpl_GetRenderTarget(IWineD3DDevice* iface,DWORD RenderTargetIndex, IWineD3DSurface **ppRenderTarget) {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-
-    if (RenderTargetIndex >= This->adapter->gl_info.limits.buffers)
-    {
-        ERR("(%p) : Only %d render targets are supported.\n",
-                This, This->adapter->gl_info.limits.buffers);
-        return WINED3DERR_INVALIDCALL;
-    }
-
-    *ppRenderTarget = (IWineD3DSurface *)This->render_targets[RenderTargetIndex];
-    TRACE("(%p) : RenderTarget %d Index returning %p\n", This, RenderTargetIndex, *ppRenderTarget);
-    /* Note inc ref on returned surface */
-    if(*ppRenderTarget != NULL)
-        IWineD3DSurface_AddRef(*ppRenderTarget);
-    return WINED3D_OK;
-}
-
-static HRESULT WINAPI IWineD3DDeviceImpl_SetFrontBackBuffers(IWineD3DDevice *iface,
-        IWineD3DSurface *front, IWineD3DSurface *back)
+static HRESULT WINAPI IWineD3DDeviceImpl_GetRenderTarget(IWineD3DDevice *iface,
+        DWORD render_target_idx, IWineD3DSurface **render_target)
 {
-    IWineD3DSurfaceImpl *front_impl = (IWineD3DSurfaceImpl *)front;
-    IWineD3DSurfaceImpl *back_impl = (IWineD3DSurfaceImpl *)back;
-    IWineD3DSwapChainImpl *swapchain;
-    HRESULT hr;
-
-    TRACE("iface %p, front %p, back %p.\n", iface, front, back);
+    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)iface;
 
-    if (FAILED(hr = IWineD3DDevice_GetSwapChain(iface, 0, (IWineD3DSwapChain **)&swapchain)))
-    {
-        ERR("Failed to get the swapchain, hr %#x.\n", hr);
-        return hr;
-    }
+    TRACE("iface %p, render_target_idx %u, render_target %p.\n",
+            iface, render_target_idx, render_target);
 
-    if (front_impl && !(front_impl->resource.usage & WINED3DUSAGE_RENDERTARGET))
+    if (render_target_idx >= device->adapter->gl_info.limits.buffers)
     {
-        ERR("Trying to set a front buffer which doesn't have WINED3DUSAGE_RENDERTARGET usage.\n");
-        IWineD3DSwapChain_Release((IWineD3DSwapChain *)swapchain);
+        WARN("Only %u render targets are supported.\n", device->adapter->gl_info.limits.buffers);
         return WINED3DERR_INVALIDCALL;
     }
 
-    if (back_impl)
-    {
-        if (!(back_impl->resource.usage & WINED3DUSAGE_RENDERTARGET))
-        {
-            ERR("Trying to set a back buffer which doesn't have WINED3DUSAGE_RENDERTARGET usage.\n");
-            IWineD3DSwapChain_Release((IWineD3DSwapChain *)swapchain);
-            return WINED3DERR_INVALIDCALL;
-        }
+    *render_target = (IWineD3DSurface *)device->render_targets[render_target_idx];
+    if (*render_target) IWineD3DSurface_AddRef(*render_target);
 
-        if (!swapchain->back_buffers)
-        {
-            swapchain->back_buffers = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*swapchain->back_buffers));
-            if (!swapchain->back_buffers)
-            {
-                ERR("Failed to allocate back buffer array memory.\n");
-                IWineD3DSwapChain_Release((IWineD3DSwapChain *)swapchain);
-                return E_OUTOFMEMORY;
-            }
-        }
-    }
+    TRACE("Returning render target %p.\n", *render_target);
 
-    if (swapchain->front_buffer != front_impl)
-    {
-        TRACE("Changing the front buffer from %p to %p.\n", swapchain->front_buffer, front_impl);
-
-        if (swapchain->front_buffer)
-        {
-            IWineD3DSurface_SetContainer((IWineD3DSurface *)swapchain->front_buffer, NULL);
-            swapchain->front_buffer->Flags &= ~SFLAG_SWAPCHAIN;
-        }
-        swapchain->front_buffer = front_impl;
-
-        if (front)
-        {
-            IWineD3DSurface_SetContainer(front, (IWineD3DBase *)swapchain);
-            front_impl->Flags |= SFLAG_SWAPCHAIN;
-        }
-    }
-
-    if (swapchain->back_buffers[0] != back_impl)
-    {
-        TRACE("Changing the back buffer from %p to %p.\n", swapchain->back_buffers[0], back_impl);
-
-        if (swapchain->back_buffers[0])
-        {
-            IWineD3DSurface_SetContainer((IWineD3DSurface *)swapchain->back_buffers[0], NULL);
-            swapchain->back_buffers[0]->Flags &= ~SFLAG_SWAPCHAIN;
-        }
-        swapchain->back_buffers[0] = back_impl;
-
-        if (back)
-        {
-            swapchain->presentParms.BackBufferWidth = back_impl->currentDesc.Width;
-            swapchain->presentParms.BackBufferHeight = back_impl->currentDesc.Height;
-            swapchain->presentParms.BackBufferFormat = back_impl->resource.format_desc->format;
-            swapchain->presentParms.BackBufferCount = 1;
-
-            IWineD3DSurface_SetContainer(back, (IWineD3DBase *)swapchain);
-            back_impl->Flags |= SFLAG_SWAPCHAIN;
-        }
-        else
-        {
-            swapchain->presentParms.BackBufferCount = 0;
-            HeapFree(GetProcessHeap(), 0, swapchain->back_buffers);
-            swapchain->back_buffers = NULL;
-        }
-    }
-
-    IWineD3DSwapChain_Release((IWineD3DSwapChain *)swapchain);
     return WINED3D_OK;
 }
 
-static HRESULT  WINAPI  IWineD3DDeviceImpl_GetDepthStencilSurface(IWineD3DDevice* iface, IWineD3DSurface **ppZStencilSurface) {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    *ppZStencilSurface = (IWineD3DSurface *)This->depth_stencil;
-    TRACE("(%p) : zStencilSurface  returning %p\n", This,  *ppZStencilSurface);
-
-    if(*ppZStencilSurface != NULL) {
-        /* Note inc ref on returned surface */
-        IWineD3DSurface_AddRef(*ppZStencilSurface);
-        return WINED3D_OK;
-    } else {
-        return WINED3DERR_NOTFOUND;
-    }
-}
-
-void stretch_rect_fbo(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *src_surface, const RECT *src_rect_in,
-        IWineD3DSurfaceImpl *dst_surface, const RECT *dst_rect_in, const WINED3DTEXTUREFILTERTYPE filter)
+static HRESULT WINAPI IWineD3DDeviceImpl_GetDepthStencilSurface(IWineD3DDevice *iface, IWineD3DSurface **depth_stencil)
 {
-    GLbitfield mask = GL_COLOR_BUFFER_BIT; /* TODO: Support blitting depth/stencil surfaces */
-    const struct wined3d_gl_info *gl_info;
-    struct wined3d_context *context;
-    GLenum gl_filter;
-    RECT src_rect, dst_rect;
-
-    TRACE("device %p, src_surface %p, src_rect_in %s, dst_surface %p, dst_rect_in %s, filter %s (0x%08x).\n",
-            device, src_surface, wine_dbgstr_rect(src_rect_in), dst_surface,
-            wine_dbgstr_rect(dst_rect_in), debug_d3dtexturefiltertype(filter), filter);
+    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)iface;
 
-    src_rect = *src_rect_in;
-    dst_rect = *dst_rect_in;
+    TRACE("iface %p, depth_stencil %p.\n", iface, depth_stencil);
 
-    switch (filter) {
-        case WINED3DTEXF_LINEAR:
-            gl_filter = GL_LINEAR;
-            break;
+    *depth_stencil = (IWineD3DSurface *)device->depth_stencil;
+    TRACE("Returning depth/stencil surface %p.\n", *depth_stencil);
+    if (!*depth_stencil) return WINED3DERR_NOTFOUND;
+    IWineD3DSurface_AddRef(*depth_stencil);
 
-        default:
-            FIXME("Unsupported filter mode %s (0x%08x)\n", debug_d3dtexturefiltertype(filter), filter);
-        case WINED3DTEXF_NONE:
-        case WINED3DTEXF_POINT:
-            gl_filter = GL_NEAREST;
-            break;
-    }
+    return WINED3D_OK;
+}
 
-    /* Make sure the drawables are up-to-date. Note that loading the
-     * destination surface isn't strictly required if we overwrite the
-     * entire surface. */
-    IWineD3DSurface_LoadLocation((IWineD3DSurface *)src_surface, SFLAG_INDRAWABLE, NULL);
-    IWineD3DSurface_LoadLocation((IWineD3DSurface *)dst_surface, SFLAG_INDRAWABLE, NULL);
+static HRESULT WINAPI IWineD3DDeviceImpl_SetRenderTarget(IWineD3DDevice *iface,
+        DWORD render_target_idx, IWineD3DSurface *render_target, BOOL set_viewport)
+{
+    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)iface;
+    IWineD3DSurfaceImpl *prev;
 
-    if (!surface_is_offscreen(src_surface)) context = context_acquire(device, src_surface);
-    else if (!surface_is_offscreen(dst_surface)) context = context_acquire(device, dst_surface);
-    else context = context_acquire(device, NULL);
+    TRACE("iface %p, render_target_idx %u, render_target %p, set_viewport %#x.\n",
+            iface, render_target_idx, render_target, set_viewport);
 
-    if (!context->valid)
+    if (render_target_idx >= device->adapter->gl_info.limits.buffers)
     {
-        context_release(context);
-        WARN("Invalid context, skipping blit.\n");
-        return;
+        WARN("Only %u render targets are supported.\n", device->adapter->gl_info.limits.buffers);
+        return WINED3DERR_INVALIDCALL;
     }
 
-    gl_info = context->gl_info;
-
-    if (!surface_is_offscreen(src_surface))
+    prev = device->render_targets[render_target_idx];
+    if (render_target == (IWineD3DSurface *)prev)
     {
-        GLenum buffer = surface_get_gl_buffer(src_surface);
-
-        TRACE("Source surface %p is onscreen\n", src_surface);
-
-        if (buffer == GL_FRONT)
-            surface_translate_frontbuffer_coords(src_surface, context->win_handle, &src_rect);
-
-        src_rect.top = src_surface->currentDesc.Height - src_rect.top;
-        src_rect.bottom = src_surface->currentDesc.Height - src_rect.bottom;
-
-        ENTER_GL();
-        context_bind_fbo(context, GL_READ_FRAMEBUFFER, NULL);
-        glReadBuffer(buffer);
-        checkGLcall("glReadBuffer()");
-    } else {
-        TRACE("Source surface %p is offscreen\n", src_surface);
-        ENTER_GL();
-        context_apply_fbo_state_blit(context, GL_READ_FRAMEBUFFER, src_surface, NULL);
-        glReadBuffer(GL_COLOR_ATTACHMENT0);
-        checkGLcall("glReadBuffer()");
+        TRACE("Trying to do a NOP SetRenderTarget operation.\n");
+        return WINED3D_OK;
     }
-    LEAVE_GL();
-
-    /* Attach dst surface to dst fbo */
-    if (!surface_is_offscreen(dst_surface))
-    {
-        GLenum buffer = surface_get_gl_buffer(dst_surface);
 
-        TRACE("Destination surface %p is onscreen\n", dst_surface);
-
-        if (buffer == GL_FRONT)
-            surface_translate_frontbuffer_coords(dst_surface, context->win_handle, &dst_rect);
-
-        dst_rect.top = dst_surface->currentDesc.Height - dst_rect.top;
-        dst_rect.bottom = dst_surface->currentDesc.Height - dst_rect.bottom;
-
-        ENTER_GL();
-        context_bind_fbo(context, GL_DRAW_FRAMEBUFFER, NULL);
-        context_set_draw_buffer(context, buffer);
-    }
-    else
+    /* Render target 0 can't be set to NULL. */
+    if (!render_target && !render_target_idx)
     {
-        TRACE("Destination surface %p is offscreen\n", dst_surface);
-
-        ENTER_GL();
-        context_apply_fbo_state_blit(context, GL_DRAW_FRAMEBUFFER, dst_surface, NULL);
-        context_set_draw_buffer(context, GL_COLOR_ATTACHMENT0);
+        WARN("Trying to set render target 0 to NULL.\n");
+        return WINED3DERR_INVALIDCALL;
     }
-    glDisable(GL_SCISSOR_TEST);
-    IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_SCISSORTESTENABLE));
-
-    gl_info->fbo_ops.glBlitFramebuffer(src_rect.left, src_rect.top, src_rect.right, src_rect.bottom,
-            dst_rect.left, dst_rect.top, dst_rect.right, dst_rect.bottom, mask, gl_filter);
-    checkGLcall("glBlitFramebuffer()");
-
-    LEAVE_GL();
-
-    if (wined3d_settings.strict_draw_ordering) wglFlush(); /* Flush to ensure ordering across contexts. */
-
-    context_release(context);
-
-    IWineD3DSurface_ModifyLocation((IWineD3DSurface *)dst_surface, SFLAG_INDRAWABLE, TRUE);
-}
-
-static HRESULT WINAPI IWineD3DDeviceImpl_SetRenderTarget(IWineD3DDevice *iface, DWORD RenderTargetIndex, IWineD3DSurface *pRenderTarget,
-                                                         BOOL set_viewport) {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-
-    TRACE("(%p) : Setting rendertarget %d to %p\n", This, RenderTargetIndex, pRenderTarget);
 
-    if (RenderTargetIndex >= This->adapter->gl_info.limits.buffers)
+    if (render_target && !(((IWineD3DSurfaceImpl *)render_target)->resource.usage & WINED3DUSAGE_RENDERTARGET))
     {
-        WARN("(%p) : Unsupported target %u set, returning WINED3DERR_INVALIDCALL(only %u supported)\n",
-                This, RenderTargetIndex, This->adapter->gl_info.limits.buffers);
+        FIXME("Surface %p doesn't have render target usage.\n", render_target);
         return WINED3DERR_INVALIDCALL;
     }
 
-    /* MSDN says that null disables the render target
-    but a device must always be associated with a render target
-    nope MSDN says that we return invalid call to a null rendertarget with an index of 0
-    */
-    if (RenderTargetIndex == 0 && pRenderTarget == NULL) {
-        FIXME("Trying to set render target 0 to NULL\n");
-        return WINED3DERR_INVALIDCALL;
-    }
-    if (pRenderTarget && !(((IWineD3DSurfaceImpl *)pRenderTarget)->resource.usage & WINED3DUSAGE_RENDERTARGET)) {
-        FIXME("(%p)Trying to set the render target to a surface(%p) that wasn't created with a usage of WINED3DUSAGE_RENDERTARGET\n",This ,pRenderTarget);
-        return WINED3DERR_INVALIDCALL;
-    }
+    if (render_target) IWineD3DSurface_AddRef(render_target);
+    device->render_targets[render_target_idx] = (IWineD3DSurfaceImpl *)render_target;
+    /* Release after the assignment, to prevent device_resource_released()
+     * from seeing the surface as still in use. */
+    if (prev) IWineD3DSurface_Release((IWineD3DSurface *)prev);
 
-    /* If we are trying to set what we already have, don't bother */
-    if (pRenderTarget == (IWineD3DSurface *)This->render_targets[RenderTargetIndex])
+    /* Render target 0 is special. */
+    if (!render_target_idx && set_viewport)
     {
-        TRACE("Trying to do a NOP SetRenderTarget operation\n");
-        return WINED3D_OK;
-    }
-    if (pRenderTarget)
-        IWineD3DSurface_AddRef(pRenderTarget);
-    if (This->render_targets[RenderTargetIndex])
-        IWineD3DSurface_Release((IWineD3DSurface *)This->render_targets[RenderTargetIndex]);
-    This->render_targets[RenderTargetIndex] = (IWineD3DSurfaceImpl *)pRenderTarget;
-
-    /* Render target 0 is special */
-    if(RenderTargetIndex == 0 && set_viewport) {
-        /* Finally, reset the viewport and scissor rect as the MSDN states.
-         * Tests show that stateblock recording is ignored, the change goes
-         * directly into the primary stateblock.
-         */
-        This->stateBlock->viewport.Height = This->render_targets[0]->currentDesc.Height;
-        This->stateBlock->viewport.Width  = This->render_targets[0]->currentDesc.Width;
-        This->stateBlock->viewport.X      = 0;
-        This->stateBlock->viewport.Y      = 0;
-        This->stateBlock->viewport.MaxZ   = 1.0f;
-        This->stateBlock->viewport.MinZ   = 0.0f;
-        IWineD3DDeviceImpl_MarkStateDirty(This, STATE_VIEWPORT);
-
-        This->stateBlock->scissorRect.top = 0;
-        This->stateBlock->scissorRect.left = 0;
-        This->stateBlock->scissorRect.right = This->stateBlock->viewport.Width;
-        This->stateBlock->scissorRect.bottom = This->stateBlock->viewport.Height;
-        IWineD3DDeviceImpl_MarkStateDirty(This, STATE_SCISSORRECT);
+        /* Set the viewport and scissor rectangles, if requested. Tests show
+         * that stateblock recording is ignored, the change goes directly
+         * into the primary stateblock. */
+        device->stateBlock->state.viewport.Height = device->render_targets[0]->currentDesc.Height;
+        device->stateBlock->state.viewport.Width  = device->render_targets[0]->currentDesc.Width;
+        device->stateBlock->state.viewport.X      = 0;
+        device->stateBlock->state.viewport.Y      = 0;
+        device->stateBlock->state.viewport.MaxZ   = 1.0f;
+        device->stateBlock->state.viewport.MinZ   = 0.0f;
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_VIEWPORT);
+
+        device->stateBlock->state.scissor_rect.top = 0;
+        device->stateBlock->state.scissor_rect.left = 0;
+        device->stateBlock->state.scissor_rect.right = device->stateBlock->state.viewport.Width;
+        device->stateBlock->state.scissor_rect.bottom = device->stateBlock->state.viewport.Height;
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_SCISSORRECT);
     }
+
     return WINED3D_OK;
 }
 
-static HRESULT WINAPI IWineD3DDeviceImpl_SetDepthStencilSurface(IWineD3DDevice *iface, IWineD3DSurface *pNewZStencil) {
+static HRESULT WINAPI IWineD3DDeviceImpl_SetDepthStencilSurface(IWineD3DDevice *iface, IWineD3DSurface *depth_stencil)
+{
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
     IWineD3DSurfaceImpl *tmp;
 
-    TRACE("device %p, depth_stencil %p, old depth_stencil %p.\n", This, pNewZStencil, This->depth_stencil);
+    TRACE("device %p, depth_stencil %p, old depth_stencil %p.\n", This, depth_stencil, This->depth_stencil);
 
-    if (This->depth_stencil == (IWineD3DSurfaceImpl *)pNewZStencil)
+    if (This->depth_stencil == (IWineD3DSurfaceImpl *)depth_stencil)
     {
         TRACE("Trying to do a NOP SetRenderTarget operation.\n");
         return WINED3D_OK;
@@ -5941,11 +5751,11 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetDepthStencilSurface(IWineD3DDevice *
     }
 
     tmp = This->depth_stencil;
-    This->depth_stencil = (IWineD3DSurfaceImpl *)pNewZStencil;
+    This->depth_stencil = (IWineD3DSurfaceImpl *)depth_stencil;
     if (This->depth_stencil) IWineD3DSurface_AddRef((IWineD3DSurface *)This->depth_stencil);
     if (tmp) IWineD3DSurface_Release((IWineD3DSurface *)tmp);
 
-    if ((!tmp && pNewZStencil) || (!pNewZStencil && tmp))
+    if ((!tmp && depth_stencil) || (!depth_stencil && tmp))
     {
         /* Swapping NULL / non NULL depth stencil affects the depth and tests */
         IWineD3DDeviceImpl_MarkStateDirty(This, STATE_RENDER(WINED3DRS_ZENABLE));
@@ -5956,14 +5766,15 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetDepthStencilSurface(IWineD3DDevice *
     return WINED3D_OK;
 }
 
-static HRESULT  WINAPI  IWineD3DDeviceImpl_SetCursorProperties(IWineD3DDevice* iface, UINT XHotSpot,
-                                                        UINT YHotSpot, IWineD3DSurface *pCursorBitmap) {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
-    /* TODO: the use of Impl is deprecated. */
-    IWineD3DSurfaceImpl * pSur = (IWineD3DSurfaceImpl *) pCursorBitmap;
+static HRESULT WINAPI IWineD3DDeviceImpl_SetCursorProperties(IWineD3DDevice *iface,
+        UINT XHotSpot, UINT YHotSpot, IWineD3DSurface *cursor_image)
+{
+    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+    IWineD3DSurfaceImpl *s = (IWineD3DSurfaceImpl *)cursor_image;
     WINED3DLOCKED_RECT lockedRect;
 
-    TRACE("(%p) : Spot Pos(%u,%u)\n", This, XHotSpot, YHotSpot);
+    TRACE("iface %p, hotspot_x %u, hotspot_y %u, cursor_image %p.\n",
+            iface, XHotSpot, YHotSpot, cursor_image);
 
     /* some basic validation checks */
     if (This->cursorTexture)
@@ -5976,25 +5787,28 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_SetCursorProperties(IWineD3DDevice* i
         This->cursorTexture = 0;
     }
 
-    if ( (pSur->currentDesc.Width == 32) && (pSur->currentDesc.Height == 32) )
+    if ((s->currentDesc.Width == 32) && (s->currentDesc.Height == 32))
         This->haveHardwareCursor = TRUE;
     else
         This->haveHardwareCursor = FALSE;
 
-    if(pCursorBitmap) {
+    if (cursor_image)
+    {
         WINED3DLOCKED_RECT rect;
 
         /* MSDN: Cursor must be A8R8G8B8 */
-        if (pSur->resource.format_desc->format != WINED3DFMT_B8G8R8A8_UNORM)
+        if (s->resource.format->id != WINED3DFMT_B8G8R8A8_UNORM)
         {
-            ERR("(%p) : surface(%p) has an invalid format\n", This, pCursorBitmap);
+            WARN("surface %p has an invalid format.\n", cursor_image);
             return WINED3DERR_INVALIDCALL;
         }
 
         /* MSDN: Cursor must be smaller than the display mode */
-        if(pSur->currentDesc.Width > This->ddraw_width ||
-           pSur->currentDesc.Height > This->ddraw_height) {
-            ERR("(%p) : Surface(%p) is %dx%d pixels, but screen res is %dx%d\n", This, pSur, pSur->currentDesc.Width, pSur->currentDesc.Height, This->ddraw_width, This->ddraw_height);
+        if (s->currentDesc.Width > This->ddraw_width
+                || s->currentDesc.Height > This->ddraw_height)
+        {
+            WARN("Surface %p dimensions are %ux%u, but screen dimensions are %ux%u.\n",
+                    s, s->currentDesc.Width, s->currentDesc.Height, This->ddraw_width, This->ddraw_height);
             return WINED3DERR_INVALIDCALL;
         }
 
@@ -6007,20 +5821,20 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_SetCursorProperties(IWineD3DDevice* i
              * creating circular refcount dependencies. Copy out the gl texture
              * instead.
              */
-            This->cursorWidth = pSur->currentDesc.Width;
-            This->cursorHeight = pSur->currentDesc.Height;
-            if (SUCCEEDED(IWineD3DSurface_LockRect(pCursorBitmap, &rect, NULL, WINED3DLOCK_READONLY)))
+            This->cursorWidth = s->currentDesc.Width;
+            This->cursorHeight = s->currentDesc.Height;
+            if (SUCCEEDED(IWineD3DSurface_LockRect(cursor_image, &rect, NULL, WINED3DLOCK_READONLY)))
             {
                 const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
-                const struct wined3d_format_desc *format_desc = getFormatDescEntry(WINED3DFMT_B8G8R8A8_UNORM, gl_info);
+                const struct wined3d_format *format = wined3d_get_format(gl_info, WINED3DFMT_B8G8R8A8_UNORM);
                 struct wined3d_context *context;
                 char *mem, *bits = rect.pBits;
-                GLint intfmt = format_desc->glInternal;
-                GLint format = format_desc->glFormat;
-                GLint type = format_desc->glType;
+                GLint intfmt = format->glInternal;
+                GLint gl_format = format->glFormat;
+                GLint type = format->glType;
                 INT height = This->cursorHeight;
                 INT width = This->cursorWidth;
-                INT bpp = format_desc->byte_count;
+                INT bpp = format->byte_count;
                 DWORD sampler;
                 INT i;
 
@@ -6029,7 +5843,7 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_SetCursorProperties(IWineD3DDevice* i
                 mem = HeapAlloc(GetProcessHeap(), 0, width * height * bpp);
                 for(i = 0; i < height; i++)
                     memcpy(&mem[width * bpp * i], &bits[rect.Pitch * i], width * bpp);
-                IWineD3DSurface_UnlockRect(pCursorBitmap);
+                IWineD3DSurface_UnlockRect(cursor_image);
 
                 context = context_acquire(This, NULL);
 
@@ -6055,7 +5869,7 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_SetCursorProperties(IWineD3DDevice* i
                 glBindTexture(GL_TEXTURE_2D, This->cursorTexture);
                 checkGLcall("glBindTexture");
                 /* Copy the bitmap memory into the cursor texture */
-                glTexImage2D(GL_TEXTURE_2D, 0, intfmt, width, height, 0, format, type, mem);
+                glTexImage2D(GL_TEXTURE_2D, 0, intfmt, width, height, 0, gl_format, type, mem);
                 HeapFree(GetProcessHeap(), 0, mem);
                 checkGLcall("glTexImage2D");
 
@@ -6084,22 +5898,17 @@ static HRESULT  WINAPI  IWineD3DDeviceImpl_SetCursorProperties(IWineD3DDevice* i
              * 32-bit cursors.  32x32 bits split into 32-bit chunks == 32
              * chunks. */
             DWORD *maskBits = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
-                (pSur->currentDesc.Width * pSur->currentDesc.Height / 8));
-            IWineD3DSurface_LockRect(pCursorBitmap, &lockedRect, NULL,
-                                         WINED3DLOCK_NO_DIRTY_UPDATE |
-                                         WINED3DLOCK_READONLY
-            );
-            TRACE("width: %i height: %i\n", pSur->currentDesc.Width,
-                  pSur->currentDesc.Height);
+                    (s->currentDesc.Width * s->currentDesc.Height / 8));
+            IWineD3DSurface_LockRect(cursor_image, &lockedRect, NULL,
+                    WINED3DLOCK_NO_DIRTY_UPDATE | WINED3DLOCK_READONLY);
+            TRACE("width: %u height: %u.\n", s->currentDesc.Width, s->currentDesc.Height);
 
             cursorInfo.fIcon = FALSE;
             cursorInfo.xHotspot = XHotSpot;
             cursorInfo.yHotspot = YHotSpot;
-            cursorInfo.hbmMask = CreateBitmap(pSur->currentDesc.Width, pSur->currentDesc.Height,
-                    1, 1, maskBits);
-            cursorInfo.hbmColor = CreateBitmap(pSur->currentDesc.Width, pSur->currentDesc.Height,
-                    1, 32, lockedRect.pBits);
-            IWineD3DSurface_UnlockRect(pCursorBitmap);
+            cursorInfo.hbmMask = CreateBitmap(s->currentDesc.Width, s->currentDesc.Height, 1, 1, maskBits);
+            cursorInfo.hbmColor = CreateBitmap(s->currentDesc.Width, s->currentDesc.Height, 1, 32, lockedRect.pBits);
+            IWineD3DSurface_UnlockRect(cursor_image);
             /* Create our cursor and clean up. */
             cursor = CreateIconIndirect(&cursorInfo);
             SetCursor(cursor);
@@ -6174,6 +5983,9 @@ static HRESULT WINAPI IWineD3DDeviceImpl_EvictManagedResources(IWineD3DDevice *i
     TRACE("iface %p.\n", iface);
 
     IWineD3DDevice_EnumResources(iface, evict_managed_resource, NULL);
+    /* Invalidate stream sources, the buffer(s) may have been evicted. */
+    IWineD3DDeviceImpl_MarkStateDirty((IWineD3DDeviceImpl *)iface, STATE_STREAMSRC);
+
     return WINED3D_OK;
 }
 
@@ -6196,7 +6008,7 @@ static HRESULT updateSurfaceDesc(IWineD3DSurfaceImpl *surface, const WINED3DPRES
     surface->currentDesc.Width = pPresentationParameters->BackBufferWidth;
     surface->currentDesc.Height = pPresentationParameters->BackBufferHeight;
     if (gl_info->supported[ARB_TEXTURE_NON_POWER_OF_TWO] || gl_info->supported[ARB_TEXTURE_RECTANGLE]
-            || gl_info->supported[WINE_NORMALIZED_TEXRECT])
+            || gl_info->supported[WINED3D_GL_NORMALIZED_TEXRECT])
     {
         surface->pow2Width = pPresentationParameters->BackBufferWidth;
         surface->pow2Height = pPresentationParameters->BackBufferHeight;
@@ -6270,6 +6082,7 @@ static BOOL is_display_mode_supported(IWineD3DDeviceImpl *This, const WINED3DPRE
     return FALSE;
 }
 
+/* Do not call while under the GL lock. */
 static void delete_opengl_contexts(IWineD3DDevice *iface, IWineD3DSwapChainImpl *swapchain)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
@@ -6314,6 +6127,7 @@ static void delete_opengl_contexts(IWineD3DDevice *iface, IWineD3DSwapChainImpl
     swapchain->num_contexts = 0;
 }
 
+/* Do not call while under the GL lock. */
 static HRESULT create_primary_opengl_context(IWineD3DDevice *iface, IWineD3DSwapChainImpl *swapchain)
 {
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
@@ -6378,7 +6192,10 @@ err:
     return hr;
 }
 
-static HRESULT WINAPI IWineD3DDeviceImpl_Reset(IWineD3DDevice* iface, WINED3DPRESENT_PARAMETERS* pPresentationParameters) {
+/* Do not call while under the GL lock. */
+static HRESULT WINAPI IWineD3DDeviceImpl_Reset(IWineD3DDevice *iface,
+        WINED3DPRESENT_PARAMETERS *pPresentationParameters)
+{
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
     IWineD3DSwapChainImpl *swapchain;
     HRESULT hr;
@@ -6429,18 +6246,19 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Reset(IWineD3DDevice* iface, WINED3DPRE
     swapchain->presentParms.FullScreen_RefreshRateInHz = pPresentationParameters->FullScreen_RefreshRateInHz;
 
     /* What to do about these? */
-    if(pPresentationParameters->BackBufferCount != 0 &&
-        pPresentationParameters->BackBufferCount != swapchain->presentParms.BackBufferCount) {
+    if (pPresentationParameters->BackBufferCount
+            && pPresentationParameters->BackBufferCount != swapchain->presentParms.BackBufferCount)
         ERR("Cannot change the back buffer count yet\n");
-    }
+
     if(pPresentationParameters->BackBufferFormat != WINED3DFMT_UNKNOWN &&
         pPresentationParameters->BackBufferFormat != swapchain->presentParms.BackBufferFormat) {
         ERR("Cannot change the back buffer format yet\n");
     }
-    if(pPresentationParameters->hDeviceWindow != NULL &&
-        pPresentationParameters->hDeviceWindow != swapchain->presentParms.hDeviceWindow) {
+
+    if (pPresentationParameters->hDeviceWindow
+            && pPresentationParameters->hDeviceWindow != swapchain->presentParms.hDeviceWindow)
         ERR("Cannot change the device window yet\n");
-    }
+
     if (pPresentationParameters->EnableAutoDepthStencil && !This->auto_depth_stencil)
     {
         HRESULT hrc;
@@ -6448,7 +6266,6 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Reset(IWineD3DDevice* iface, WINED3DPRE
         TRACE("Creating the depth stencil buffer\n");
 
         hrc = IWineD3DDeviceParent_CreateDepthStencilSurface(This->device_parent,
-                This->parent,
                 pPresentationParameters->BackBufferWidth,
                 pPresentationParameters->BackBufferHeight,
                 pPresentationParameters->AutoDepthStencilFormat,
@@ -6495,9 +6312,9 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Reset(IWineD3DDevice* iface, WINED3DPRE
     }
 
     /* Should Width == 800 && Height == 0 set 800x600? */
-    if(pPresentationParameters->BackBufferWidth != 0 && pPresentationParameters->BackBufferHeight != 0 &&
-       (pPresentationParameters->BackBufferWidth != swapchain->presentParms.BackBufferWidth ||
-        pPresentationParameters->BackBufferHeight != swapchain->presentParms.BackBufferHeight))
+    if (pPresentationParameters->BackBufferWidth && pPresentationParameters->BackBufferHeight
+            && (pPresentationParameters->BackBufferWidth != swapchain->presentParms.BackBufferWidth
+            || pPresentationParameters->BackBufferHeight != swapchain->presentParms.BackBufferHeight))
     {
         UINT i;
 
@@ -6537,15 +6354,30 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Reset(IWineD3DDevice* iface, WINED3DPRE
     if (!pPresentationParameters->Windowed != !swapchain->presentParms.Windowed
             || DisplayModeChanged)
     {
+        BOOL filter = This->filter_messages;
+        This->filter_messages = TRUE;
+
         IWineD3DDevice_SetDisplayMode(iface, 0, &mode);
 
         if (!pPresentationParameters->Windowed)
         {
-            if(swapchain->presentParms.Windowed) {
+            if (swapchain->presentParms.Windowed)
+            {
+                HWND focus_window = This->createParms.hFocusWindow;
+                if (!focus_window) focus_window = pPresentationParameters->hDeviceWindow;
+                if (FAILED(hr = IWineD3DDevice_AcquireFocusWindow(iface, focus_window)))
+                {
+                    ERR("Failed to acquire focus window, hr %#x.\n", hr);
+                    IWineD3DSwapChain_Release((IWineD3DSwapChain *)swapchain);
+                    return hr;
+                }
+
                 /* switch from windowed to fs */
                 swapchain_setup_fullscreen_window(swapchain, pPresentationParameters->BackBufferWidth,
                         pPresentationParameters->BackBufferHeight);
-            } else {
+            }
+            else
+            {
                 /* Fullscreen -> fullscreen mode change */
                 MoveWindow(swapchain->device_window, 0, 0,
                            pPresentationParameters->BackBufferWidth, pPresentationParameters->BackBufferHeight,
@@ -6556,9 +6388,14 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Reset(IWineD3DDevice* iface, WINED3DPRE
         {
             /* Fullscreen -> windowed switch */
             swapchain_restore_fullscreen_window(swapchain);
+            IWineD3DDevice_ReleaseFocusWindow(iface);
         }
         swapchain->presentParms.Windowed = pPresentationParameters->Windowed;
-    } else if(!pPresentationParameters->Windowed) {
+
+        This->filter_messages = filter;
+    }
+    else if (!pPresentationParameters->Windowed)
+    {
         DWORD style = This->style, exStyle = This->exStyle;
         /* If we're in fullscreen, and the mode wasn't changed, we have to get the window back into
          * the right position. Some applications(Battlefield 2, Guild Wars) move it and then call
@@ -6573,16 +6410,13 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Reset(IWineD3DDevice* iface, WINED3DPRE
     }
 
     /* Note: No parent needed for initial internal stateblock */
-    hr = IWineD3DDevice_CreateStateBlock(iface, WINED3DSBT_INIT, (IWineD3DStateBlock **)&This->stateBlock, NULL);
+    hr = IWineD3DDevice_CreateStateBlock(iface, WINED3DSBT_INIT, (IWineD3DStateBlock **)&This->stateBlock);
     if (FAILED(hr)) ERR("Resetting the stateblock failed with error 0x%08x\n", hr);
     else TRACE("Created stateblock %p\n", This->stateBlock);
     This->updateStateBlock = This->stateBlock;
     IWineD3DStateBlock_AddRef((IWineD3DStateBlock *)This->updateStateBlock);
 
-    hr = IWineD3DStateBlock_InitStartupStateBlock((IWineD3DStateBlock *) This->stateBlock);
-    if(FAILED(hr)) {
-        ERR("Resetting the stateblock failed with error 0x%08x\n", hr);
-    }
+    stateblock_init_default_state(This->stateBlock);
 
     if(wined3d_settings.offscreen_rendering_mode == ORM_FBO)
     {
@@ -6682,100 +6516,103 @@ static void device_resource_remove(IWineD3DDeviceImpl *This, IWineD3DResource *r
     list_remove(&((IWineD3DResourceImpl *) resource)->resource.resource_list_entry);
 }
 
-void device_resource_released(IWineD3DDeviceImpl *This, IWineD3DResource *resource)
+void device_resource_released(IWineD3DDeviceImpl *device, IWineD3DResource *resource)
 {
     WINED3DRESOURCETYPE type = IWineD3DResource_GetType(resource);
-    int counter;
+    unsigned int i;
 
-    TRACE("(%p) : resource %p\n", This, resource);
+    TRACE("device %p, resource %p, type %s.\n", device, resource, debug_d3dresourcetype(type));
 
-    context_resource_released((IWineD3DDevice *)This, resource, type);
+    context_resource_released(device, resource, type);
 
-    switch (type) {
-        /* TODO: check front and back buffers, rendertargets etc..  possibly swapchains? */
-        case WINED3DRTYPE_SURFACE: {
-            unsigned int i;
+    switch (type)
+    {
+        case WINED3DRTYPE_SURFACE:
+            if (!device->d3d_initialized) break;
 
-            if (This->d3d_initialized)
+            for (i = 0; i < device->adapter->gl_info.limits.buffers; ++i)
             {
-                for (i = 0; i < This->adapter->gl_info.limits.buffers; ++i)
+                if (device->render_targets[i] == (IWineD3DSurfaceImpl *)resource)
                 {
-                    if (This->render_targets[i] == (IWineD3DSurfaceImpl *)resource)
-                        This->render_targets[i] = NULL;
+                    ERR("Surface %p is still in use as render target %u.\n", resource, i);
+                    device->render_targets[i] = NULL;
                 }
-                if (This->depth_stencil == (IWineD3DSurfaceImpl *)resource)
-                    This->depth_stencil = NULL;
             }
 
+            if (device->depth_stencil == (IWineD3DSurfaceImpl *)resource)
+            {
+                ERR("Surface %p is still in use as depth/stencil buffer.\n", resource);
+                device->depth_stencil = NULL;
+            }
             break;
-        }
+
         case WINED3DRTYPE_TEXTURE:
         case WINED3DRTYPE_CUBETEXTURE:
         case WINED3DRTYPE_VOLUMETEXTURE:
-                for (counter = 0; counter < MAX_COMBINED_SAMPLERS; counter++) {
-                    if (This->stateBlock != NULL && This->stateBlock->textures[counter] == (IWineD3DBaseTexture *)resource) {
-                        WARN("Texture being released is still by a stateblock, Stage = %u Texture = %p\n", counter, resource);
-                        This->stateBlock->textures[counter] = NULL;
-                    }
-                    if (This->updateStateBlock != This->stateBlock ){
-                        if (This->updateStateBlock->textures[counter] == (IWineD3DBaseTexture *)resource) {
-                            WARN("Texture being released is still by a stateblock, Stage = %u Texture = %p\n", counter, resource);
-                            This->updateStateBlock->textures[counter] = NULL;
-                        }
-                    }
+            for (i = 0; i < MAX_COMBINED_SAMPLERS; ++i)
+            {
+                if (device->stateBlock && device->stateBlock->state.textures[i] == (IWineD3DBaseTextureImpl *)resource)
+                {
+                    ERR("Texture %p is still in use by stateblock %p, stage %u.\n",
+                            resource, device->stateBlock, i);
+                    device->stateBlock->state.textures[i] = NULL;
                 }
-        break;
-        case WINED3DRTYPE_VOLUME:
-        /* TODO: nothing really? */
-        break;
+
+                if (device->updateStateBlock != device->stateBlock
+                        && device->updateStateBlock->state.textures[i] == (IWineD3DBaseTextureImpl *)resource)
+                {
+                    ERR("Texture %p is still in use by stateblock %p, stage %u.\n",
+                            resource, device->updateStateBlock, i);
+                    device->updateStateBlock->state.textures[i] = NULL;
+                }
+            }
+            break;
+
         case WINED3DRTYPE_BUFFER:
-        {
-            int streamNumber;
-            TRACE("Cleaning up stream pointers\n");
-
-            for(streamNumber = 0; streamNumber < MAX_STREAMS; streamNumber ++){
-                /* FINDOUT: should a warn be generated if were recording and updateStateBlock->streamSource is lost?
-                FINDOUT: should changes.streamSource[StreamNumber] be set ?
-                */
-                if (This->updateStateBlock != NULL ) { /* ==NULL when device is being destroyed */
-                    if ((IWineD3DResource *)This->updateStateBlock->streamSource[streamNumber] == resource) {
-                        FIXME("Vertex buffer released while bound to a state block, stream %d\n", streamNumber);
-                        This->updateStateBlock->streamSource[streamNumber] = 0;
-                        /* Set changed flag? */
-                    }
+            for (i = 0; i < MAX_STREAMS; ++i)
+            {
+                if (device->stateBlock
+                        && device->stateBlock->state.streams[i].buffer == (struct wined3d_buffer *)resource)
+                {
+                    ERR("Buffer %p is still in use by stateblock %p, stream %u.\n",
+                            resource, device->stateBlock, i);
+                    device->stateBlock->state.streams[i].buffer = NULL;
                 }
-                if (This->stateBlock != NULL ) { /* only happens if there is an error in the application, or on reset/release (because we don't manage internal tracking properly) */
-                    if ((IWineD3DResource *)This->stateBlock->streamSource[streamNumber] == resource) {
-                        TRACE("Vertex buffer released while bound to a state block, stream %d\n", streamNumber);
-                        This->stateBlock->streamSource[streamNumber] = 0;
-                    }
+
+                if (device->updateStateBlock != device->stateBlock
+                        && device->updateStateBlock->state.streams[i].buffer == (struct wined3d_buffer *)resource)
+                {
+                    ERR("Buffer %p is still in use by stateblock %p, stream %u.\n",
+                            resource, device->updateStateBlock, i);
+                    device->updateStateBlock->state.streams[i].buffer = NULL;
                 }
+
             }
 
-            if (This->updateStateBlock != NULL ) { /* ==NULL when device is being destroyed */
-                if (This->updateStateBlock->pIndexData == (IWineD3DBuffer *)resource) {
-                    This->updateStateBlock->pIndexData =  NULL;
-                }
+            if (device->stateBlock && device->stateBlock->state.index_buffer == (struct wined3d_buffer *)resource)
+            {
+                ERR("Buffer %p is still in use by stateblock %p as index buffer.\n",
+                        resource, device->stateBlock);
+                device->stateBlock->state.index_buffer =  NULL;
             }
-            if (This->stateBlock != NULL ) { /* ==NULL when device is being destroyed */
-                if (This->stateBlock->pIndexData == (IWineD3DBuffer *)resource) {
-                    This->stateBlock->pIndexData =  NULL;
-                }
+
+            if (device->updateStateBlock != device->stateBlock
+                    && device->updateStateBlock->state.index_buffer == (struct wined3d_buffer *)resource)
+            {
+                ERR("Buffer %p is still in use by stateblock %p as index buffer.\n",
+                        resource, device->updateStateBlock);
+                device->updateStateBlock->state.index_buffer =  NULL;
             }
-        }
-        break;
+            break;
 
         default:
-        FIXME("(%p) unknown resource type %p %u\n", This, resource, IWineD3DResource_GetType(resource));
-        break;
+            break;
     }
 
-
     /* Remove the resource from the resourceStore */
-    device_resource_remove(This, resource);
-
-    TRACE("Resource released\n");
+    device_resource_remove(device, resource);
 
+    TRACE("Resource released.\n");
 }
 
 static HRESULT WINAPI IWineD3DDeviceImpl_EnumResources(IWineD3DDevice *iface, D3DCB_ENUMRESOURCES pCallback, void *pData) {
@@ -6829,7 +6666,6 @@ static const IWineD3DDeviceVtbl IWineD3DDevice_Vtbl =
     IWineD3DDeviceImpl_AddRef,
     IWineD3DDeviceImpl_Release,
     /*** IWineD3DDevice methods ***/
-    IWineD3DDeviceImpl_GetParent,
     /*** Creation methods**/
     IWineD3DDeviceImpl_CreateBuffer,
     IWineD3DDeviceImpl_CreateVertexBuffer,
@@ -6908,7 +6744,6 @@ static const IWineD3DDeviceVtbl IWineD3DDevice_Vtbl =
     IWineD3DDeviceImpl_GetRenderState,
     IWineD3DDeviceImpl_SetRenderTarget,
     IWineD3DDeviceImpl_GetRenderTarget,
-    IWineD3DDeviceImpl_SetFrontBackBuffers,
     IWineD3DDeviceImpl_SetSamplerState,
     IWineD3DDeviceImpl_GetSamplerState,
     IWineD3DDeviceImpl_SetScissorRect,
@@ -6974,7 +6809,7 @@ static const IWineD3DDeviceVtbl IWineD3DDevice_Vtbl =
 
 HRESULT device_init(IWineD3DDeviceImpl *device, IWineD3DImpl *wined3d,
         UINT adapter_idx, WINED3DDEVTYPE device_type, HWND focus_window, DWORD flags,
-        IUnknown *parent, IWineD3DDeviceParent *device_parent)
+        IWineD3DDeviceParent *device_parent)
 {
     struct wined3d_adapter *adapter = &wined3d->adapters[adapter_idx];
     const struct fragment_pipeline *fragment_pipeline;
@@ -6989,7 +6824,6 @@ HRESULT device_init(IWineD3DDeviceImpl *device, IWineD3DImpl *wined3d,
     device->wined3d = (IWineD3D *)wined3d;
     IWineD3D_AddRef(device->wined3d);
     device->adapter = wined3d->adapter_count ? adapter : NULL;
-    device->parent  = parent;
     device->device_parent = device_parent;
     list_init(&device->resources);
     list_init(&device->shaders);
index 2906147..1df2eaa 100644 (file)
@@ -77,6 +77,7 @@ static const struct {
     {"GL_ARB_sync",                         ARB_SYNC,                       0                           },
     {"GL_ARB_texture_border_clamp",         ARB_TEXTURE_BORDER_CLAMP,       0                           },
     {"GL_ARB_texture_compression",          ARB_TEXTURE_COMPRESSION,        0                           },
+    {"GL_ARB_texture_compression_rgtc",     ARB_TEXTURE_COMPRESSION_RGTC,   0                           },
     {"GL_ARB_texture_cube_map",             ARB_TEXTURE_CUBE_MAP,           0                           },
     {"GL_ARB_texture_env_add",              ARB_TEXTURE_ENV_ADD,            0                           },
     {"GL_ARB_texture_env_combine",          ARB_TEXTURE_ENV_COMBINE,        0                           },
@@ -104,6 +105,7 @@ static const struct {
     {"GL_EXT_blend_equation_separate",      EXT_BLEND_EQUATION_SEPARATE,    0                           },
     {"GL_EXT_blend_func_separate",          EXT_BLEND_FUNC_SEPARATE,        0                           },
     {"GL_EXT_blend_minmax",                 EXT_BLEND_MINMAX,               0                           },
+    {"GL_EXT_depth_bounds_test",            EXT_DEPTH_BOUNDS_TEST,          0                           },
     {"GL_EXT_draw_buffers2",                EXT_DRAW_BUFFERS2,              0                           },
     {"GL_EXT_fog_coord",                    EXT_FOG_COORD,                  0                           },
     {"GL_EXT_framebuffer_blit",             EXT_FRAMEBUFFER_BLIT,           0                           },
@@ -138,6 +140,7 @@ static const struct {
     {"GL_NV_fragment_program_option",       NV_FRAGMENT_PROGRAM_OPTION,     0                           },
     {"GL_NV_half_float",                    NV_HALF_FLOAT,                  0                           },
     {"GL_NV_light_max_exponent",            NV_LIGHT_MAX_EXPONENT,          0                           },
+    {"GL_NV_point_sprite",                  NV_POINT_SPRITE,                0                           },
     {"GL_NV_register_combiners",            NV_REGISTER_COMBINERS,          0                           },
     {"GL_NV_register_combiners2",           NV_REGISTER_COMBINERS2,         0                           },
     {"GL_NV_texgen_reflection",             NV_TEXGEN_REFLECTION,           0                           },
@@ -158,8 +161,6 @@ static const struct {
  * Utility functions follow
  **********************************************************/
 
-static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapter, WINED3DDEVTYPE DeviceType, WINED3DFORMAT AdapterFormat, DWORD Usage, WINED3DRESOURCETYPE RType, WINED3DFORMAT CheckFormat, WINED3DSURFTYPE SurfaceType);
-
 const struct min_lookup minMipLookup[] =
 {
     /* NONE         POINT                       LINEAR */
@@ -243,6 +244,7 @@ static void WineD3D_ReleaseFakeGLContext(struct wined3d_fake_gl_ctx *ctx)
     }
 }
 
+/* Do not call while under the GL lock. */
 static BOOL WineD3D_CreateFakeGLContext(struct wined3d_fake_gl_ctx *ctx)
 {
     PIXELFORMATDESCRIPTOR pfd;
@@ -337,7 +339,7 @@ unsigned int WineD3DAdapterChangeGLRam(IWineD3DDeviceImpl *device, unsigned int
 
 static void wined3d_adapter_cleanup(struct wined3d_adapter *adapter)
 {
-    HeapFree(GetProcessHeap(), 0, adapter->gl_info.gl_formats);
+    HeapFree(GetProcessHeap(), 0, adapter->gl_info.formats);
     HeapFree(GetProcessHeap(), 0, adapter->cfgs);
 }
 
@@ -374,7 +376,9 @@ static ULONG WINAPI IWineD3DImpl_Release(IWineD3D *iface) {
     ULONG ref;
     TRACE("(%p) : Releasing from %d\n", This, This->ref);
     ref = InterlockedDecrement(&This->ref);
-    if (ref == 0) {
+
+    if (!ref)
+    {
         unsigned int i;
 
         for (i = 0; i < This->adapter_count; ++i)
@@ -413,7 +417,8 @@ static inline BOOL test_arb_vs_offset_limit(const struct wined3d_gl_info *gl_inf
     GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB, prog));
     GL_EXTCALL(glProgramStringARB(GL_VERTEX_PROGRAM_ARB, GL_PROGRAM_FORMAT_ASCII_ARB,
                                   strlen(testcode), testcode));
-    if(glGetError() != 0) {
+    if (glGetError())
+    {
         TRACE("OpenGL implementation does not allow indirect addressing offsets > 63\n");
         TRACE("error: %s\n", debugstr_a((const char *)glGetString(GL_PROGRAM_ERROR_STRING_ARB)));
         ret = TRUE;
@@ -452,7 +457,9 @@ static BOOL match_geforce5(const struct wined3d_gl_info *gl_info, const char *gl
 {
     if (card_vendor == HW_VENDOR_NVIDIA)
     {
-        if (device == CARD_NVIDIA_GEFORCEFX_5800 || device == CARD_NVIDIA_GEFORCEFX_5600)
+        if (device == CARD_NVIDIA_GEFORCEFX_5200 ||
+            device == CARD_NVIDIA_GEFORCEFX_5600 ||
+            device == CARD_NVIDIA_GEFORCEFX_5800)
         {
             return TRUE;
         }
@@ -707,7 +714,7 @@ static BOOL match_fbo_tex_update(const struct wined3d_gl_info *gl_info, const ch
     glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 4, 4, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, data);
     checkGLcall("glTexSubImage2D");
 
-    glClearColor(0.996, 0.729, 0.745, 0.792);
+    glClearColor(0.996f, 0.729f, 0.745f, 0.792f);
     glClear(GL_COLOR_BUFFER_BIT);
     checkGLcall("glClear");
 
@@ -786,7 +793,7 @@ static void quirk_ati_dx9(struct wined3d_gl_info *gl_info)
     {
         TRACE("GL_ARB_texture_non_power_of_two advertised on R500 or earlier card, removing.\n");
         gl_info->supported[ARB_TEXTURE_NON_POWER_OF_TWO] = FALSE;
-        gl_info->supported[WINE_NORMALIZED_TEXRECT] = TRUE;
+        gl_info->supported[WINED3D_GL_NORMALIZED_TEXRECT] = TRUE;
     }
 
     /* fglrx has the same structural issues as the one described in quirk_apple_glsl_constants, although
@@ -960,89 +967,183 @@ static const struct driver_quirk quirk_table[] =
  * 7 -> Vista
  * 8 -> Win 7
  *
- * "y" is the Direct3D level the driver supports:
+ * "y" is the maximum Direct3D version the driver supports.
+ * y  -> d3d version mapping:
  * 11 -> d3d6
  * 12 -> d3d7
  * 13 -> d3d8
  * 14 -> d3d9
  * 15 -> d3d10
+ * 16 -> d3d10.1
+ * 17 -> d3d11
  *
- * "z" is unknown, possibly vendor specific.
+ * "z" is the subversion number.
  *
- * "w" is the vendor specific driver version.
+ * "w" is the vendor specific driver build number.
  */
+
 struct driver_version_information
+{
+    enum wined3d_display_driver driver;
+    enum wined3d_driver_model driver_model;
+    const char *driver_name;            /* name of Windows driver */
+    WORD version;                       /* version word ('y'), contained in low word of DriverVersion.HighPart */
+    WORD subversion;                    /* subversion word ('z'), contained in high word of DriverVersion.LowPart */
+    WORD build;                         /* build number ('w'), contained in low word of DriverVersion.LowPart */
+};
+
+/* The driver version table contains driver information for different devices on several OS versions. */
+static const struct driver_version_information driver_version_table[] =
+{
+    /* ATI
+     * - Radeon HD2x00 (R600) and up supported by current drivers.
+     * - Radeon 9500 (R300) - X1*00 (R5xx) supported upto Catalyst 9.3 (Linux) and 10.2 (XP/Vista/Win7)
+     * - Radeon 7xxx (R100) - 9250 (RV250) supported upto Catalyst 6.11 (XP)
+     * - Rage 128 supported upto XP, latest official build 6.13.3279 dated October 2001 */
+    {DRIVER_ATI_RAGE_128PRO,    DRIVER_MODEL_NT5X,  "ati2dvaa.dll", 13, 3279,  0},
+    {DRIVER_ATI_R100,           DRIVER_MODEL_NT5X,  "ati2dvag.dll", 14, 10, 6614},
+    {DRIVER_ATI_R300,           DRIVER_MODEL_NT5X,  "ati2dvag.dll", 14, 10, 6764},
+    {DRIVER_ATI_R600,           DRIVER_MODEL_NT5X,  "ati2dvag.dll", 14, 10, 8681},
+    {DRIVER_ATI_R300,           DRIVER_MODEL_NT6X,  "atiumdag.dll", 14, 10, 741 },
+    {DRIVER_ATI_R600,           DRIVER_MODEL_NT6X,  "atiumdag.dll", 14, 10, 741 },
+
+    /* Intel
+     * The drivers are unified but not all versions support all GPUs. At some point the 2k/xp
+     * drivers used ialmrnt5.dll for GMA800/GMA900 but at some point the file was renamed to
+     * igxprd32.dll but the GMA800 driver was never updated. */
+    {DRIVER_INTEL_GMA800,       DRIVER_MODEL_NT5X,  "ialmrnt5.dll", 14, 10, 3889},
+    {DRIVER_INTEL_GMA900,       DRIVER_MODEL_NT5X,  "igxprd32.dll", 14, 10, 4764},
+    {DRIVER_INTEL_GMA950,       DRIVER_MODEL_NT5X,  "igxprd32.dll", 14, 10, 4926},
+    {DRIVER_INTEL_GMA3000,      DRIVER_MODEL_NT5X,  "igxprd32.dll", 14, 10, 5218},
+    {DRIVER_INTEL_GMA950,       DRIVER_MODEL_NT6X,  "igdumd32.dll", 14, 10, 1504},
+    {DRIVER_INTEL_GMA3000,      DRIVER_MODEL_NT6X,  "igdumd32.dll", 15, 10, 1666},
+
+    /* Nvidia
+     * - Geforce6 and newer cards are supported by the current driver (197.x) on XP-Win7
+     * - GeforceFX support is up to 173.x on <= XP
+     * - Geforce2MX/3/4 up to 96.x on <= XP
+     * - TNT/Geforce1/2 up to 71.x on <= XP
+     * All version numbers used below are from the Linux nvidia drivers. */
+    {DRIVER_NVIDIA_TNT,         DRIVER_MODEL_NT5X,  "nv4_disp.dll", 14, 10, 7186},
+    {DRIVER_NVIDIA_GEFORCE2MX,  DRIVER_MODEL_NT5X,  "nv4_disp.dll", 14, 10, 9371},
+    {DRIVER_NVIDIA_GEFORCEFX,   DRIVER_MODEL_NT5X,  "nv4_disp.dll", 14, 11, 7516},
+    {DRIVER_NVIDIA_GEFORCE6,    DRIVER_MODEL_NT5X,  "nv4_disp.dll", 15, 11, 9745},
+    {DRIVER_NVIDIA_GEFORCE6,    DRIVER_MODEL_NT6X,  "nvd3dum.dll",  15, 11, 9745},
+};
+
+struct gpu_description
 {
     WORD vendor;                    /* reported PCI card vendor ID  */
     WORD card;                      /* reported PCI card device ID  */
     const char *description;        /* Description of the card e.g. NVIDIA RIVA TNT */
-    WORD d3d_level;                 /* driver hiword to report      */
-    WORD lopart_hi, lopart_lo;      /* driver loword to report      */
+    enum wined3d_display_driver driver;
+    unsigned int vidmem;
 };
 
-static const struct driver_version_information driver_version_table[] =
+/* The amount of video memory stored in the gpu description table is the minimum amount of video memory
+ * found on a board containing a specific GPU. */
+static const struct gpu_description gpu_description_table[] =
 {
-    /* Nvidia drivers. Geforce6 and newer cards are supported by the current driver (180.x)
-     * GeforceFX support is up to 173.x, - driver uses numbering x.y.11.7341 for 173.41 where x is the windows revision (6=2000/xp, 7=vista), y is unknown
-     * Geforce2MX/3/4 up to 96.x - driver uses numbering 9.6.8.9 for 96.89
-     * TNT/Geforce1/2 up to 71.x - driver uses numbering 7.1.8.6 for 71.86
-     *
-     * All version numbers used below are from the Linux nvidia drivers. */
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_RIVA_TNT,           "NVIDIA RIVA TNT",                  1,  8,  6      },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_RIVA_TNT2,          "NVIDIA RIVA TNT2/TNT2 Pro",        1,  8,  6      },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE,            "NVIDIA GeForce 256",               1,  8,  6      },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE2_MX,        "NVIDIA GeForce2 MX/MX 400",        6,  4,  3      },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE2,           "NVIDIA GeForce2 GTS/GeForce2 Pro", 1,  8,  6      },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE3,           "NVIDIA GeForce3",                  6,  10, 9371   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE4_MX,        "NVIDIA GeForce4 MX 460",           6,  10, 9371   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE4_TI4200,    "NVIDIA GeForce4 Ti 4200",          6,  10, 9371   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCEFX_5200,     "NVIDIA GeForce FX 5200",           15, 11, 7516   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCEFX_5600,     "NVIDIA GeForce FX 5600",           15, 11, 7516   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCEFX_5800,     "NVIDIA GeForce FX 5800",           15, 11, 7516   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_6200,       "NVIDIA GeForce 6200",              15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_6600GT,     "NVIDIA GeForce 6600 GT",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_6800,       "NVIDIA GeForce 6800",              15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7300,       "NVIDIA GeForce Go 7300",           15, 11, 8585   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7400,       "NVIDIA GeForce Go 7400",           15, 11, 8585   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7600,       "NVIDIA GeForce 7600 GT",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7800GT,     "NVIDIA GeForce 7800 GT",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8300GS,     "NVIDIA GeForce 8300 GS",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8600GT,     "NVIDIA GeForce 8600 GT",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8600MGT,    "NVIDIA GeForce 8600M GT",          15, 11, 8585   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8800GTS,    "NVIDIA GeForce 8800 GTS",          15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9200,       "NVIDIA GeForce 9200",              15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9400GT,     "NVIDIA GeForce 9400 GT",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9500GT,     "NVIDIA GeForce 9500 GT",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9600GT,     "NVIDIA GeForce 9600 GT",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9800GT,     "NVIDIA GeForce 9800 GT",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX260,     "NVIDIA GeForce GTX 260",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX275,     "NVIDIA GeForce GTX 275",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX280,     "NVIDIA GeForce GTX 280",           15, 11, 8618   },
-    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GT240,      "NVIDIA GeForce GT 240",            15, 11, 8618   },
-
-    /* ATI cards. The driver versions are somewhat similar, but not quite the same. Let's hardcode. */
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_9500,           "ATI Radeon 9500",                  14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_X700,           "ATI Radeon X700 SE",               14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_X1600,          "ATI Radeon X1600 Series",          14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD2350,         "ATI Mobility Radeon HD 2350",      14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD2600,         "ATI Mobility Radeon HD 2600",      14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD2900,         "ATI Radeon HD 2900 XT",            14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4350,         "ATI Radeon HD 4350",               14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4600,         "ATI Radeon HD 4600 Series",        14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4700,         "ATI Radeon HD 4700 Series",        14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4800,         "ATI Radeon HD 4800 Series",        14, 10, 6764    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD5700,         "ATI Radeon HD 5700 Series",        14, 10, 8681    },
-    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD5800,         "ATI Radeon HD 5800 Series",        14, 10, 8681    },
-
-    /* TODO: Add information about legacy ATI hardware, Intel and other cards. */
+    /* Nvidia cards */
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_RIVA_TNT,           "NVIDIA RIVA TNT",                  DRIVER_NVIDIA_TNT,       16  },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_RIVA_TNT2,          "NVIDIA RIVA TNT2/TNT2 Pro",        DRIVER_NVIDIA_TNT,       32  },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE,            "NVIDIA GeForce 256",               DRIVER_NVIDIA_TNT,       32  },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE2,           "NVIDIA GeForce2 GTS/GeForce2 Pro", DRIVER_NVIDIA_TNT,       32  },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE2_MX,        "NVIDIA GeForce2 MX/MX 400",        DRIVER_NVIDIA_GEFORCE2MX,32  },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE3,           "NVIDIA GeForce3",                  DRIVER_NVIDIA_GEFORCE2MX,64  },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE4_MX,        "NVIDIA GeForce4 MX 460",           DRIVER_NVIDIA_GEFORCE2MX,64  },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE4_TI4200,    "NVIDIA GeForce4 Ti 4200",          DRIVER_NVIDIA_GEFORCE2MX,64, },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCEFX_5200,     "NVIDIA GeForce FX 5200",           DRIVER_NVIDIA_GEFORCEFX, 64  },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCEFX_5600,     "NVIDIA GeForce FX 5600",           DRIVER_NVIDIA_GEFORCEFX, 128 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCEFX_5800,     "NVIDIA GeForce FX 5800",           DRIVER_NVIDIA_GEFORCEFX, 256 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_6200,       "NVIDIA GeForce 6200",              DRIVER_NVIDIA_GEFORCE6,  64  },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_6600GT,     "NVIDIA GeForce 6600 GT",           DRIVER_NVIDIA_GEFORCE6,  128 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_6800,       "NVIDIA GeForce 6800",              DRIVER_NVIDIA_GEFORCE6,  128 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7300,       "NVIDIA GeForce Go 7300",           DRIVER_NVIDIA_GEFORCE6,  256 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7400,       "NVIDIA GeForce Go 7400",           DRIVER_NVIDIA_GEFORCE6,  256 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7600,       "NVIDIA GeForce 7600 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7800GT,     "NVIDIA GeForce 7800 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8300GS,     "NVIDIA GeForce 8300 GS",           DRIVER_NVIDIA_GEFORCE6,  128 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8400GS,     "NVIDIA GeForce 8400 GS",           DRIVER_NVIDIA_GEFORCE6,  128 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8600GT,     "NVIDIA GeForce 8600 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8600MGT,    "NVIDIA GeForce 8600M GT",          DRIVER_NVIDIA_GEFORCE6,  512 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8800GTS,    "NVIDIA GeForce 8800 GTS",          DRIVER_NVIDIA_GEFORCE6,  320 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8800GTX,    "NVIDIA GeForce 8800 GTX",          DRIVER_NVIDIA_GEFORCE6,  768 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9200,       "NVIDIA GeForce 9200",              DRIVER_NVIDIA_GEFORCE6,  256 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9400GT,     "NVIDIA GeForce 9400 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9500GT,     "NVIDIA GeForce 9500 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9600GT,     "NVIDIA GeForce 9600 GT",           DRIVER_NVIDIA_GEFORCE6,  384 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9800GT,     "NVIDIA GeForce 9800 GT",           DRIVER_NVIDIA_GEFORCE6,  512 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_210,        "NVIDIA GeForce 210",               DRIVER_NVIDIA_GEFORCE6,  512 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GT220,      "NVIDIA GeForce GT 220",            DRIVER_NVIDIA_GEFORCE6,  512 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GT240,      "NVIDIA GeForce GT 240",            DRIVER_NVIDIA_GEFORCE6,  512 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX260,     "NVIDIA GeForce GTX 260",           DRIVER_NVIDIA_GEFORCE6,  1024},
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX275,     "NVIDIA GeForce GTX 275",           DRIVER_NVIDIA_GEFORCE6,  896 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX280,     "NVIDIA GeForce GTX 280",           DRIVER_NVIDIA_GEFORCE6,  1024},
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GT325M,     "NVIDIA GeForce GT 325M",           DRIVER_NVIDIA_GEFORCE6,  1024},
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTS350M,    "NVIDIA GeForce GTS 350M",          DRIVER_NVIDIA_GEFORCE6,  1024},
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX460,     "NVIDIA GeForce GTX 460",           DRIVER_NVIDIA_GEFORCE6,  768 },
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX465,     "NVIDIA GeForce GTX 465",           DRIVER_NVIDIA_GEFORCE6,  1024},
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX470,     "NVIDIA GeForce GTX 470",           DRIVER_NVIDIA_GEFORCE6,  1280},
+    {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX480,     "NVIDIA GeForce GTX 480",           DRIVER_NVIDIA_GEFORCE6,  1536},
+    /* ATI cards */
+    {HW_VENDOR_ATI,        CARD_ATI_RAGE_128PRO,           "ATI Rage Fury",                    DRIVER_ATI_RAGE_128PRO,  16  },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_7200,           "ATI RADEON 7200 SERIES",           DRIVER_ATI_R100,         32  },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_8500,           "ATI RADEON 8500 SERIES",           DRIVER_ATI_R100,         64  },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_9500,           "ATI Radeon 9500",                  DRIVER_ATI_R300,         64  },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_XPRESS_200M,    "ATI RADEON XPRESS 200M Series",    DRIVER_ATI_R300,         64  },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_X700,           "ATI Radeon X700 SE",               DRIVER_ATI_R300,         128 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_X1600,          "ATI Radeon X1600 Series",          DRIVER_ATI_R300,         128 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD2350,         "ATI Mobility Radeon HD 2350",      DRIVER_ATI_R600,         256 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD2600,         "ATI Mobility Radeon HD 2600",      DRIVER_ATI_R600,         256 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD2900,         "ATI Radeon HD 2900 XT",            DRIVER_ATI_R600,         512 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD3200,         "ATI Radeon HD 3200 Graphics",      DRIVER_ATI_R600,         128 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4350,         "ATI Radeon HD 4350",               DRIVER_ATI_R600,         256 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4600,         "ATI Radeon HD 4600 Series",        DRIVER_ATI_R600,         512 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4700,         "ATI Radeon HD 4700 Series",        DRIVER_ATI_R600,         512 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4800,         "ATI Radeon HD 4800 Series",        DRIVER_ATI_R600,         512 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD5700,         "ATI Radeon HD 5700 Series",        DRIVER_ATI_R600,         512 },
+    {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD5800,         "ATI Radeon HD 5800 Series",        DRIVER_ATI_R600,         1024},
+    /* Intel cards */
+    {HW_VENDOR_INTEL,      CARD_INTEL_I830G,               "Intel(R) 82830M Graphics Controller",                       DRIVER_INTEL_GMA800,  32 },
+    {HW_VENDOR_INTEL,      CARD_INTEL_I855G,               "Intel(R) 82852/82855 GM/GME Graphics Controller",           DRIVER_INTEL_GMA800,  32 },
+    {HW_VENDOR_INTEL,      CARD_INTEL_I865G,               "Intel(R) 82865G Graphics Controller",                       DRIVER_INTEL_GMA800,  32 },
+    {HW_VENDOR_INTEL,      CARD_INTEL_I915G,               "Intel(R) 82915G/GV/910GL Express Chipset Family",           DRIVER_INTEL_GMA900,  64 },
+    {HW_VENDOR_INTEL,      CARD_INTEL_I915GM,              "Mobile Intel(R) 915GM/GMS,910GML Express Chipset Family",   DRIVER_INTEL_GMA900,  64 },
+    {HW_VENDOR_INTEL,      CARD_INTEL_I945GM,              "Mobile Intel(R) 945GM Express Chipset Family",              DRIVER_INTEL_GMA950,  64 },
+    {HW_VENDOR_INTEL,      CARD_INTEL_X3100,               "Mobile Intel(R) 965 Express Chipset Family",                DRIVER_INTEL_GMA3000, 128}
 };
 
+static const struct driver_version_information *get_driver_version_info(enum wined3d_display_driver driver,
+        enum wined3d_driver_model driver_model)
+{
+    unsigned int i;
+
+    TRACE("Looking up version info for driver=%d driver_model=%d\n", driver, driver_model);
+    for (i = 0; i < (sizeof(driver_version_table) / sizeof(driver_version_table[0])); i++)
+    {
+        const struct driver_version_information *entry = &driver_version_table[i];
+
+        if (entry->driver == driver && entry->driver_model == driver_model)
+        {
+            TRACE_(d3d_caps)("Found driver '%s' version=%d subversion=%d build=%d\n",
+                entry->driver_name, entry->version, entry->subversion, entry->build);
+
+            return entry;
+        }
+    }
+    return NULL;
+}
+
 static void init_driver_info(struct wined3d_driver_info *driver_info,
         enum wined3d_pci_vendor vendor, enum wined3d_pci_device device)
 {
     OSVERSIONINFOW os_version;
     WORD driver_os_version;
     unsigned int i;
+    enum wined3d_display_driver driver = DRIVER_UNKNOWN;
+    enum wined3d_driver_model driver_model;
+    const struct driver_version_information *version_info;
 
     if (wined3d_settings.pci_vendor_id != PCI_VENDOR_NONE)
     {
@@ -1058,22 +1159,9 @@ static void init_driver_info(struct wined3d_driver_info *driver_info,
     }
     driver_info->device = device;
 
-    switch (vendor)
-    {
-        case HW_VENDOR_ATI:
-            driver_info->name = "ati2dvag.dll";
-            break;
-
-        case HW_VENDOR_NVIDIA:
-            driver_info->name = "nv4_disp.dll";
-            break;
-
-        case HW_VENDOR_INTEL:
-        default:
-            FIXME_(d3d_caps)("Unhandled vendor %04x.\n", vendor);
-            driver_info->name = "Display";
-            break;
-    }
+    /* Set a default amount of video memory (64MB). In general this code isn't used unless the user
+     * overrides the pci ids to a card which is not in our database. */
+    driver_info->vidmem = WINE_DEFAULT_VIDMEM;
 
     memset(&os_version, 0, sizeof(os_version));
     os_version.dwOSVersionInfoSize = sizeof(os_version);
@@ -1081,6 +1169,7 @@ static void init_driver_info(struct wined3d_driver_info *driver_info,
     {
         ERR("Failed to get OS version, reporting 2000/XP.\n");
         driver_os_version = 6;
+        driver_model = DRIVER_MODEL_NT5X;
     }
     else
     {
@@ -1088,17 +1177,23 @@ static void init_driver_info(struct wined3d_driver_info *driver_info,
         switch (os_version.dwMajorVersion)
         {
             case 4:
+                /* If needed we could distinguish between 9x and NT4, but this code won't make
+                 * sense for NT4 since it had no way to obtain this info through DirectDraw 3.0.
+                 */
                 driver_os_version = 4;
+                driver_model = DRIVER_MODEL_WIN9X;
                 break;
 
             case 5:
                 driver_os_version = 6;
+                driver_model = DRIVER_MODEL_NT5X;
                 break;
 
             case 6:
                 if (os_version.dwMinorVersion == 0)
                 {
                     driver_os_version = 7;
+                    driver_model = DRIVER_MODEL_NT6X;
                 }
                 else
                 {
@@ -1108,6 +1203,7 @@ static void init_driver_info(struct wined3d_driver_info *driver_info,
                                 os_version.dwMajorVersion, os_version.dwMinorVersion);
                     }
                     driver_os_version = 8;
+                    driver_model = DRIVER_MODEL_NT6X;
                 }
                 break;
 
@@ -1115,28 +1211,73 @@ static void init_driver_info(struct wined3d_driver_info *driver_info,
                 FIXME("Unhandled OS version %u.%u, reporting 2000/XP.\n",
                         os_version.dwMajorVersion, os_version.dwMinorVersion);
                 driver_os_version = 6;
+                driver_model = DRIVER_MODEL_NT5X;
                 break;
         }
     }
 
-    driver_info->description = "Direct3D HAL";
-    driver_info->version_high = MAKEDWORD_VERSION(driver_os_version, 15);
-    driver_info->version_low = MAKEDWORD_VERSION(8, 6); /* Nvidia RIVA TNT, arbitrary */
-
-    for (i = 0; i < (sizeof(driver_version_table) / sizeof(driver_version_table[0])); ++i)
+    /* When we reach this stage we always have a vendor or device id (it can be a default one).
+     * This means that unless the ids are overriden, we will always find a GPU description. */
+    for (i = 0; i < (sizeof(gpu_description_table) / sizeof(gpu_description_table[0])); i++)
     {
-        if (vendor == driver_version_table[i].vendor && device == driver_version_table[i].card)
+        if (vendor == gpu_description_table[i].vendor && device == gpu_description_table[i].card)
         {
             TRACE_(d3d_caps)("Found card %04x:%04x in driver DB.\n", vendor, device);
 
-            driver_info->description = driver_version_table[i].description;
-            driver_info->version_high = MAKEDWORD_VERSION(driver_os_version, driver_version_table[i].d3d_level);
-            driver_info->version_low = MAKEDWORD_VERSION(driver_version_table[i].lopart_hi,
-                    driver_version_table[i].lopart_lo);
+            driver_info->description = gpu_description_table[i].description;
+            driver_info->vidmem = gpu_description_table[i].vidmem * 1024*1024;
+            driver = gpu_description_table[i].driver;
             break;
         }
     }
 
+    if (wined3d_settings.emulated_textureram)
+    {
+        TRACE_(d3d_caps)("Overriding amount of video memory with: %d byte\n", wined3d_settings.emulated_textureram);
+        driver_info->vidmem = wined3d_settings.emulated_textureram;
+    }
+
+    /* Try to obtain driver version information for the current Windows version. This fails in
+     * some cases:
+     * - the gpu is not available on the currently selected OS version:
+     *   - Geforce GTX480 on Win98. When running applications in compatibility mode on Windows,
+     *     version information for the current Windows version is returned instead of faked info.
+     *     We do the same and assume the default Windows version to emulate is WinXP.
+     *
+     *   - Videocard is a Riva TNT but winver is set to win7 (there are no drivers for this beast)
+     *     For now return the XP driver info. Perhaps later on we should return VESA.
+     *
+     * - the gpu is not in our database (can happen when the user overrides the vendor_id / device_id)
+     *   This could be an indication that our database is not up to date, so this should be fixed.
+     */
+    version_info = get_driver_version_info(driver, driver_model);
+    if (version_info)
+    {
+        driver_info->name = version_info->driver_name;
+        driver_info->version_high = MAKEDWORD_VERSION(driver_os_version, version_info->version);
+        driver_info->version_low = MAKEDWORD_VERSION(version_info->subversion, version_info->build);
+    }
+    else
+    {
+        version_info = get_driver_version_info(driver, DRIVER_MODEL_NT5X);
+        if (version_info)
+        {
+            driver_info->name = version_info->driver_name;
+            driver_info->version_high = MAKEDWORD_VERSION(driver_os_version, version_info->version);
+            driver_info->version_low = MAKEDWORD_VERSION(version_info->subversion, version_info->build);
+        }
+        else
+        {
+            driver_info->description = "Direct3D HAL";
+            driver_info->name = "Display";
+            driver_info->version_high = MAKEDWORD_VERSION(driver_os_version, 15);
+            driver_info->version_low = MAKEDWORD_VERSION(8, 6); /* Nvidia RIVA TNT, arbitrary */
+
+            FIXME("Unable to find a driver/device info for vendor_id=%#x device_id=%#x for driver_model=%d\n",
+                    vendor, device, driver_model);
+        }
+    }
+
     TRACE_(d3d_caps)("Reporting (fake) driver version 0x%08x-0x%08x.\n",
             driver_info->version_high, driver_info->version_low);
 }
@@ -1232,7 +1373,11 @@ static enum wined3d_pci_vendor wined3d_guess_card_vendor(const char *gl_vendor_s
     if (strstr(gl_vendor_string, "ATI")
             || strstr(gl_vendor_string, "Advanced Micro Devices, Inc.")
             || strstr(gl_vendor_string, "X.Org R300 Project")
-            || strstr(gl_vendor_string, "DRI R300 Project"))
+            || strstr(gl_renderer, "R100")
+            || strstr(gl_renderer, "R200")
+            || strstr(gl_renderer, "R300")
+            || strstr(gl_renderer, "R600")
+            || strstr(gl_renderer, "R700"))
         return HW_VENDOR_ATI;
 
     if (strstr(gl_vendor_string, "Intel(R)")
@@ -1254,52 +1399,99 @@ static enum wined3d_pci_vendor wined3d_guess_card_vendor(const char *gl_vendor_s
 
 
 static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl_info *gl_info,
-        const char *gl_renderer, unsigned int *vidmem)
+        const char *gl_renderer)
 {
     if (WINE_D3D10_CAPABLE(gl_info))
     {
+        /* Geforce 400 - highend */
+        if (strstr(gl_renderer, "GTX 480"))
+        {
+            return CARD_NVIDIA_GEFORCE_GTX480;
+        }
+
+        /* Geforce 400 - midend high */
+        if (strstr(gl_renderer, "GTX 470"))
+        {
+            return CARD_NVIDIA_GEFORCE_GTX470;
+        }
+
+        /* Geforce 400 - midend */
+        if (strstr(gl_renderer, "GTX 465"))
+        {
+            return CARD_NVIDIA_GEFORCE_GTX465;
+        }
+
+        /* Geforce 400 - midend */
+        if (strstr(gl_renderer, "GTX 460"))
+        {
+            return CARD_NVIDIA_GEFORCE_GTX460;
+        }
+
+        /* Geforce 300 highend mobile */
+        if (strstr(gl_renderer, "GTS 350M")
+                || strstr(gl_renderer, "GTS 360M"))
+        {
+            return CARD_NVIDIA_GEFORCE_GTS350M;
+        }
+
+        /* Geforce 300 midend mobile (Geforce GT 325M/330M use the same core) */
+        if (strstr(gl_renderer, "GT 325M")
+                || strstr(gl_renderer, "GT 330M"))
+        {
+            return CARD_NVIDIA_GEFORCE_GT325M;
+        }
+
         /* Geforce 200 - highend */
         if (strstr(gl_renderer, "GTX 280")
                 || strstr(gl_renderer, "GTX 285")
                 || strstr(gl_renderer, "GTX 295"))
         {
-            *vidmem = 1024;
             return CARD_NVIDIA_GEFORCE_GTX280;
         }
 
         /* Geforce 200 - midend high */
         if (strstr(gl_renderer, "GTX 275"))
         {
-            *vidmem = 896;
             return CARD_NVIDIA_GEFORCE_GTX275;
         }
 
         /* Geforce 200 - midend */
         if (strstr(gl_renderer, "GTX 260"))
         {
-            *vidmem = 1024;
             return CARD_NVIDIA_GEFORCE_GTX260;
         }
         /* Geforce 200 - midend */
         if (strstr(gl_renderer, "GT 240"))
         {
-           *vidmem = 512;
            return CARD_NVIDIA_GEFORCE_GT240;
         }
 
+        /* Geforce 200 lowend */
+        if (strstr(gl_renderer, "GT 220"))
+        {
+           return CARD_NVIDIA_GEFORCE_GT220;
+        }
+        /* Geforce 200 lowend (Geforce 305/310 use the same core) */
+        if (strstr(gl_renderer, "Geforce 210")
+                || strstr(gl_renderer, "G 210")
+                || strstr(gl_renderer, "Geforce 305")
+                || strstr(gl_renderer, "Geforce 310"))
+        {
+           return CARD_NVIDIA_GEFORCE_210;
+        }
+
         /* Geforce9 - highend / Geforce 200 - midend (GTS 150/250 are based on the same core) */
         if (strstr(gl_renderer, "9800")
                 || strstr(gl_renderer, "GTS 150")
                 || strstr(gl_renderer, "GTS 250"))
         {
-            *vidmem = 512;
             return CARD_NVIDIA_GEFORCE_9800GT;
         }
 
-        /* Geforce9 - midend */
-        if (strstr(gl_renderer, "9600"))
+        /* Geforce9 - midend (GT 140 uses the same core as the 9600GT) */
+        if (strstr(gl_renderer, "9600")
+                || strstr(gl_renderer, "GT 140"))
         {
-            *vidmem = 384; /* The 9600GSO has 384MB, the 9600GT has 512-1024MB */
             return CARD_NVIDIA_GEFORCE_9600GT;
         }
 
@@ -1308,14 +1500,12 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
                 || strstr(gl_renderer, "GT 120")
                 || strstr(gl_renderer, "GT 130"))
         {
-            *vidmem = 256; /* The 9500GT has 256-1024MB */
             return CARD_NVIDIA_GEFORCE_9500GT;
         }
 
         /* Geforce9 - lowend */
         if (strstr(gl_renderer, "9400"))
         {
-            *vidmem = 256; /* The 9400GT has 256-1024MB */
             return CARD_NVIDIA_GEFORCE_9400GT;
         }
 
@@ -1325,21 +1515,24 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
                 || strstr(gl_renderer, "9300")
                 || strstr(gl_renderer, "G 100"))
         {
-            *vidmem = 256; /* The 9100-9300 cards have 256MB */
             return CARD_NVIDIA_GEFORCE_9200;
         }
 
+        /* Geforce8 - highend high*/
+        if (strstr(gl_renderer, "8800 GTX"))
+        {
+            return CARD_NVIDIA_GEFORCE_8800GTX;
+        }
+
         /* Geforce8 - highend */
         if (strstr(gl_renderer, "8800"))
         {
-            *vidmem = 320; /* The 8800GTS uses 320MB, a 8800GTX can have 768MB */
             return CARD_NVIDIA_GEFORCE_8800GTS;
         }
 
         /* Geforce8 - midend mobile */
         if (strstr(gl_renderer, "8600 M"))
         {
-            *vidmem = 512;
             return CARD_NVIDIA_GEFORCE_8600MGT;
         }
 
@@ -1347,23 +1540,25 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
         if (strstr(gl_renderer, "8600")
                 || strstr(gl_renderer, "8700"))
         {
-            *vidmem = 256;
             return CARD_NVIDIA_GEFORCE_8600GT;
         }
 
+        /* Geforce8 - mid-lowend */
+        if (strstr(gl_renderer, "8400")
+                || strstr(gl_renderer, "8500"))
+        {
+            return CARD_NVIDIA_GEFORCE_8400GS;
+        }
+
         /* Geforce8 - lowend */
         if (strstr(gl_renderer, "8100")
                 || strstr(gl_renderer, "8200")
-                || strstr(gl_renderer, "8300")
-                || strstr(gl_renderer, "8400")
-                || strstr(gl_renderer, "8500"))
+                || strstr(gl_renderer, "8300"))
         {
-            *vidmem = 128; /* 128-256MB for a 8300, 256-512MB for a 8400 */
             return CARD_NVIDIA_GEFORCE_8300GS;
         }
 
         /* Geforce8-compatible fall back if the GPU is not in the list yet */
-        *vidmem = 128;
         return CARD_NVIDIA_GEFORCE_8300GS;
     }
 
@@ -1379,7 +1574,6 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
                 || strstr(gl_renderer, "Quadro FX 4")
                 || strstr(gl_renderer, "Quadro FX 5"))
         {
-            *vidmem = 256; /* A 7800GT uses 256MB while highend 7900 cards can use 512MB */
             return CARD_NVIDIA_GEFORCE_7800GT;
         }
 
@@ -1387,28 +1581,24 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
         if (strstr(gl_renderer, "7600")
                 || strstr(gl_renderer, "7700"))
         {
-            *vidmem = 256; /* The 7600 uses 256-512MB */
             return CARD_NVIDIA_GEFORCE_7600;
         }
 
         /* Geforce7 lower medium */
         if (strstr(gl_renderer, "7400"))
         {
-            *vidmem = 256; /* The 7400 uses 256-512MB */
             return CARD_NVIDIA_GEFORCE_7400;
         }
 
         /* Geforce7 lowend */
         if (strstr(gl_renderer, "7300"))
         {
-            *vidmem = 256; /* Mac Pros with this card have 256 MB */
             return CARD_NVIDIA_GEFORCE_7300;
         }
 
         /* Geforce6 highend */
         if (strstr(gl_renderer, "6800"))
         {
-            *vidmem = 128; /* The 6800 uses 128-256MB, the 7600 uses 256-512MB */
             return CARD_NVIDIA_GEFORCE_6800;
         }
 
@@ -1417,12 +1607,10 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
                 || strstr(gl_renderer, "6610")
                 || strstr(gl_renderer, "6700"))
         {
-            *vidmem = 128; /* A 6600GT has 128-256MB */
             return CARD_NVIDIA_GEFORCE_6600GT;
         }
 
         /* Geforce6/7 lowend */
-        *vidmem = 64; /* */
         return CARD_NVIDIA_GEFORCE_6200; /* Geforce 6100/6150/6200/7300/7400/7500 */
     }
 
@@ -1434,7 +1622,6 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
                 || strstr(gl_renderer, "5950")
                 || strstr(gl_renderer, "Quadro FX"))
         {
-            *vidmem = 256; /* 5800-5900 cards use 256MB */
             return CARD_NVIDIA_GEFORCEFX_5800;
         }
 
@@ -1444,12 +1631,10 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
                 || strstr(gl_renderer, "5700")
                 || strstr(gl_renderer, "5750"))
         {
-            *vidmem = 128; /* A 5600 uses 128-256MB */
             return CARD_NVIDIA_GEFORCEFX_5600;
         }
 
         /* GeforceFX - lowend */
-        *vidmem = 64; /* Normal FX5200 cards use 64-256MB; laptop (non-standard) can have less */
         return CARD_NVIDIA_GEFORCEFX_5200; /* GeforceFX 5100/5200/5250/5300/5500 */
     }
 
@@ -1457,11 +1642,9 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
     {
         if (strstr(gl_renderer, "GeForce4 Ti") || strstr(gl_renderer, "Quadro4"))
         {
-            *vidmem = 64; /* Geforce4 Ti cards have 64-128MB */
             return CARD_NVIDIA_GEFORCE4_TI4200; /* Geforce4 Ti4200/Ti4400/Ti4600/Ti4800, Quadro4 */
         }
 
-        *vidmem = 64; /* Geforce3 cards have 64-128MB */
         return CARD_NVIDIA_GEFORCE3; /* Geforce3 standard/Ti200/Ti500, Quadro DCC */
     }
 
@@ -1469,43 +1652,32 @@ static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl
     {
         if (strstr(gl_renderer, "GeForce4 MX"))
         {
-            /* Most Geforce4MX GPUs have at least 64MB of memory, some
-             * early models had 32MB but most have 64MB or even 128MB. */
-            *vidmem = 64;
             return CARD_NVIDIA_GEFORCE4_MX; /* MX420/MX440/MX460/MX4000 */
         }
 
         if (strstr(gl_renderer, "GeForce2 MX") || strstr(gl_renderer, "Quadro2 MXR"))
         {
-            *vidmem = 32; /* Geforce2MX GPUs have 32-64MB of video memory */
             return CARD_NVIDIA_GEFORCE2_MX; /* Geforce2 standard/MX100/MX200/MX400, Quadro2 MXR */
         }
 
         if (strstr(gl_renderer, "GeForce2") || strstr(gl_renderer, "Quadro2"))
         {
-            *vidmem = 32; /* Geforce2 GPUs have 32-64MB of video memory */
             return CARD_NVIDIA_GEFORCE2; /* Geforce2 GTS/Pro/Ti/Ultra, Quadro2 */
         }
 
-        /* Most Geforce1 cards have 32MB, there are also some rare 16
-         * and 64MB (Dell) models. */
-        *vidmem = 32;
         return CARD_NVIDIA_GEFORCE; /* Geforce 256/DDR, Quadro */
     }
 
     if (strstr(gl_renderer, "TNT2"))
     {
-        *vidmem = 32; /* Most TNT2 boards have 32MB, though there are 16MB boards too */
         return CARD_NVIDIA_RIVA_TNT2; /* Riva TNT2 standard/M64/Pro/Ultra */
     }
 
-    *vidmem = 16; /* Most TNT boards have 16MB, some rare models have 8MB */
     return CARD_NVIDIA_RIVA_TNT; /* Riva TNT, Vanta */
-
 }
 
 static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_info *gl_info,
-        const char *gl_renderer, unsigned int *vidmem)
+        const char *gl_renderer)
 {
     /* See http://developer.amd.com/drivers/pc_vendor_id/Pages/default.aspx
      *
@@ -1518,7 +1690,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "HD 5850")   /* Radeon EG CYPRESS XT */
                 || strstr(gl_renderer, "HD 5870"))  /* Radeon EG CYPRESS PRO */
         {
-            *vidmem = 1024; /* note: HD58xx cards use 1024MB  */
             return CARD_ATI_RADEON_HD5800;
         }
 
@@ -1527,7 +1698,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "HD 5750")   /* Radeon EG JUNIPER LE */
                 || strstr(gl_renderer, "HD 5770"))  /* Radeon EG JUNIPER XT */
         {
-            *vidmem = 512; /* note: HD5770 cards use 1024MB and HD5750 cards use 512MB or 1024MB  */
             return CARD_ATI_RADEON_HD5700;
         }
 
@@ -1538,7 +1708,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "HD 4870")   /* Radeon RV770 */
                 || strstr(gl_renderer, "HD 4890"))  /* Radeon RV790 */
         {
-            *vidmem = 512; /* note: HD4890 cards use 1024MB */
             return CARD_ATI_RADEON_HD4800;
         }
 
@@ -1546,7 +1715,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
         if (strstr(gl_renderer, "HD 4700")          /* Radeon RV770 */
                 || strstr(gl_renderer, "HD 4770"))  /* Radeon RV740 */
         {
-            *vidmem = 512;
             return CARD_ATI_RADEON_HD4700;
         }
 
@@ -1555,7 +1723,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "HD 4650")   /* Radeon RV730 */
                 || strstr(gl_renderer, "HD 4670"))  /* Radeon RV730 */
         {
-            *vidmem = 512;
             return CARD_ATI_RADEON_HD4600;
         }
 
@@ -1563,7 +1730,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
         if (strstr(gl_renderer, "HD 4350")          /* Radeon RV710 */
                 || strstr(gl_renderer, "HD 4550"))  /* Radeon RV710 */
         {
-            *vidmem = 256;
             return CARD_ATI_RADEON_HD4350;
         }
 
@@ -1572,7 +1738,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "HD 3870")
                 || strstr(gl_renderer, "HD 3850"))
         {
-            *vidmem = 512; /* HD2900/HD3800 uses 256-1024MB */
             return CARD_ATI_RADEON_HD2900;
         }
 
@@ -1582,7 +1747,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "HD 3690")
                 || strstr(gl_renderer, "HD 3650"))
         {
-            *vidmem = 256; /* HD2600/HD3600 uses 256-512MB */
             return CARD_ATI_RADEON_HD2600;
         }
 
@@ -1595,7 +1759,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "HD 3430")
                 || strstr(gl_renderer, "HD 3400"))
         {
-            *vidmem = 256; /* HD2350/2400 use 256MB, HD34xx use 256-512MB */
             return CARD_ATI_RADEON_HD2350;
         }
 
@@ -1604,12 +1767,10 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "HD 3200")
                 || strstr(gl_renderer, "HD 3300"))
         {
-            *vidmem = 128; /* 128MB */
             return CARD_ATI_RADEON_HD3200;
         }
 
         /* Default for when no GPU has been found */
-        *vidmem = 128; /* 128MB */
         return CARD_ATI_RADEON_HD3200;
     }
 
@@ -1622,7 +1783,6 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "X1900")
                 || strstr(gl_renderer, "X1950"))
         {
-            *vidmem = 128; /* X1600 uses 128-256MB, >=X1800 uses 256MB */
             return CARD_ATI_RADEON_X1600;
         }
 
@@ -1640,53 +1800,44 @@ static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_in
                 || strstr(gl_renderer, "HD 2300")
                 )
         {
-            *vidmem = 128; /* x700/x8*0 use 128-256MB, >=x1300 128-512MB */
             return CARD_ATI_RADEON_X700;
         }
 
         /* Radeon Xpress Series - onboard, DX9b, Shader 2.0, 300-400MHz */
         if (strstr(gl_renderer, "Radeon Xpress"))
         {
-            *vidmem = 64; /* Shared RAM, BIOS configurable, 64-256M */
             return CARD_ATI_RADEON_XPRESS_200M;
         }
 
         /* Radeon R3xx */
-        *vidmem = 64; /* Radeon 9500 uses 64MB, higher models use up to 256MB */
         return CARD_ATI_RADEON_9500; /* Radeon 9500/9550/9600/9700/9800/X300/X550/X600 */
     }
 
     if (WINE_D3D8_CAPABLE(gl_info))
     {
-        *vidmem = 64; /* 8500/9000 cards use mostly 64MB, though there are 32MB and 128MB models */
         return CARD_ATI_RADEON_8500; /* Radeon 8500/9000/9100/9200/9300 */
     }
 
     if (WINE_D3D7_CAPABLE(gl_info))
     {
-        *vidmem = 32; /* There are models with up to 64MB */
         return CARD_ATI_RADEON_7200; /* Radeon 7000/7100/7200/7500 */
     }
 
-    *vidmem = 16; /* There are 16-32MB models */
     return CARD_ATI_RAGE_128PRO;
-
 }
 
-static enum wined3d_pci_device select_card_intel_binary(const struct wined3d_gl_info *gl_info,
-        const char *gl_renderer, unsigned int *vidmem)
+static enum wined3d_pci_device select_card_intel(const struct wined3d_gl_info *gl_info,
+        const char *gl_renderer)
 {
-    if (strstr(gl_renderer, "X3100"))
+    if (strstr(gl_renderer, "X3100") || strstr(gl_renderer, "965GM"))
     {
-        /* MacOS calls the card GMA X3100, Google findings also suggest the name GM965 */
-        *vidmem = 128;
+        /* MacOS calls the card GMA X3100, otherwise known as GM965/GL960 */
         return CARD_INTEL_X3100;
     }
 
     if (strstr(gl_renderer, "GMA 950") || strstr(gl_renderer, "945GM"))
     {
         /* MacOS calls the card GMA 950, but everywhere else the PCI ID is named 945GM */
-        *vidmem = 64;
         return CARD_INTEL_I945GM;
     }
 
@@ -1700,7 +1851,7 @@ static enum wined3d_pci_device select_card_intel_binary(const struct wined3d_gl_
 }
 
 static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info *gl_info,
-        const char *gl_renderer, unsigned int *vidmem)
+        const char *gl_renderer)
 {
     /* See http://developer.amd.com/drivers/pc_vendor_id/Pages/default.aspx
      *
@@ -1713,28 +1864,24 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
                 || strstr(gl_renderer, "RV770")  /* Radeon RV770 */
                 || strstr(gl_renderer, "RV790"))  /* Radeon RV790 */
         {
-            *vidmem = 512; /* note: HD4890 cards use 1024MB */
             return CARD_ATI_RADEON_HD4800;
         }
 
         /* Radeon R740 HD4700 - midend */
         if (strstr(gl_renderer, "RV740"))          /* Radeon RV740 */
         {
-            *vidmem = 512;
             return CARD_ATI_RADEON_HD4700;
         }
 
         /* Radeon R730 HD4600 - midend */
         if (strstr(gl_renderer, "RV730"))        /* Radeon RV730 */
         {
-            *vidmem = 512;
             return CARD_ATI_RADEON_HD4600;
         }
 
         /* Radeon R710 HD4500/HD4350 - lowend */
         if (strstr(gl_renderer, "RV710"))          /* Radeon RV710 */
         {
-            *vidmem = 256;
             return CARD_ATI_RADEON_HD4350;
         }
 
@@ -1743,7 +1890,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
                 || strstr(gl_renderer, "RV670")
                 || strstr(gl_renderer, "R680"))
         {
-            *vidmem = 512; /* HD2900/HD3800 uses 256-1024MB */
             return CARD_ATI_RADEON_HD2900;
         }
 
@@ -1751,7 +1897,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
         if (strstr(gl_renderer, "RV630")
                 || strstr(gl_renderer, "RV635"))
         {
-            *vidmem = 256; /* HD2600/HD3600 uses 256-512MB */
             return CARD_ATI_RADEON_HD2600;
         }
 
@@ -1759,7 +1904,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
         if (strstr(gl_renderer, "RV610")
                 || strstr(gl_renderer, "RV620"))
         {
-            *vidmem = 256; /* HD2350/2400 use 256MB, HD34xx use 256-512MB */
             return CARD_ATI_RADEON_HD2350;
         }
 
@@ -1767,7 +1911,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
         if (strstr(gl_renderer, "RS780")
                 || strstr(gl_renderer, "RS880"))
         {
-            *vidmem = 128; /* 128MB */
             return CARD_ATI_RADEON_HD3200;
         }
 
@@ -1779,7 +1922,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
                 || strstr(gl_renderer, "RV570")
                 || strstr(gl_renderer, "R580"))
         {
-            *vidmem = 128; /* X1600 uses 128-256MB, >=X1800 uses 256MB */
             return CARD_ATI_RADEON_X1600;
         }
 
@@ -1794,7 +1936,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
                 || strstr(gl_renderer, "RV515")
                 || strstr(gl_renderer, "RV516"))
         {
-            *vidmem = 128; /* x700/x8*0 use 128-256MB, >=x1300 128-512MB */
             return CARD_ATI_RADEON_X700;
         }
 
@@ -1807,7 +1948,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
                 || strstr(gl_renderer, "RS690")
                 || strstr(gl_renderer, "RS740"))
         {
-            *vidmem = 64; /* Shared RAM, BIOS configurable, 64-256M */
             return CARD_ATI_RADEON_XPRESS_200M;
         }
 
@@ -1820,7 +1960,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
                 || strstr(gl_renderer, "R350")
                 || strstr(gl_renderer, "R360"))
         {
-            *vidmem = 64; /* Radeon 9500 uses 64MB, higher models use up to 256MB */
             return CARD_ATI_RADEON_9500; /* Radeon 9500/9550/9600/9700/9800/X300/X550/X600 */
         }
     }
@@ -1832,28 +1971,24 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
                 || strstr(gl_renderer, "(RV770")  /* Radeon RV770 */
                 || strstr(gl_renderer, "(RV790"))  /* Radeon RV790 */
         {
-            *vidmem = 512; /* note: HD4890 cards use 1024MB */
             return CARD_ATI_RADEON_HD4800;
         }
 
         /* Radeon R740 HD4700 - midend */
         if (strstr(gl_renderer, "(RV740"))          /* Radeon RV740 */
         {
-            *vidmem = 512;
             return CARD_ATI_RADEON_HD4700;
         }
 
         /* Radeon R730 HD4600 - midend */
         if (strstr(gl_renderer, "(RV730"))        /* Radeon RV730 */
         {
-            *vidmem = 512;
             return CARD_ATI_RADEON_HD4600;
         }
 
         /* Radeon R710 HD4500/HD4350 - lowend */
         if (strstr(gl_renderer, "(RV710"))          /* Radeon RV710 */
         {
-            *vidmem = 256;
             return CARD_ATI_RADEON_HD4350;
         }
 
@@ -1862,7 +1997,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
                 || strstr(gl_renderer, "(RV670")
                 || strstr(gl_renderer, "(R680"))
         {
-            *vidmem = 512; /* HD2900/HD3800 uses 256-1024MB */
             return CARD_ATI_RADEON_HD2900;
         }
 
@@ -1870,7 +2004,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
         if (strstr(gl_renderer, "(RV630")
                 || strstr(gl_renderer, "(RV635"))
         {
-            *vidmem = 256; /* HD2600/HD3600 uses 256-512MB */
             return CARD_ATI_RADEON_HD2600;
         }
 
@@ -1878,7 +2011,6 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
         if (strstr(gl_renderer, "(RV610")
                 || strstr(gl_renderer, "(RV620"))
         {
-            *vidmem = 256; /* HD2350/2400 use 256MB, HD34xx use 256-512MB */
             return CARD_ATI_RADEON_HD2350;
         }
 
@@ -1886,30 +2018,25 @@ static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info
         if (strstr(gl_renderer, "(RS780")
                 || strstr(gl_renderer, "(RS880"))
         {
-            *vidmem = 128; /* 128MB */
             return CARD_ATI_RADEON_HD3200;
         }
     }
 
     if (WINE_D3D8_CAPABLE(gl_info))
     {
-        *vidmem = 64; /* 8500/9000 cards use mostly 64MB, though there are 32MB and 128MB models */
         return CARD_ATI_RADEON_8500; /* Radeon 8500/9000/9100/9200/9300 */
     }
 
     if (WINE_D3D7_CAPABLE(gl_info))
     {
-        *vidmem = 32; /* There are models with up to 64MB */
         return CARD_ATI_RADEON_7200; /* Radeon 7000/7100/7200/7500 */
     }
 
-    *vidmem = 16; /* There are 16-32MB models */
     return CARD_ATI_RAGE_128PRO;
-
 }
 
 static enum wined3d_pci_device select_card_nvidia_mesa(const struct wined3d_gl_info *gl_info,
-        const char *gl_renderer, unsigned int *vidmem)
+        const char *gl_renderer)
 {
     FIXME_(d3d_caps)("Card selection not handled for Mesa Nouveau driver\n");
     if (WINE_D3D9_CAPABLE(gl_info)) return CARD_NVIDIA_GEFORCEFX_5600;
@@ -1919,21 +2046,13 @@ static enum wined3d_pci_device select_card_nvidia_mesa(const struct wined3d_gl_i
     return CARD_NVIDIA_RIVA_128;
 }
 
-static enum wined3d_pci_device select_card_intel_mesa(const struct wined3d_gl_info *gl_info,
-        const char *gl_renderer, unsigned int *vidmem)
-{
-    FIXME_(d3d_caps)("Card selection not handled for Mesa Intel driver\n");
-    return CARD_INTEL_I915G;
-}
-
 
 struct vendor_card_selection
 {
     enum wined3d_gl_vendor gl_vendor;
     enum wined3d_pci_vendor card_vendor;
     const char *description;        /* Description of the card selector i.e. Apple OS/X Intel */
-    enum wined3d_pci_device (*select_card)(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
-            unsigned int *vidmem );
+    enum wined3d_pci_device (*select_card)(const struct wined3d_gl_info *gl_info, const char *gl_renderer);
 };
 
 static const struct vendor_card_selection vendor_card_select_table[] =
@@ -1941,17 +2060,17 @@ static const struct vendor_card_selection vendor_card_select_table[] =
     {GL_VENDOR_NVIDIA, HW_VENDOR_NVIDIA,  "Nvidia binary driver",     select_card_nvidia_binary},
     {GL_VENDOR_APPLE,  HW_VENDOR_NVIDIA,  "Apple OSX NVidia binary driver",   select_card_nvidia_binary},
     {GL_VENDOR_APPLE,  HW_VENDOR_ATI,     "Apple OSX AMD/ATI binary driver",  select_card_ati_binary},
-    {GL_VENDOR_APPLE,  HW_VENDOR_INTEL,   "Apple OSX Intel binary driver",    select_card_intel_binary},
+    {GL_VENDOR_APPLE,  HW_VENDOR_INTEL,   "Apple OSX Intel binary driver",    select_card_intel},
     {GL_VENDOR_FGLRX,  HW_VENDOR_ATI,     "AMD/ATI binary driver",    select_card_ati_binary},
     {GL_VENDOR_MESA,   HW_VENDOR_ATI,     "Mesa AMD/ATI driver",      select_card_ati_mesa},
     {GL_VENDOR_MESA,   HW_VENDOR_NVIDIA,  "Mesa Nouveau driver",      select_card_nvidia_mesa},
-    {GL_VENDOR_MESA,   HW_VENDOR_INTEL,   "Mesa Intel driver",        select_card_intel_mesa},
-    {GL_VENDOR_INTEL,  HW_VENDOR_INTEL,   "Mesa Intel driver",        select_card_intel_mesa}
+    {GL_VENDOR_MESA,   HW_VENDOR_INTEL,   "Mesa Intel driver",        select_card_intel},
+    {GL_VENDOR_INTEL,  HW_VENDOR_INTEL,   "Mesa Intel driver",        select_card_intel}
 };
 
 
 static enum wined3d_pci_device wined3d_guess_card(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
-        enum wined3d_gl_vendor *gl_vendor, enum wined3d_pci_vendor *card_vendor, unsigned int *vidmem)
+        enum wined3d_gl_vendor *gl_vendor, enum wined3d_pci_vendor *card_vendor)
 {
     /* Above is a list of Nvidia and ATI GPUs. Both vendors have dozens of
      * different GPUs with roughly the same features. In most cases GPUs from a
@@ -2016,7 +2135,7 @@ static enum wined3d_pci_device wined3d_guess_card(const struct wined3d_gl_info *
             || (vendor_card_select_table[i].card_vendor != *card_vendor))
                 continue;
         TRACE_(d3d_caps)("Applying card_selector \"%s\".\n", vendor_card_select_table[i].description);
-        return vendor_card_select_table[i].select_card(gl_info, gl_renderer, vidmem);
+        return vendor_card_select_table[i].select_card(gl_info, gl_renderer);
     }
 
     FIXME_(d3d_caps)("No card selector available for GL vendor %d and card vendor %04x.\n",
@@ -2069,6 +2188,23 @@ static const struct blit_shader *select_blit_implementation(struct wined3d_adapt
     else return &ffp_blit;
 }
 
+static void load_gl_funcs(struct wined3d_gl_info *gl_info, DWORD gl_version)
+{
+    DWORD ver;
+
+#define USE_GL_FUNC(type, pfn, ext, replace) \
+    if (gl_info->supported[ext]) gl_info->pfn = (type)pwglGetProcAddress(#pfn); \
+    else if ((ver = ver_for_ext(ext)) && ver <= gl_version) gl_info->pfn = (type)pwglGetProcAddress(#replace); \
+    else gl_info->pfn = NULL;
+
+    GL_EXT_FUNCS_GEN;
+#undef USE_GL_FUNC
+
+#define USE_GL_FUNC(type, pfn, ext, replace) gl_info->pfn = (type)pwglGetProcAddress(#pfn);
+    WGL_EXT_FUNCS_GEN;
+#undef USE_GL_FUNC
+}
+
 /* Context activation is done by the caller. */
 static BOOL IWineD3DImpl_FillGLCaps(struct wined3d_adapter *adapter)
 {
@@ -2085,7 +2221,6 @@ static BOOL IWineD3DImpl_FillGLCaps(struct wined3d_adapter *adapter)
     GLfloat     gl_floatv[2];
     unsigned    i;
     HDC         hdc;
-    unsigned int vidmem=0;
     DWORD gl_version;
     size_t len;
 
@@ -2181,22 +2316,20 @@ static BOOL IWineD3DImpl_FillGLCaps(struct wined3d_adapter *adapter)
     while (*GL_Extensions)
     {
         const char *start;
-        char current_ext[256];
 
         while (isspace(*GL_Extensions)) ++GL_Extensions;
         start = GL_Extensions;
         while (!isspace(*GL_Extensions) && *GL_Extensions) ++GL_Extensions;
 
         len = GL_Extensions - start;
-        if (!len || len >= sizeof(current_ext)) continue;
+        if (!len) continue;
 
-        memcpy(current_ext, start, len);
-        current_ext[len] = '\0';
-        TRACE_(d3d_caps)("- %s\n", debugstr_a(current_ext));
+        TRACE_(d3d_caps)("- %s\n", debugstr_an(start, len));
 
         for (i = 0; i < (sizeof(EXTENSION_MAP) / sizeof(*EXTENSION_MAP)); ++i)
         {
-            if (!strcmp(current_ext, EXTENSION_MAP[i].extension_string))
+            if (len == strlen(EXTENSION_MAP[i].extension_string)
+                    && !memcmp(start, EXTENSION_MAP[i].extension_string, len))
             {
                 TRACE_(d3d_caps)(" FOUND: %s support.\n", EXTENSION_MAP[i].extension_string);
                 gl_info->supported[EXTENSION_MAP[i].extension] = TRUE;
@@ -2206,19 +2339,7 @@ static BOOL IWineD3DImpl_FillGLCaps(struct wined3d_adapter *adapter)
     }
 
     /* Now work out what GL support this card really has */
-#define USE_GL_FUNC(type, pfn, ext, replace) \
-{ \
-    DWORD ver = ver_for_ext(ext); \
-    if (gl_info->supported[ext]) gl_info->pfn = (type)pwglGetProcAddress(#pfn); \
-    else if (ver && ver <= gl_version) gl_info->pfn = (type)pwglGetProcAddress(#replace); \
-    else gl_info->pfn = NULL; \
-}
-    GL_EXT_FUNCS_GEN;
-#undef USE_GL_FUNC
-
-#define USE_GL_FUNC(type, pfn, ext, replace) gl_info->pfn = (type)pwglGetProcAddress(#pfn);
-    WGL_EXT_FUNCS_GEN;
-#undef USE_GL_FUNC
+    load_gl_funcs( gl_info, gl_version );
 
     ENTER_GL();
 
@@ -2235,6 +2356,8 @@ static BOOL IWineD3DImpl_FillGLCaps(struct wined3d_adapter *adapter)
         }
     }
 
+    if (gl_version >= MAKEDWORD_VERSION(2, 0)) gl_info->supported[WINED3D_GL_VERSION_2_0] = TRUE;
+
     if (gl_info->supported[APPLE_FENCE])
     {
         /* GL_NV_fence and GL_APPLE_fence provide the same functionality basically.
@@ -2286,6 +2409,11 @@ static BOOL IWineD3DImpl_FillGLCaps(struct wined3d_adapter *adapter)
         TRACE_(d3d_caps)(" IMPLIED: ARB_vertex_array_bgra support (by EXT_vertex_array_bgra).\n");
         gl_info->supported[ARB_VERTEX_ARRAY_BGRA] = TRUE;
     }
+    if (!gl_info->supported[ARB_TEXTURE_COMPRESSION_RGTC] && gl_info->supported[EXT_TEXTURE_COMPRESSION_RGTC])
+    {
+        TRACE_(d3d_caps)(" IMPLIED: ARB_texture_compression_rgtc support (by EXT_texture_compression_rgtc).\n");
+        gl_info->supported[ARB_TEXTURE_COMPRESSION_RGTC] = TRUE;
+    }
     if (gl_info->supported[NV_TEXTURE_SHADER2])
     {
         if (gl_info->supported[NV_REGISTER_COMBINERS])
@@ -2575,15 +2703,9 @@ static BOOL IWineD3DImpl_FillGLCaps(struct wined3d_adapter *adapter)
     card_vendor = wined3d_guess_card_vendor(gl_vendor_str, gl_renderer_str);
     TRACE_(d3d_caps)("found GL_VENDOR (%s)->(0x%04x/0x%04x)\n", debugstr_a(gl_vendor_str), gl_vendor, card_vendor);
 
-    device = wined3d_guess_card(gl_info, gl_renderer_str, &gl_vendor, &card_vendor, &vidmem);
+    device = wined3d_guess_card(gl_info, gl_renderer_str, &gl_vendor, &card_vendor);
     TRACE_(d3d_caps)("FOUND (fake) card: 0x%x (vendor id), 0x%x (device id)\n", card_vendor, device);
 
-    /* If we have an estimate use it, else default to 64MB;  */
-    if(vidmem)
-        gl_info->vidmem = vidmem*1024*1024; /* convert from MBs to bytes */
-    else
-        gl_info->vidmem = WINE_DEFAULT_VIDMEM;
-
     gl_info->wrap_lookup[WINED3DTADDRESS_WRAP - WINED3DTADDRESS_WRAP] = GL_REPEAT;
     gl_info->wrap_lookup[WINED3DTADDRESS_MIRROR - WINED3DTADDRESS_WRAP] =
             gl_info->supported[ARB_TEXTURE_MIRRORED_REPEAT] ? GL_MIRRORED_REPEAT_ARB : GL_REPEAT;
@@ -2600,22 +2722,24 @@ static BOOL IWineD3DImpl_FillGLCaps(struct wined3d_adapter *adapter)
         if(GL_EXTCALL(wglGetExtensionsStringARB))
             WGL_Extensions = GL_EXTCALL(wglGetExtensionsStringARB(hdc));
 
-        if (NULL == WGL_Extensions) {
+        if (!WGL_Extensions)
+        {
             ERR("   WGL_Extensions returns NULL\n");
-        } else {
+        }
+        else
+        {
             TRACE_(d3d_caps)("WGL_Extensions reported:\n");
-            while (*WGL_Extensions != 0x00) {
+            while (*WGL_Extensions)
+            {
                 const char *Start;
                 char ThisExtn[256];
 
                 while (isspace(*WGL_Extensions)) WGL_Extensions++;
                 Start = WGL_Extensions;
-                while (!isspace(*WGL_Extensions) && *WGL_Extensions != 0x00) {
-                    WGL_Extensions++;
-                }
+                while (!isspace(*WGL_Extensions) && *WGL_Extensions) ++WGL_Extensions;
 
                 len = WGL_Extensions - Start;
-                if (len == 0 || len >= sizeof(ThisExtn))
+                if (!len || len >= sizeof(ThisExtn))
                     continue;
 
                 memcpy(ThisExtn, Start, len);
@@ -2676,18 +2800,21 @@ static HMONITOR WINAPI IWineD3DImpl_GetAdapterMonitor(IWineD3D *iface, UINT Adap
      of the same bpp but different resolutions                                  */
 
 /* Note: dx9 supplies a format. Calls from d3d8 supply WINED3DFMT_UNKNOWN */
-static UINT     WINAPI IWineD3DImpl_GetAdapterModeCount(IWineD3D *iface, UINT Adapter, WINED3DFORMAT Format) {
+static UINT WINAPI IWineD3DImpl_GetAdapterModeCount(IWineD3D *iface, UINT Adapter, enum wined3d_format_id format_id)
+{
     IWineD3DImpl *This = (IWineD3DImpl *)iface;
-    TRACE_(d3d_caps)("(%p}->(Adapter: %d, Format: %s)\n", This, Adapter, debug_d3dformat(Format));
+
+    TRACE_(d3d_caps)("iface %p, adapter %u, format_id: %s.\n", iface, Adapter, debug_d3dformat(format_id));
 
     if (Adapter >= IWineD3D_GetAdapterCount(iface)) {
         return 0;
     }
 
     /* TODO: Store modes per adapter and read it from the adapter structure */
-    if (Adapter == 0) { /* Display */
-        const struct wined3d_format_desc *format_desc = getFormatDescEntry(Format, &This->adapters[Adapter].gl_info);
-        UINT format_bits = format_desc->byte_count * CHAR_BIT;
+    if (Adapter == 0)
+    {
+        const struct wined3d_format *format = wined3d_get_format(&This->adapters[Adapter].gl_info, format_id);
+        UINT format_bits = format->byte_count * CHAR_BIT;
         unsigned int i = 0;
         unsigned int j = 0;
         DEVMODEW mode;
@@ -2699,7 +2826,7 @@ static UINT     WINAPI IWineD3DImpl_GetAdapterModeCount(IWineD3D *iface, UINT Ad
         {
             ++j;
 
-            if (Format == WINED3DFMT_UNKNOWN)
+            if (format_id == WINED3DFMT_UNKNOWN)
             {
                 /* This is for D3D8, do not enumerate P8 here */
                 if (mode.dmBitsPerPel == 32 || mode.dmBitsPerPel == 16) ++i;
@@ -2719,22 +2846,26 @@ static UINT     WINAPI IWineD3DImpl_GetAdapterModeCount(IWineD3D *iface, UINT Ad
 }
 
 /* Note: dx9 supplies a format. Calls from d3d8 supply WINED3DFMT_UNKNOWN */
-static HRESULT WINAPI IWineD3DImpl_EnumAdapterModes(IWineD3D *iface, UINT Adapter, WINED3DFORMAT Format, UINT Mode, WINED3DDISPLAYMODE* pMode) {
+static HRESULT WINAPI IWineD3DImpl_EnumAdapterModes(IWineD3D *iface, UINT Adapter,
+        enum wined3d_format_id format_id, UINT Mode, WINED3DDISPLAYMODE *pMode)
+{
     IWineD3DImpl *This = (IWineD3DImpl *)iface;
-    TRACE_(d3d_caps)("(%p}->(Adapter:%d, mode:%d, pMode:%p, format:%s)\n", This, Adapter, Mode, pMode, debug_d3dformat(Format));
+
+    TRACE_(d3d_caps)("iface %p, adapter_idx %u, format %s, mode_idx %u, mode %p.\n",
+            iface, Adapter, debug_d3dformat(format_id), Mode, pMode);
 
     /* Validate the parameters as much as possible */
-    if (NULL == pMode ||
-        Adapter >= IWineD3DImpl_GetAdapterCount(iface) ||
-        Mode    >= IWineD3DImpl_GetAdapterModeCount(iface, Adapter, Format)) {
+    if (!pMode || Adapter >= IWineD3DImpl_GetAdapterCount(iface)
+            || Mode >= IWineD3DImpl_GetAdapterModeCount(iface, Adapter, format_id))
+    {
         return WINED3DERR_INVALIDCALL;
     }
 
     /* TODO: Store modes per adapter and read it from the adapter structure */
     if (Adapter == 0)
     {
-        const struct wined3d_format_desc *format_desc = getFormatDescEntry(Format, &This->adapters[Adapter].gl_info);
-        UINT format_bits = format_desc->byte_count * CHAR_BIT;
+        const struct wined3d_format *format = wined3d_get_format(&This->adapters[Adapter].gl_info, format_id);
+        UINT format_bits = format->byte_count * CHAR_BIT;
         DEVMODEW DevModeW;
         int ModeIdx = 0;
         UINT i = 0;
@@ -2748,7 +2879,7 @@ static HRESULT WINAPI IWineD3DImpl_EnumAdapterModes(IWineD3D *iface, UINT Adapte
            just count through the ones with valid bit depths */
         while ((i<=Mode) && EnumDisplaySettingsExW(NULL, j++, &DevModeW, 0))
         {
-            if (Format == WINED3DFMT_UNKNOWN)
+            if (format_id == WINED3DFMT_UNKNOWN)
             {
                 /* This is for D3D8, do not enumerate P8 here */
                 if (DevModeW.dmBitsPerPel == 32 || DevModeW.dmBitsPerPel == 16) ++i;
@@ -2759,8 +2890,9 @@ static HRESULT WINAPI IWineD3DImpl_EnumAdapterModes(IWineD3D *iface, UINT Adapte
             }
         }
 
-        if (i == 0) {
-            TRACE_(d3d_caps)("No modes found for format (%x - %s)\n", Format, debug_d3dformat(Format));
+        if (!i)
+        {
+            TRACE_(d3d_caps)("No modes found for format (%x - %s)\n", format_id, debug_d3dformat(format_id));
             return WINED3DERR_INVALIDCALL;
         }
         ModeIdx = j - 1;
@@ -2773,12 +2905,13 @@ static HRESULT WINAPI IWineD3DImpl_EnumAdapterModes(IWineD3D *iface, UINT Adapte
             if (DevModeW.dmFields & DM_DISPLAYFREQUENCY)
                 pMode->RefreshRate = DevModeW.dmDisplayFrequency;
 
-            if (Format == WINED3DFMT_UNKNOWN) {
+            if (format_id == WINED3DFMT_UNKNOWN)
                 pMode->Format = pixelformat_for_depth(DevModeW.dmBitsPerPel);
-            } else {
-                pMode->Format = Format;
-            }
-        } else {
+            else
+                pMode->Format = format_id;
+        }
+        else
+        {
             TRACE_(d3d_caps)("Requested mode out of range %d\n", Mode);
             return WINED3DERR_INVALIDCALL;
         }
@@ -2800,10 +2933,8 @@ static HRESULT WINAPI IWineD3DImpl_GetAdapterDisplayMode(IWineD3D *iface, UINT A
 {
     TRACE("iface %p, adapter_idx %u, display_mode %p.\n", iface, Adapter, pMode);
 
-    if (NULL == pMode ||
-        Adapter >= IWineD3D_GetAdapterCount(iface)) {
+    if (!pMode || Adapter >= IWineD3D_GetAdapterCount(iface))
         return WINED3DERR_INVALIDCALL;
-    }
 
     if (Adapter == 0) { /* Display */
         int bpp = 0;
@@ -2898,7 +3029,7 @@ static HRESULT WINAPI IWineD3DImpl_GetAdapterIdentifier(IWineD3D *iface, UINT Ad
 }
 
 static BOOL IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(const struct wined3d_gl_info *gl_info,
-        const WineD3D_PixelFormat *cfg, const struct wined3d_format_desc *format_desc)
+        const WineD3D_PixelFormat *cfg, const struct wined3d_format *format)
 {
     short redSize, greenSize, blueSize, alphaSize, colorBits;
 
@@ -2906,12 +3037,12 @@ static BOOL IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(const struct wined
         return FALSE;
 
     /* Float formats need FBOs. If FBOs are used this function isn't called */
-    if (format_desc->Flags & WINED3DFMT_FLAG_FLOAT) return FALSE;
+    if (format->Flags & WINED3DFMT_FLAG_FLOAT) return FALSE;
 
     if(cfg->iPixelType == WGL_TYPE_RGBA_ARB) { /* Integer RGBA formats */
-        if (!getColorBits(format_desc, &redSize, &greenSize, &blueSize, &alphaSize, &colorBits))
+        if (!getColorBits(format, &redSize, &greenSize, &blueSize, &alphaSize, &colorBits))
         {
-            ERR("Unable to check compatibility for Format=%s\n", debug_d3dformat(format_desc->format));
+            ERR("Unable to check compatibility for format %s.\n", debug_d3dformat(format->id));
             return FALSE;
         }
 
@@ -2935,7 +3066,7 @@ static BOOL IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(const struct wined
 }
 
 static BOOL IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(const struct wined3d_gl_info *gl_info,
-        const WineD3D_PixelFormat *cfg, const struct wined3d_format_desc *format_desc)
+        const WineD3D_PixelFormat *cfg, const struct wined3d_format *format)
 {
     short depthSize, stencilSize;
     BOOL lockable = FALSE;
@@ -2943,16 +3074,16 @@ static BOOL IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(const struct wined3
     if(!cfg)
         return FALSE;
 
-    if (!getDepthStencilBits(format_desc, &depthSize, &stencilSize))
+    if (!getDepthStencilBits(format, &depthSize, &stencilSize))
     {
-        ERR("Unable to check compatibility for Format=%s\n", debug_d3dformat(format_desc->format));
+        ERR("Unable to check compatibility for format %s.\n", debug_d3dformat(format->id));
         return FALSE;
     }
 
     /* Float formats need FBOs. If FBOs are used this function isn't called */
-    if (format_desc->Flags & WINED3DFMT_FLAG_FLOAT) return FALSE;
+    if (format->Flags & WINED3DFMT_FLAG_FLOAT) return FALSE;
 
-    if ((format_desc->format == WINED3DFMT_D16_LOCKABLE) || (format_desc->format == WINED3DFMT_D32_FLOAT))
+    if ((format->id == WINED3DFMT_D16_LOCKABLE) || (format->id == WINED3DFMT_D32_FLOAT))
         lockable = TRUE;
 
     /* On some modern cards like the Geforce8/9 GLX doesn't offer some dephthstencil formats which D3D9 reports.
@@ -2969,16 +3100,16 @@ static BOOL IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(const struct wined3
     return TRUE;
 }
 
-static HRESULT WINAPI IWineD3DImpl_CheckDepthStencilMatch(IWineD3D *iface, UINT Adapter, WINED3DDEVTYPE DeviceType,
-                                                   WINED3DFORMAT AdapterFormat,
-                                                   WINED3DFORMAT RenderTargetFormat,
-                                                   WINED3DFORMAT DepthStencilFormat) {
+static HRESULT WINAPI IWineD3DImpl_CheckDepthStencilMatch(IWineD3D *iface,
+        UINT Adapter, WINED3DDEVTYPE DeviceType, enum wined3d_format_id AdapterFormat,
+        enum wined3d_format_id RenderTargetFormat, enum wined3d_format_id DepthStencilFormat)
+{
     IWineD3DImpl *This = (IWineD3DImpl *)iface;
     int nCfgs;
     const WineD3D_PixelFormat *cfgs;
     const struct wined3d_adapter *adapter;
-    const struct wined3d_format_desc *rt_format_desc;
-    const struct wined3d_format_desc *ds_format_desc;
+    const struct wined3d_format *rt_format;
+    const struct wined3d_format *ds_format;
     int it;
 
     WARN_(d3d_caps)("(%p)-> (STUB) (Adptr:%d, DevType:(%x,%s), AdptFmt:(%x,%s), RendrTgtFmt:(%x,%s), DepthStencilFmt:(%x,%s))\n",
@@ -2994,12 +3125,13 @@ static HRESULT WINAPI IWineD3DImpl_CheckDepthStencilMatch(IWineD3D *iface, UINT
     }
 
     adapter = &This->adapters[Adapter];
-    rt_format_desc = getFormatDescEntry(RenderTargetFormat, &adapter->gl_info);
-    ds_format_desc = getFormatDescEntry(DepthStencilFormat, &adapter->gl_info);
+    rt_format = wined3d_get_format(&adapter->gl_info, RenderTargetFormat);
+    ds_format = wined3d_get_format(&adapter->gl_info, DepthStencilFormat);
     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
     {
-        if ((rt_format_desc->Flags & WINED3DFMT_FLAG_RENDERTARGET) &&
-            (ds_format_desc->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL))) {
+        if ((rt_format->Flags & WINED3DFMT_FLAG_RENDERTARGET)
+                && (ds_format->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL)))
+        {
             TRACE_(d3d_caps)("(%p) : Formats matched\n", This);
             return WINED3D_OK;
         }
@@ -3008,10 +3140,11 @@ static HRESULT WINAPI IWineD3DImpl_CheckDepthStencilMatch(IWineD3D *iface, UINT
     {
         cfgs = adapter->cfgs;
         nCfgs = adapter->nCfgs;
-        for (it = 0; it < nCfgs; ++it) {
-            if (IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(&adapter->gl_info, &cfgs[it], rt_format_desc))
+        for (it = 0; it < nCfgs; ++it)
+        {
+            if (IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(&adapter->gl_info, &cfgs[it], rt_format))
             {
-                if (IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(&adapter->gl_info, &cfgs[it], ds_format_desc))
+                if (IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(&adapter->gl_info, &cfgs[it], ds_format))
                 {
                     TRACE_(d3d_caps)("(%p) : Formats matched\n", This);
                     return WINED3D_OK;
@@ -3024,12 +3157,13 @@ static HRESULT WINAPI IWineD3DImpl_CheckDepthStencilMatch(IWineD3D *iface, UINT
     return WINED3DERR_NOTAVAILABLE;
 }
 
-static HRESULT WINAPI IWineD3DImpl_CheckDeviceMultiSampleType(IWineD3D *iface, UINT Adapter, WINED3DDEVTYPE DeviceType,
-        WINED3DFORMAT SurfaceFormat, BOOL Windowed, WINED3DMULTISAMPLE_TYPE MultiSampleType, DWORD *pQualityLevels)
+static HRESULT WINAPI IWineD3DImpl_CheckDeviceMultiSampleType(IWineD3D *iface, UINT Adapter,
+        WINED3DDEVTYPE DeviceType, enum wined3d_format_id SurfaceFormat, BOOL Windowed,
+        WINED3DMULTISAMPLE_TYPE MultiSampleType, DWORD *pQualityLevels)
 {
     IWineD3DImpl *This = (IWineD3DImpl *)iface;
-    const struct wined3d_format_desc *glDesc;
     const struct wined3d_adapter *adapter;
+    const struct wined3d_format *format;
 
     TRACE_(d3d_caps)("(%p)-> (Adptr:%d, DevType:(%x,%s), SurfFmt:(%x,%s), Win?%d, MultiSamp:%x, pQual:%p)\n",
           This,
@@ -3058,10 +3192,11 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceMultiSampleType(IWineD3D *iface, U
         return WINED3DERR_NOTAVAILABLE;
 
     adapter = &This->adapters[Adapter];
-    glDesc = getFormatDescEntry(SurfaceFormat, &adapter->gl_info);
-    if (!glDesc) return WINED3DERR_INVALIDCALL;
+    format = wined3d_get_format(&adapter->gl_info, SurfaceFormat);
+    if (!format) return WINED3DERR_INVALIDCALL;
 
-    if(glDesc->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL)) {
+    if (format->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL))
+    {
         int i, nCfgs;
         const WineD3D_PixelFormat *cfgs;
 
@@ -3071,7 +3206,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceMultiSampleType(IWineD3D *iface, U
             if(cfgs[i].numSamples != MultiSampleType)
                 continue;
 
-            if (!IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(&adapter->gl_info, &cfgs[i], glDesc))
+            if (!IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(&adapter->gl_info, &cfgs[i], format))
                 continue;
 
             TRACE("Found iPixelFormat=%d to support MultiSampleType=%d for format %s\n", cfgs[i].iPixelFormat, MultiSampleType, debug_d3dformat(SurfaceFormat));
@@ -3081,12 +3216,13 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceMultiSampleType(IWineD3D *iface, U
             return WINED3D_OK;
         }
     }
-    else if(glDesc->Flags & WINED3DFMT_FLAG_RENDERTARGET) {
+    else if (format->Flags & WINED3DFMT_FLAG_RENDERTARGET)
+    {
         short redSize, greenSize, blueSize, alphaSize, colorBits;
         int i, nCfgs;
         const WineD3D_PixelFormat *cfgs;
 
-        if (!getColorBits(glDesc, &redSize, &greenSize, &blueSize, &alphaSize, &colorBits))
+        if (!getColorBits(format, &redSize, &greenSize, &blueSize, &alphaSize, &colorBits))
         {
             ERR("Unable to color bits for format %#x, can't check multisampling capability!\n", SurfaceFormat);
             return WINED3DERR_NOTAVAILABLE;
@@ -3106,7 +3242,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceMultiSampleType(IWineD3D *iface, U
             /* Not all drivers report alpha-less formats since they use 32-bit anyway, so accept alpha even if we didn't ask for it. */
             if(alphaSize && cfgs[i].alphaSize != alphaSize)
                 continue;
-            if(cfgs[i].colorSize != (glDesc->byte_count << 3))
+            if (cfgs[i].colorSize != (format->byte_count << 3))
                 continue;
 
             TRACE("Found iPixelFormat=%d to support MultiSampleType=%d for format %s\n", cfgs[i].iPixelFormat, MultiSampleType, debug_d3dformat(SurfaceFormat));
@@ -3119,116 +3255,29 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceMultiSampleType(IWineD3D *iface, U
     return WINED3DERR_NOTAVAILABLE;
 }
 
-static HRESULT WINAPI IWineD3DImpl_CheckDeviceType(IWineD3D *iface, UINT Adapter, WINED3DDEVTYPE DeviceType,
-        WINED3DFORMAT DisplayFormat, WINED3DFORMAT BackBufferFormat, BOOL Windowed)
-{
-    HRESULT hr = WINED3DERR_NOTAVAILABLE;
-    UINT nmodes;
-
-    TRACE("iface %p, adapter_idx %u, device_type %s, display_format %s, backbuffer_format %s, windowed %#x.\n",
-            iface, Adapter, debug_d3ddevicetype(DeviceType), debug_d3dformat(DisplayFormat),
-            debug_d3dformat(BackBufferFormat), Windowed);
-
-    if (Adapter >= IWineD3D_GetAdapterCount(iface)) {
-        WARN_(d3d_caps)("Adapter >= IWineD3D_GetAdapterCount(iface), returning WINED3DERR_INVALIDCALL\n");
-        return WINED3DERR_INVALIDCALL;
-    }
-
-    /* The task of this function is to check whether a certain display / backbuffer format
-     * combination is available on the given adapter. In fullscreen mode microsoft specified
-     * that the display format shouldn't provide alpha and that ignoring alpha the backbuffer
-     * and display format should match exactly.
-     * In windowed mode format conversion can occur and this depends on the driver. When format
-     * conversion is done, this function should nevertheless fail and applications need to use
-     * CheckDeviceFormatConversion.
-     * At the moment we assume that fullscreen and windowed have the same capabilities */
-
-    /* There are only 4 display formats */
-    if (!(DisplayFormat == WINED3DFMT_B5G6R5_UNORM
-            || DisplayFormat == WINED3DFMT_B5G5R5X1_UNORM
-            || DisplayFormat == WINED3DFMT_B8G8R8X8_UNORM
-            || DisplayFormat == WINED3DFMT_B10G10R10A2_UNORM))
-    {
-        TRACE_(d3d_caps)("Format %s unsupported as display format\n", debug_d3dformat(DisplayFormat));
-        return WINED3DERR_NOTAVAILABLE;
-    }
-
-    /* If the requested DisplayFormat is not available, don't continue */
-    nmodes = IWineD3DImpl_GetAdapterModeCount(iface, Adapter, DisplayFormat);
-    if(!nmodes) {
-        TRACE_(d3d_caps)("No available modes for display format %s\n", debug_d3dformat(DisplayFormat));
-        return WINED3DERR_NOTAVAILABLE;
-    }
-
-    /* Windowed mode allows you to specify WINED3DFMT_UNKNOWN for the backbufferformat, it means 'reuse' the display format for the backbuffer */
-    if(!Windowed && BackBufferFormat == WINED3DFMT_UNKNOWN) {
-        TRACE_(d3d_caps)("BackBufferFormat WINED3FMT_UNKNOWN not available in Windowed mode\n");
-        return WINED3DERR_NOTAVAILABLE;
-    }
-
-    /* In FULLSCREEN mode R5G6B5 can only be mixed with backbuffer format R5G6B5 */
-    if (DisplayFormat == WINED3DFMT_B5G6R5_UNORM && BackBufferFormat != WINED3DFMT_B5G6R5_UNORM)
-    {
-        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s/%s\n", debug_d3dformat(DisplayFormat), debug_d3dformat(BackBufferFormat));
-        return WINED3DERR_NOTAVAILABLE;
-    }
-
-    /* In FULLSCREEN mode X1R5G5B5 can only be mixed with backbuffer format *1R5G5B5 */
-    if (DisplayFormat == WINED3DFMT_B5G5R5X1_UNORM
-            && !(BackBufferFormat == WINED3DFMT_B5G5R5X1_UNORM || BackBufferFormat == WINED3DFMT_B5G5R5A1_UNORM))
-    {
-        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s/%s\n", debug_d3dformat(DisplayFormat), debug_d3dformat(BackBufferFormat));
-        return WINED3DERR_NOTAVAILABLE;
-    }
-
-    /* In FULLSCREEN mode X8R8G8B8 can only be mixed with backbuffer format *8R8G8B8 */
-    if (DisplayFormat == WINED3DFMT_B8G8R8X8_UNORM
-            && !(BackBufferFormat == WINED3DFMT_B8G8R8X8_UNORM || BackBufferFormat == WINED3DFMT_B8G8R8A8_UNORM))
-    {
-        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s/%s\n", debug_d3dformat(DisplayFormat), debug_d3dformat(BackBufferFormat));
-        return WINED3DERR_NOTAVAILABLE;
-    }
-
-    /* A2R10G10B10 is only allowed in fullscreen mode and it can only be mixed with backbuffer format A2R10G10B10 */
-    if (DisplayFormat == WINED3DFMT_B10G10R10A2_UNORM
-            && (BackBufferFormat != WINED3DFMT_B10G10R10A2_UNORM || Windowed))
-    {
-        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s/%s\n", debug_d3dformat(DisplayFormat), debug_d3dformat(BackBufferFormat));
-        return WINED3DERR_NOTAVAILABLE;
-    }
-
-    /* Use CheckDeviceFormat to see if the BackBufferFormat is usable with the given DisplayFormat */
-    hr = IWineD3DImpl_CheckDeviceFormat(iface, Adapter, DeviceType, DisplayFormat, WINED3DUSAGE_RENDERTARGET, WINED3DRTYPE_SURFACE, BackBufferFormat, SURFACE_OPENGL);
-    if(FAILED(hr))
-        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s/%s\n", debug_d3dformat(DisplayFormat), debug_d3dformat(BackBufferFormat));
-
-    return hr;
-}
-
-
 /* Check if we support bumpmapping for a format */
-static BOOL CheckBumpMapCapability(struct wined3d_adapter *adapter, const struct wined3d_format_desc *format_desc)
+static BOOL CheckBumpMapCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
 {
     /* Ask the fixed function pipeline implementation if it can deal
      * with the conversion. If we've got a GL extension giving native
      * support this will be an identity conversion. */
-    return (format_desc->Flags & WINED3DFMT_FLAG_BUMPMAP)
-            && adapter->fragment_pipe->color_fixup_supported(format_desc->color_fixup);
+    return (format->Flags & WINED3DFMT_FLAG_BUMPMAP)
+            && adapter->fragment_pipe->color_fixup_supported(format->color_fixup);
 }
 
 /* Check if the given DisplayFormat + DepthStencilFormat combination is valid for the Adapter */
 static BOOL CheckDepthStencilCapability(struct wined3d_adapter *adapter,
-        const struct wined3d_format_desc *display_format_desc, const struct wined3d_format_desc *ds_format_desc)
+        const struct wined3d_format *display_format, const struct wined3d_format *ds_format)
 {
     int it=0;
 
     /* Only allow depth/stencil formats */
-    if (!(ds_format_desc->depth_size || ds_format_desc->stencil_size)) return FALSE;
+    if (!(ds_format->depth_size || ds_format->stencil_size)) return FALSE;
 
     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
     {
         /* With FBOs WGL limitations do not apply, but the format needs to be FBO attachable */
-        if (ds_format_desc->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL)) return TRUE;
+        if (ds_format->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL)) return TRUE;
     }
     else
     {
@@ -3236,9 +3285,9 @@ static BOOL CheckDepthStencilCapability(struct wined3d_adapter *adapter,
         for (it = 0; it < adapter->nCfgs; ++it)
         {
             WineD3D_PixelFormat *cfg = &adapter->cfgs[it];
-            if (IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(&adapter->gl_info, cfg, display_format_desc))
+            if (IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(&adapter->gl_info, cfg, display_format))
             {
-                if (IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(&adapter->gl_info, cfg, ds_format_desc))
+                if (IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(&adapter->gl_info, cfg, ds_format))
                 {
                     return TRUE;
                 }
@@ -3249,28 +3298,29 @@ static BOOL CheckDepthStencilCapability(struct wined3d_adapter *adapter,
     return FALSE;
 }
 
-static BOOL CheckFilterCapability(struct wined3d_adapter *adapter, const struct wined3d_format_desc *format_desc)
+static BOOL CheckFilterCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
 {
     /* The flags entry of a format contains the filtering capability */
-    if (format_desc->Flags & WINED3DFMT_FLAG_FILTERING) return TRUE;
+    if (format->Flags & WINED3DFMT_FLAG_FILTERING) return TRUE;
 
     return FALSE;
 }
 
 /* Check the render target capabilities of a format */
 static BOOL CheckRenderTargetCapability(struct wined3d_adapter *adapter,
-        const struct wined3d_format_desc *adapter_format_desc, const struct wined3d_format_desc *check_format_desc)
+        const struct wined3d_format *adapter_format, const struct wined3d_format *check_format)
 {
     /* Filter out non-RT formats */
-    if (!(check_format_desc->Flags & WINED3DFMT_FLAG_RENDERTARGET)) return FALSE;
-    if(wined3d_settings.offscreen_rendering_mode == ORM_BACKBUFFER) {
+    if (!(check_format->Flags & WINED3DFMT_FLAG_RENDERTARGET)) return FALSE;
+    if (wined3d_settings.offscreen_rendering_mode == ORM_BACKBUFFER)
+    {
         WineD3D_PixelFormat *cfgs = adapter->cfgs;
         int it;
         short AdapterRed, AdapterGreen, AdapterBlue, AdapterAlpha, AdapterTotalSize;
         short CheckRed, CheckGreen, CheckBlue, CheckAlpha, CheckTotalSize;
 
-        getColorBits(adapter_format_desc, &AdapterRed, &AdapterGreen, &AdapterBlue, &AdapterAlpha, &AdapterTotalSize);
-        getColorBits(check_format_desc, &CheckRed, &CheckGreen, &CheckBlue, &CheckAlpha, &CheckTotalSize);
+        getColorBits(adapter_format, &AdapterRed, &AdapterGreen, &AdapterBlue, &AdapterAlpha, &AdapterTotalSize);
+        getColorBits(check_format, &CheckRed, &CheckGreen, &CheckBlue, &CheckAlpha, &CheckTotalSize);
 
         /* In backbuffer mode the front and backbuffer share the same WGL pixelformat.
          * The format must match in RGB, alpha is allowed to be different. (Only the backbuffer can have alpha) */
@@ -3284,10 +3334,10 @@ static BOOL CheckRenderTargetCapability(struct wined3d_adapter *adapter,
         for (it = 0; it < adapter->nCfgs; ++it)
         {
             if (cfgs[it].windowDrawable && IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(&adapter->gl_info,
-                    &cfgs[it], check_format_desc))
+                    &cfgs[it], check_format))
             {
-                TRACE_(d3d_caps)("iPixelFormat=%d is compatible with CheckFormat=%s\n",
-                        cfgs[it].iPixelFormat, debug_d3dformat(check_format_desc->format));
+                TRACE_(d3d_caps)("Pixel format %d is compatible with format %s.\n",
+                        cfgs[it].iPixelFormat, debug_d3dformat(check_format->id));
                 return TRUE;
             }
         }
@@ -3301,18 +3351,17 @@ static BOOL CheckRenderTargetCapability(struct wined3d_adapter *adapter,
     return FALSE;
 }
 
-static BOOL CheckSrgbReadCapability(struct wined3d_adapter *adapter, const struct wined3d_format_desc *format_desc)
+static BOOL CheckSrgbReadCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
 {
-    return adapter->gl_info.supported[EXT_TEXTURE_SRGB]
-            && (format_desc->Flags & WINED3DFMT_FLAG_SRGB_READ);
+    return adapter->gl_info.supported[EXT_TEXTURE_SRGB] && (format->Flags & WINED3DFMT_FLAG_SRGB_READ);
 }
 
-static BOOL CheckSrgbWriteCapability(struct wined3d_adapter *adapter, const struct wined3d_format_desc *format_desc)
+static BOOL CheckSrgbWriteCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
 {
     /* Only offer SRGB writing on X8R8G8B8/A8R8G8B8 when we use ARB or GLSL shaders as we are
      * doing the color fixup in shaders.
      * Note Windows drivers (at least on the Geforce 8800) also offer this on R5G6B5. */
-    if (format_desc->Flags & WINED3DFMT_FLAG_SRGB_WRITE)
+    if (format->Flags & WINED3DFMT_FLAG_SRGB_WRITE)
     {
         int vs_selected_mode;
         int ps_selected_mode;
@@ -3324,21 +3373,21 @@ static BOOL CheckSrgbWriteCapability(struct wined3d_adapter *adapter, const stru
         }
     }
 
-    TRACE_(d3d_caps)("[FAILED] - no SRGB writing support on format=%s\n", debug_d3dformat(format_desc->format));
+    TRACE_(d3d_caps)("[FAILED] - sRGB writes not supported by format %s.\n", debug_d3dformat(format->id));
     return FALSE;
 }
 
 /* Check if a format support blending in combination with pixel shaders */
 static BOOL CheckPostPixelShaderBlendingCapability(struct wined3d_adapter *adapter,
-        const struct wined3d_format_desc *format_desc)
+        const struct wined3d_format *format)
 {
     /* The flags entry of a format contains the post pixel shader blending capability */
-    if (format_desc->Flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING) return TRUE;
+    if (format->Flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING) return TRUE;
 
     return FALSE;
 }
 
-static BOOL CheckWrapAndMipCapability(struct wined3d_adapter *adapter, const struct wined3d_format_desc *format_desc)
+static BOOL CheckWrapAndMipCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
 {
     /* OpenGL supports mipmapping on all formats basically. Wrapping is unsupported,
      * but we have to report mipmapping so we cannot reject this flag. Tests show that
@@ -3353,11 +3402,11 @@ static BOOL CheckWrapAndMipCapability(struct wined3d_adapter *adapter, const str
 }
 
 /* Check if a texture format is supported on the given adapter */
-static BOOL CheckTextureCapability(struct wined3d_adapter *adapter, const struct wined3d_format_desc *format_desc)
+static BOOL CheckTextureCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
 {
     const struct wined3d_gl_info *gl_info = &adapter->gl_info;
 
-    switch (format_desc->format)
+    switch (format->id)
     {
         /*****
          *  supported: RGB(A) formats
@@ -3433,7 +3482,7 @@ static BOOL CheckTextureCapability(struct wined3d_adapter *adapter, const struct
             /* Ask the shader backend if it can deal with the conversion. If
              * we've got a GL extension giving native support this will be an
              * identity conversion. */
-            if (adapter->shader_backend->shader_color_fixup_supported(format_desc->color_fixup))
+            if (adapter->shader_backend->shader_color_fixup_supported(format->color_fixup))
             {
                 TRACE_(d3d_caps)("[OK]\n");
                 return TRUE;
@@ -3547,10 +3596,10 @@ static BOOL CheckTextureCapability(struct wined3d_adapter *adapter, const struct
         /* Vendor specific formats */
         case WINED3DFMT_ATI2N:
             if (gl_info->supported[ATI_TEXTURE_COMPRESSION_3DC]
-                    || gl_info->supported[EXT_TEXTURE_COMPRESSION_RGTC])
+                    || gl_info->supported[ARB_TEXTURE_COMPRESSION_RGTC])
             {
-                if (adapter->shader_backend->shader_color_fixup_supported(format_desc->color_fixup)
-                        && adapter->fragment_pipe->color_fixup_supported(format_desc->color_fixup))
+                if (adapter->shader_backend->shader_color_fixup_supported(format->color_fixup)
+                        && adapter->fragment_pipe->color_fixup_supported(format->color_fixup))
                 {
                     TRACE_(d3d_caps)("[OK]\n");
                     return TRUE;
@@ -3562,6 +3611,21 @@ static BOOL CheckTextureCapability(struct wined3d_adapter *adapter, const struct
             TRACE_(d3d_caps)("[FAILED]\n");
             return FALSE;
 
+        /* Depth bound test. To query if the card supports it CheckDeviceFormat with the special
+         * format MAKEFOURCC('N','V','D','B') is used.
+         * It is enabled by setting D3DRS_ADAPTIVETESS_X render state to MAKEFOURCC('N','V','D','B') and
+         * then controlled by setting D3DRS_ADAPTIVETESS_Z (zMin) and D3DRS_ADAPTIVETESS_W (zMax)
+         * to test value.
+         */
+        case WINED3DFMT_NVDB:
+            if (gl_info->supported[EXT_DEPTH_BOUNDS_TEST])
+            {
+                TRACE_(d3d_caps)("[OK]\n");
+                return TRUE;
+            }
+            TRACE_(d3d_caps)("[FAILED]\n");
+            return FALSE;
+
         case WINED3DFMT_NVHU:
         case WINED3DFMT_NVHS:
             /* These formats seem to be similar to the HILO formats in GL_NV_texture_shader. NVHU
@@ -3577,19 +3641,20 @@ static BOOL CheckTextureCapability(struct wined3d_adapter *adapter, const struct
             return FALSE;
 
         default:
-            ERR("Unhandled format=%s\n", debug_d3dformat(format_desc->format));
+            ERR("Unhandled format %s.\n", debug_d3dformat(format->id));
             break;
     }
     return FALSE;
 }
 
 static BOOL CheckSurfaceCapability(struct wined3d_adapter *adapter,
-        const struct wined3d_format_desc *adapter_format_desc,
-        const struct wined3d_format_desc *check_format_desc,
+        const struct wined3d_format *adapter_format,
+        const struct wined3d_format *check_format,
         WINED3DSURFTYPE SurfaceType)
 {
-    if(SurfaceType == SURFACE_GDI) {
-        switch(check_format_desc->format)
+    if (SurfaceType == SURFACE_GDI)
+    {
+        switch (check_format->id)
         {
             case WINED3DFMT_B8G8R8_UNORM:
             case WINED3DFMT_B8G8R8A8_UNORM:
@@ -3618,14 +3683,14 @@ static BOOL CheckSurfaceCapability(struct wined3d_adapter *adapter,
     }
 
     /* All format that are supported for textures are supported for surfaces as well */
-    if (CheckTextureCapability(adapter, check_format_desc)) return TRUE;
+    if (CheckTextureCapability(adapter, check_format)) return TRUE;
     /* All depth stencil formats are supported on surfaces */
-    if (CheckDepthStencilCapability(adapter, adapter_format_desc, check_format_desc)) return TRUE;
+    if (CheckDepthStencilCapability(adapter, adapter_format, check_format)) return TRUE;
 
     /* If opengl can't process the format natively, the blitter may be able to convert it */
     if (adapter->blitter->blit_supported(&adapter->gl_info, BLIT_OP_BLIT,
-                                         NULL, WINED3DPOOL_DEFAULT, 0, check_format_desc,
-                                         NULL, WINED3DPOOL_DEFAULT, 0, adapter_format_desc))
+            NULL, WINED3DPOOL_DEFAULT, 0, check_format,
+            NULL, WINED3DPOOL_DEFAULT, 0, adapter_format))
     {
         TRACE_(d3d_caps)("[OK]\n");
         return TRUE;
@@ -3637,21 +3702,20 @@ static BOOL CheckSurfaceCapability(struct wined3d_adapter *adapter,
 }
 
 static BOOL CheckVertexTextureCapability(struct wined3d_adapter *adapter,
-        const struct wined3d_format_desc *format_desc)
+        const struct wined3d_format *format)
 {
-    return adapter->gl_info.limits.vertex_samplers
-            && (format_desc->Flags & WINED3DFMT_FLAG_VTF);
+    return adapter->gl_info.limits.vertex_samplers && (format->Flags & WINED3DFMT_FLAG_VTF);
 }
 
 static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapter, WINED3DDEVTYPE DeviceType,
-        WINED3DFORMAT AdapterFormat, DWORD Usage, WINED3DRESOURCETYPE RType, WINED3DFORMAT CheckFormat,
-        WINED3DSURFTYPE SurfaceType)
+        enum wined3d_format_id AdapterFormat, DWORD Usage, WINED3DRESOURCETYPE RType,
+        enum wined3d_format_id CheckFormat, WINED3DSURFTYPE SurfaceType)
 {
     IWineD3DImpl *This = (IWineD3DImpl *)iface;
     struct wined3d_adapter *adapter = &This->adapters[Adapter];
     const struct wined3d_gl_info *gl_info = &adapter->gl_info;
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(CheckFormat, gl_info);
-    const struct wined3d_format_desc *adapter_format_desc = getFormatDescEntry(AdapterFormat, gl_info);
+    const struct wined3d_format *format = wined3d_get_format(gl_info, CheckFormat);
+    const struct wined3d_format *adapter_format = wined3d_get_format(gl_info, AdapterFormat);
     DWORD UsageCaps = 0;
 
     TRACE_(d3d_caps)("(%p)-> (STUB) (Adptr:%d, DevType:(%u,%s), AdptFmt:(%u,%s), Use:(%u,%s,%s), ResTyp:(%x,%s), CheckFmt:(%u,%s))\n",
@@ -3691,7 +3755,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
                 return WINED3DERR_NOTAVAILABLE;
             }
 
-            if (!CheckTextureCapability(adapter, format_desc))
+            if (!CheckTextureCapability(adapter, format))
             {
                 TRACE_(d3d_caps)("[FAILED] - Cube texture format not supported\n");
                 return WINED3DERR_NOTAVAILABLE;
@@ -3713,7 +3777,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_RENDERTARGET)
             {
-                if (!CheckRenderTargetCapability(adapter, adapter_format_desc, format_desc))
+                if (!CheckRenderTargetCapability(adapter, adapter_format, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No rendertarget support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3727,7 +3791,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_FILTER)
             {
-                if (!CheckFilterCapability(adapter, format_desc))
+                if (!CheckFilterCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query filter support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3737,7 +3801,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING)
             {
-                if (!CheckPostPixelShaderBlendingCapability(adapter, format_desc))
+                if (!CheckPostPixelShaderBlendingCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query post pixelshader blending support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3747,7 +3811,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_SRGBREAD)
             {
-                if (!CheckSrgbReadCapability(adapter, format_desc))
+                if (!CheckSrgbReadCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query srgbread support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3757,7 +3821,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_SRGBWRITE)
             {
-                if (!CheckSrgbWriteCapability(adapter, format_desc))
+                if (!CheckSrgbWriteCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query srgbwrite support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3767,7 +3831,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_VERTEXTEXTURE)
             {
-                if (!CheckVertexTextureCapability(adapter, format_desc))
+                if (!CheckVertexTextureCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query vertextexture support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3777,7 +3841,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_WRAPANDMIP)
             {
-                if (!CheckWrapAndMipCapability(adapter, format_desc))
+                if (!CheckWrapAndMipCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No wrapping and mipmapping support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3792,7 +3856,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
              *      - WINED3DUSAGE_NONSECURE (d3d9ex)
              *      - WINED3DUSAGE_RENDERTARGET
              */
-            if (!CheckSurfaceCapability(adapter, adapter_format_desc, format_desc, SurfaceType))
+            if (!CheckSurfaceCapability(adapter, adapter_format, format, SurfaceType))
             {
                 TRACE_(d3d_caps)("[FAILED] - Not supported for plain surfaces\n");
                 return WINED3DERR_NOTAVAILABLE;
@@ -3800,7 +3864,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_DEPTHSTENCIL)
             {
-                if (!CheckDepthStencilCapability(adapter, adapter_format_desc, format_desc))
+                if (!CheckDepthStencilCapability(adapter, adapter_format, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No depthstencil support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3810,7 +3874,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_RENDERTARGET)
             {
-                if (!CheckRenderTargetCapability(adapter, adapter_format_desc, format_desc))
+                if (!CheckRenderTargetCapability(adapter, adapter_format, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No rendertarget support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3820,7 +3884,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING)
             {
-                if (!CheckPostPixelShaderBlendingCapability(adapter, format_desc))
+                if (!CheckPostPixelShaderBlendingCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query post pixelshader blending support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3847,7 +3911,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
                 return WINED3DERR_NOTAVAILABLE;
             }
 
-            if (!CheckTextureCapability(adapter, format_desc))
+            if (!CheckTextureCapability(adapter, format))
             {
                 TRACE_(d3d_caps)("[FAILED] - Texture format not supported\n");
                 return WINED3DERR_NOTAVAILABLE;
@@ -3869,7 +3933,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_RENDERTARGET)
             {
-                if (!CheckRenderTargetCapability(adapter, adapter_format_desc, format_desc))
+                if (!CheckRenderTargetCapability(adapter, adapter_format, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No rendertarget support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3883,7 +3947,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_FILTER)
             {
-                if (!CheckFilterCapability(adapter, format_desc))
+                if (!CheckFilterCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query filter support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3893,7 +3957,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_LEGACYBUMPMAP)
             {
-                if (!CheckBumpMapCapability(adapter, format_desc))
+                if (!CheckBumpMapCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No legacy bumpmap support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3903,7 +3967,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING)
             {
-                if (!CheckPostPixelShaderBlendingCapability(adapter, format_desc))
+                if (!CheckPostPixelShaderBlendingCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query post pixelshader blending support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3913,7 +3977,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_SRGBREAD)
             {
-                if (!CheckSrgbReadCapability(adapter, format_desc))
+                if (!CheckSrgbReadCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query srgbread support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3923,7 +3987,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_SRGBWRITE)
             {
-                if (!CheckSrgbWriteCapability(adapter, format_desc))
+                if (!CheckSrgbWriteCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query srgbwrite support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3933,7 +3997,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_VERTEXTEXTURE)
             {
-                if (!CheckVertexTextureCapability(adapter, format_desc))
+                if (!CheckVertexTextureCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query vertextexture support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3943,7 +4007,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_WRAPANDMIP)
             {
-                if (!CheckWrapAndMipCapability(adapter, format_desc))
+                if (!CheckWrapAndMipCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No wrapping and mipmapping support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3953,12 +4017,12 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_DEPTHSTENCIL)
             {
-                if (!CheckDepthStencilCapability(adapter, adapter_format_desc, format_desc))
+                if (!CheckDepthStencilCapability(adapter, adapter_format, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No depth stencil support\n");
                     return WINED3DERR_NOTAVAILABLE;
                 }
-                if ((format_desc->Flags & WINED3DFMT_FLAG_SHADOW) && !gl_info->supported[ARB_SHADOW])
+                if ((format->Flags & WINED3DFMT_FLAG_SHADOW) && !gl_info->supported[ARB_SHADOW])
                 {
                     TRACE_(d3d_caps)("[FAILED] - No shadow sampler support.\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -3991,7 +4055,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
                 return WINED3DERR_NOTAVAILABLE;
             }
 
-            if (!CheckTextureCapability(adapter, format_desc))
+            if (!CheckTextureCapability(adapter, format))
             {
                 TRACE_(d3d_caps)("[FAILED] - Format not supported\n");
                 return WINED3DERR_NOTAVAILABLE;
@@ -4061,7 +4125,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_FILTER)
             {
-                if (!CheckFilterCapability(adapter, format_desc))
+                if (!CheckFilterCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query filter support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -4071,7 +4135,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING)
             {
-                if (!CheckPostPixelShaderBlendingCapability(adapter, format_desc))
+                if (!CheckPostPixelShaderBlendingCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query post pixelshader blending support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -4081,7 +4145,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_SRGBREAD)
             {
-                if (!CheckSrgbReadCapability(adapter, format_desc))
+                if (!CheckSrgbReadCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query srgbread support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -4091,7 +4155,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_SRGBWRITE)
             {
-                if (!CheckSrgbWriteCapability(adapter, format_desc))
+                if (!CheckSrgbWriteCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query srgbwrite support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -4101,7 +4165,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_VERTEXTEXTURE)
             {
-                if (!CheckVertexTextureCapability(adapter, format_desc))
+                if (!CheckVertexTextureCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No query vertextexture support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -4111,7 +4175,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 
             if (Usage & WINED3DUSAGE_QUERY_WRAPANDMIP)
             {
-                if (!CheckWrapAndMipCapability(adapter, format_desc))
+                if (!CheckWrapAndMipCapability(adapter, format))
                 {
                     TRACE_(d3d_caps)("[FAILED] - No wrapping and mipmapping support\n");
                     return WINED3DERR_NOTAVAILABLE;
@@ -4140,7 +4204,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapt
 }
 
 static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormatConversion(IWineD3D *iface, UINT adapter_idx,
-        WINED3DDEVTYPE device_type, WINED3DFORMAT src_format, WINED3DFORMAT dst_format)
+        WINED3DDEVTYPE device_type, enum wined3d_format_id src_format, enum wined3d_format_id dst_format)
 {
     FIXME("iface %p, adapter_idx %u, device_type %s, src_format %s, dst_format %s stub!\n",
             iface, adapter_idx, debug_d3ddevicetype(device_type), debug_d3dformat(src_format),
@@ -4149,6 +4213,108 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormatConversion(IWineD3D *iface,
     return WINED3D_OK;
 }
 
+static HRESULT WINAPI IWineD3DImpl_CheckDeviceType(IWineD3D *iface, UINT adapter_idx, WINED3DDEVTYPE device_type,
+        enum wined3d_format_id display_format, enum wined3d_format_id backbuffer_format, BOOL windowed)
+{
+    UINT mode_count;
+    HRESULT hr;
+
+    TRACE("iface %p, adapter_idx %u, device_type %s, display_format %s, backbuffer_format %s, windowed %#x.\n",
+            iface, adapter_idx, debug_d3ddevicetype(device_type), debug_d3dformat(display_format),
+            debug_d3dformat(backbuffer_format), windowed);
+
+    if (adapter_idx >= IWineD3D_GetAdapterCount(iface))
+    {
+        WARN_(d3d_caps)("adapter_idx >= IWineD3D_GetAdapterCount(iface), returning WINED3DERR_INVALIDCALL\n");
+        return WINED3DERR_INVALIDCALL;
+    }
+
+    /* The task of this function is to check whether a certain display / backbuffer format
+     * combination is available on the given adapter. In fullscreen mode microsoft specified
+     * that the display format shouldn't provide alpha and that ignoring alpha the backbuffer
+     * and display format should match exactly.
+     * In windowed mode format conversion can occur and this depends on the driver. When format
+     * conversion is done, this function should nevertheless fail and applications need to use
+     * CheckDeviceFormatConversion.
+     * At the moment we assume that fullscreen and windowed have the same capabilities. */
+
+    /* There are only 4 display formats. */
+    if (!(display_format == WINED3DFMT_B5G6R5_UNORM
+            || display_format == WINED3DFMT_B5G5R5X1_UNORM
+            || display_format == WINED3DFMT_B8G8R8X8_UNORM
+            || display_format == WINED3DFMT_B10G10R10A2_UNORM))
+    {
+        TRACE_(d3d_caps)("Format %s is not supported as display format.\n", debug_d3dformat(display_format));
+        return WINED3DERR_NOTAVAILABLE;
+    }
+
+    /* If the requested display format is not available, don't continue. */
+    mode_count = IWineD3DImpl_GetAdapterModeCount(iface, adapter_idx, display_format);
+    if (!mode_count)
+    {
+        TRACE_(d3d_caps)("No available modes for display format %s.\n", debug_d3dformat(display_format));
+        return WINED3DERR_NOTAVAILABLE;
+    }
+
+    /* Windowed mode allows you to specify WINED3DFMT_UNKNOWN for the backbuffer format,
+     * it means 'reuse' the display format for the backbuffer. */
+    if (!windowed && backbuffer_format == WINED3DFMT_UNKNOWN)
+    {
+        TRACE_(d3d_caps)("backbuffer_format WINED3FMT_UNKNOWN only available in windowed mode.\n");
+        return WINED3DERR_NOTAVAILABLE;
+    }
+
+    /* In FULLSCREEN mode WINED3DFMT_B5G6R5_UNORM can only be mixed with
+     * backbuffer format WINED3DFMT_B5G6R5_UNORM. */
+    if (display_format == WINED3DFMT_B5G6R5_UNORM && backbuffer_format != WINED3DFMT_B5G6R5_UNORM)
+    {
+        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
+                debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
+        return WINED3DERR_NOTAVAILABLE;
+    }
+
+    /* In FULLSCREEN mode WINED3DFMT_B5G5R5X1_UNORM can only be mixed with
+     * backbuffer formats WINED3DFMT_B5G5R5X1_UNORM and
+     * WINED3DFMT_B5G5R5A1_UNORM. */
+    if (display_format == WINED3DFMT_B5G5R5X1_UNORM
+            && !(backbuffer_format == WINED3DFMT_B5G5R5X1_UNORM || backbuffer_format == WINED3DFMT_B5G5R5A1_UNORM))
+    {
+        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
+                debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
+        return WINED3DERR_NOTAVAILABLE;
+    }
+
+    /* In FULLSCREEN mode WINED3DFMT_B8G8R8X8_UNORM can only be mixed with
+     * backbuffer formats WINED3DFMT_B8G8R8X8_UNORM and
+     * WINED3DFMT_B8G8R8A8_UNORM. */
+    if (display_format == WINED3DFMT_B8G8R8X8_UNORM
+            && !(backbuffer_format == WINED3DFMT_B8G8R8X8_UNORM || backbuffer_format == WINED3DFMT_B8G8R8A8_UNORM))
+    {
+        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
+                debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
+        return WINED3DERR_NOTAVAILABLE;
+    }
+
+    /* WINED3DFMT_B10G10R10A2_UNORM is only allowed in fullscreen mode and it
+     * can only be mixed with backbuffer format WINED3DFMT_B10G10R10A2_UNORM. */
+    if (display_format == WINED3DFMT_B10G10R10A2_UNORM
+            && (backbuffer_format != WINED3DFMT_B10G10R10A2_UNORM || windowed))
+    {
+        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
+                debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
+        return WINED3DERR_NOTAVAILABLE;
+    }
+
+    /* Use CheckDeviceFormat to see if the backbuffer_format is usable with the given display_format */
+    hr = IWineD3DImpl_CheckDeviceFormat(iface, adapter_idx, device_type, display_format,
+            WINED3DUSAGE_RENDERTARGET, WINED3DRTYPE_SURFACE, backbuffer_format, SURFACE_OPENGL);
+    if (FAILED(hr))
+        TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
+                debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
+
+    return hr;
+}
+
 /* Note: d3d8 passes in a pointer to a D3DCAPS8 structure, which is a true
       subset of a D3DCAPS9 structure. However, it has to come via a void *
       as the d3d8 interface cannot import the d3d9 header                  */
@@ -4161,7 +4327,7 @@ static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter,
     int ps_selected_mode;
     struct shader_caps shader_caps;
     struct fragment_caps fragment_caps;
-    DWORD ckey_caps, blit_caps, fx_caps;
+    DWORD ckey_caps, blit_caps, fx_caps, pal_caps;
 
     TRACE_(d3d_caps)("(%p)->(Adptr:%d, DevType: %x, pCaps: %p)\n", This, Adapter, DeviceType, pCaps);
 
@@ -4688,6 +4854,8 @@ static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter,
                                         WINEDDCAPS_COLORKEY                 |
                                         WINEDDCAPS_COLORKEYHWASSIST         |
                                         WINEDDCAPS_ALIGNBOUNDARYSRC;
+    pal_caps =                          WINEDDPCAPS_8BIT                    |
+                                        WINEDDPCAPS_PRIMARYSURFACE;
 
     /* Fill the ddraw caps structure */
     pCaps->DirectDrawCaps.Caps =        WINEDDCAPS_GDI                      |
@@ -4698,6 +4866,9 @@ static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter,
                                         WINEDDCAPS2_PRIMARYGAMMA             |
                                         WINEDDCAPS2_WIDESURFACES             |
                                         WINEDDCAPS2_CANRENDERWINDOWED;
+    pCaps->DirectDrawCaps.CKeyCaps =    ckey_caps;
+    pCaps->DirectDrawCaps.FXCaps =      fx_caps;
+    pCaps->DirectDrawCaps.PalCaps =     pal_caps;
     pCaps->DirectDrawCaps.SVBCaps =     blit_caps;
     pCaps->DirectDrawCaps.SVBCKeyCaps = ckey_caps;
     pCaps->DirectDrawCaps.SVBFXCaps =   fx_caps;
@@ -4733,18 +4904,15 @@ static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter,
     return WINED3D_OK;
 }
 
-static HRESULT WINAPI IWineD3DImpl_CreateDevice(IWineD3D *iface, UINT adapter_idx,
-        WINED3DDEVTYPE device_type, HWND focus_window, DWORD flags, IUnknown *parent,
-        IWineD3DDeviceParent *device_parent, IWineD3DDevice **device)
+static HRESULT WINAPI IWineD3DImpl_CreateDevice(IWineD3D *iface, UINT adapter_idx, WINED3DDEVTYPE device_type,
+        HWND focus_window, DWORD flags, IWineD3DDeviceParent *device_parent, IWineD3DDevice **device)
 {
     IWineD3DImpl *This = (IWineD3DImpl *)iface;
     IWineD3DDeviceImpl *object;
     HRESULT hr;
 
-    TRACE("iface %p, adapter_idx %u, device_type %#x, focus_window %p, flags %#x.\n"
-            "parent %p, device_parent %p, device %p.\n",
-            iface, adapter_idx, device_type, focus_window, flags,
-            parent, device_parent, device);
+    TRACE("iface %p, adapter_idx %u, device_type %#x, focus_window %p, flags %#x, device_parent %p, device %p.\n",
+            iface, adapter_idx, device_type, focus_window, flags, device_parent, device);
 
     /* Validate the adapter number. If no adapters are available(no GL), ignore the adapter
      * number and create a device without a 3D adapter for 2D only operation. */
@@ -4760,7 +4928,7 @@ static HRESULT WINAPI IWineD3DImpl_CreateDevice(IWineD3D *iface, UINT adapter_id
         return E_OUTOFMEMORY;
     }
 
-    hr = device_init(object, This, adapter_idx, device_type, focus_window, flags, parent, device_parent);
+    hr = device_init(object, This, adapter_idx, device_type, focus_window, flags, device_parent);
     if (FAILED(hr))
     {
         WARN("Failed to initialize device, hr %#x.\n", hr);
@@ -4776,11 +4944,11 @@ static HRESULT WINAPI IWineD3DImpl_CreateDevice(IWineD3D *iface, UINT adapter_id
     return WINED3D_OK;
 }
 
-static HRESULT WINAPI IWineD3DImpl_GetParent(IWineD3D *iface, IUnknown **pParent) {
-    IWineD3DImpl *This = (IWineD3DImpl *)iface;
-    IUnknown_AddRef(This->parent);
-    *pParent = This->parent;
-    return WINED3D_OK;
+static void * WINAPI IWineD3DImpl_GetParent(IWineD3D *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ((IWineD3DImpl *)iface)->parent;
 }
 
 static void WINE_GLAPI invalid_func(const void *data)
@@ -4969,6 +5137,7 @@ static void fillGLAttribFuncs(const struct wined3d_gl_info *gl_info)
     }
 }
 
+/* Do not call while under the GL lock. */
 static BOOL InitAdapters(IWineD3DImpl *This)
 {
     static HMODULE mod_gl;
@@ -5071,11 +5240,7 @@ static BOOL InitAdapters(IWineD3DImpl *This)
 
         hdc = fake_gl_ctx.dc;
 
-        /* Use the VideoRamSize registry setting when set */
-        if(wined3d_settings.emulated_textureram)
-            adapter->TextureRam = wined3d_settings.emulated_textureram;
-        else
-            adapter->TextureRam = adapter->gl_info.vidmem;
+        adapter->TextureRam = adapter->driver_info.vidmem;
         adapter->UsedTextureRam = 0;
         TRACE("Emulating %dMB of texture ram\n", adapter->TextureRam/(1024*1024));
 
@@ -5298,7 +5463,8 @@ const struct wined3d_parent_ops wined3d_null_parent_ops =
     wined3d_null_wined3d_object_destroyed,
 };
 
-HRESULT wined3d_init(IWineD3DImpl *wined3d, UINT version, IUnknown *parent)
+/* Do not call while under the GL lock. */
+HRESULT wined3d_init(IWineD3DImpl *wined3d, UINT version, void *parent)
 {
     wined3d->lpVtbl = &IWineD3D_Vtbl;
     wined3d->dxVersion = version;
index b36ef5b..6b6102b 100644 (file)
@@ -33,13 +33,10 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d_draw);
 #include <math.h>
 
 /* GL locking is done by the caller */
-static void drawStridedFast(IWineD3DDevice *iface, GLenum primitive_type,
-        UINT count, UINT idx_size, const void *idx_data, UINT start_idx)
+static void drawStridedFast(GLenum primitive_type, UINT count, UINT idx_size, const void *idx_data, UINT start_idx)
 {
     if (idx_size)
     {
-        TRACE("(%p) : glElements(%x, %d, ...)\n", iface, primitive_type, count);
-
         glDrawElements(primitive_type, count,
                 idx_size == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT,
                 (const char *)idx_data + (idx_size * start_idx));
@@ -47,8 +44,6 @@ static void drawStridedFast(IWineD3DDevice *iface, GLenum primitive_type,
     }
     else
     {
-        TRACE("(%p) : glDrawArrays(%#x, %d, %d)\n", iface, primitive_type, start_idx, count);
-
         glDrawArrays(primitive_type, start_idx, count);
         checkGLcall("glDrawArrays");
     }
@@ -69,9 +64,10 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
     const DWORD               *pIdxBufL     = NULL;
     UINT vx_index;
     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-    const UINT *streamOffset = This->stateBlock->streamOffset;
-    LONG                      SkipnStrides = startIdx + This->stateBlock->loadBaseVertexIndex;
-    BOOL                      pixelShader = use_ps(This->stateBlock);
+    const struct wined3d_state *state = &This->stateBlock->state;
+    const struct wined3d_stream_state *streams = state->streams;
+    LONG SkipnStrides = startIdx + state->load_base_vertex_index;
+    BOOL pixelShader = use_ps(state);
     BOOL specular_fog = FALSE;
     const BYTE *texCoords[WINED3DDP_MAXTEXCOORD];
     const BYTE *diffuse = NULL, *specular = NULL, *normal = NULL, *position = NULL;
@@ -91,7 +87,7 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
          * supported or other reason), or with user pointer drawing idxData
          * will be non-NULL. */
         if (!idxData)
-            idxData = buffer_get_sysmem((struct wined3d_buffer *)This->stateBlock->pIndexData, gl_info);
+            idxData = buffer_get_sysmem(state->index_buffer, gl_info);
 
         if (idxSize == 2) pIdxBufS = idxData;
         else pIdxBufL = idxData;
@@ -106,13 +102,13 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
     if (si->use_map & (1 << WINED3D_FFP_POSITION))
     {
         element = &si->elements[WINED3D_FFP_POSITION];
-        position = element->data + streamOffset[element->stream_idx];
+        position = element->data + streams[element->stream_idx].offset;
     }
 
     if (si->use_map & (1 << WINED3D_FFP_NORMAL))
     {
         element = &si->elements[WINED3D_FFP_NORMAL];
-        normal = element->data + streamOffset[element->stream_idx];
+        normal = element->data + streams[element->stream_idx].offset;
     }
     else
     {
@@ -123,10 +119,10 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
     if (si->use_map & (1 << WINED3D_FFP_DIFFUSE))
     {
         element = &si->elements[WINED3D_FFP_DIFFUSE];
-        diffuse = element->data + streamOffset[element->stream_idx];
+        diffuse = element->data + streams[element->stream_idx].offset;
 
-        if (num_untracked_materials && element->format_desc->format != WINED3DFMT_B8G8R8A8_UNORM)
-            FIXME("Implement diffuse color tracking from %s\n", debug_d3dformat(element->format_desc->format));
+        if (num_untracked_materials && element->format->id != WINED3DFMT_B8G8R8A8_UNORM)
+            FIXME("Implement diffuse color tracking from %s\n", debug_d3dformat(element->format->id));
     }
     else
     {
@@ -136,18 +132,18 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
     if (si->use_map & (1 << WINED3D_FFP_SPECULAR))
     {
         element = &si->elements[WINED3D_FFP_SPECULAR];
-        specular = element->data + streamOffset[element->stream_idx];
+        specular = element->data + streams[element->stream_idx].offset;
 
         /* special case where the fog density is stored in the specular alpha channel */
-        if (This->stateBlock->renderState[WINED3DRS_FOGENABLE]
-                && (This->stateBlock->renderState[WINED3DRS_FOGVERTEXMODE] == WINED3DFOG_NONE
-                    || si->elements[WINED3D_FFP_POSITION].format_desc->format == WINED3DFMT_R32G32B32A32_FLOAT)
-                && This->stateBlock->renderState[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE)
+        if (state->render_states[WINED3DRS_FOGENABLE]
+                && (state->render_states[WINED3DRS_FOGVERTEXMODE] == WINED3DFOG_NONE
+                    || si->elements[WINED3D_FFP_POSITION].format->id == WINED3DFMT_R32G32B32A32_FLOAT)
+                && state->render_states[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE)
         {
             if (gl_info->supported[EXT_FOG_COORD])
             {
-                if (element->format_desc->format == WINED3DFMT_B8G8R8A8_UNORM) specular_fog = TRUE;
-                else FIXME("Implement fog coordinates from %s\n", debug_d3dformat(element->format_desc->format));
+                if (element->format->id == WINED3DFMT_B8G8R8A8_UNORM) specular_fog = TRUE;
+                else FIXME("Implement fog coordinates from %s\n", debug_d3dformat(element->format->id));
             }
             else
             {
@@ -169,7 +165,7 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
 
     for (textureNo = 0; textureNo < texture_stages; ++textureNo)
     {
-        int coordIdx = This->stateBlock->textureState[textureNo][WINED3DTSS_TEXCOORDINDEX];
+        int coordIdx = state->texture_states[textureNo][WINED3DTSS_TEXCOORDINDEX];
         DWORD texture_idx = This->texUnitMap[textureNo];
 
         if (!gl_info->supported[ARB_MULTITEXTURE] && textureNo > 0)
@@ -178,7 +174,7 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
             continue;
         }
 
-        if (!pixelShader && !This->stateBlock->textures[textureNo]) continue;
+        if (!pixelShader && !state->textures[textureNo]) continue;
 
         if (texture_idx == WINED3D_UNMAPPED_STAGE) continue;
 
@@ -196,7 +192,7 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
         if (si->use_map & (1 << (WINED3D_FFP_TEXCOORD0 + coordIdx)))
         {
             element = &si->elements[WINED3D_FFP_TEXCOORD0 + coordIdx];
-            texCoords[coordIdx] = element->data + streamOffset[element->stream_idx];
+            texCoords[coordIdx] = element->data + streams[element->stream_idx].offset;
             tex_mask |= (1 << textureNo);
         }
         else
@@ -221,13 +217,13 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
          */
 
         /* For indexed data, we need to go a few more strides in */
-        if (idxData != NULL) {
-
+        if (idxData)
+        {
             /* Indexed so work out the number of strides to skip */
             if (idxSize == 2)
-                SkipnStrides = pIdxBufS[startIdx + vx_index] + This->stateBlock->loadBaseVertexIndex;
+                SkipnStrides = pIdxBufS[startIdx + vx_index] + state->load_base_vertex_index;
             else
-                SkipnStrides = pIdxBufL[startIdx + vx_index] + This->stateBlock->loadBaseVertexIndex;
+                SkipnStrides = pIdxBufL[startIdx + vx_index] + state->load_base_vertex_index;
         }
 
         tmp_tex_mask = tex_mask;
@@ -239,11 +235,11 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
 
             if (!(tmp_tex_mask & 1)) continue;
 
-            coord_idx = This->stateBlock->textureState[texture][WINED3DTSS_TEXCOORDINDEX];
+            coord_idx = state->texture_states[texture][WINED3DTSS_TEXCOORDINDEX];
             ptr = texCoords[coord_idx] + (SkipnStrides * si->elements[WINED3D_FFP_TEXCOORD0 + coord_idx].stride);
 
             texture_idx = This->texUnitMap[texture];
-            multi_texcoord_funcs[si->elements[WINED3D_FFP_TEXCOORD0 + coord_idx].format_desc->emit_idx](
+            multi_texcoord_funcs[si->elements[WINED3D_FFP_TEXCOORD0 + coord_idx].format->emit_idx](
                     GL_TEXTURE0_ARB + texture_idx, ptr);
         }
 
@@ -251,7 +247,7 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
         if (diffuse) {
             const void *ptrToCoords = diffuse + SkipnStrides * si->elements[WINED3D_FFP_DIFFUSE].stride;
 
-            diffuse_funcs[si->elements[WINED3D_FFP_DIFFUSE].format_desc->emit_idx](ptrToCoords);
+            diffuse_funcs[si->elements[WINED3D_FFP_DIFFUSE].format->emit_idx](ptrToCoords);
             if (num_untracked_materials)
             {
                 DWORD diffuseColor = ((const DWORD *)ptrToCoords)[0];
@@ -274,7 +270,7 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
         if (specular) {
             const void *ptrToCoords = specular + SkipnStrides * si->elements[WINED3D_FFP_SPECULAR].stride;
 
-            specular_funcs[si->elements[WINED3D_FFP_SPECULAR].format_desc->emit_idx](ptrToCoords);
+            specular_funcs[si->elements[WINED3D_FFP_SPECULAR].format->emit_idx](ptrToCoords);
 
             if (specular_fog)
             {
@@ -284,21 +280,20 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
         }
 
         /* Normal -------------------------------- */
-        if (normal != NULL) {
+        if (normal)
+        {
             const void *ptrToCoords = normal + SkipnStrides * si->elements[WINED3D_FFP_NORMAL].stride;
-            normal_funcs[si->elements[WINED3D_FFP_NORMAL].format_desc->emit_idx](ptrToCoords);
+            normal_funcs[si->elements[WINED3D_FFP_NORMAL].format->emit_idx](ptrToCoords);
         }
 
         /* Position -------------------------------- */
         if (position) {
             const void *ptrToCoords = position + SkipnStrides * si->elements[WINED3D_FFP_POSITION].stride;
-            position_funcs[si->elements[WINED3D_FFP_POSITION].format_desc->emit_idx](ptrToCoords);
+            position_funcs[si->elements[WINED3D_FFP_POSITION].format->emit_idx](ptrToCoords);
         }
 
         /* For non indexed mode, step onto next parts */
-        if (idxData == NULL) {
-            ++SkipnStrides;
-        }
+        if (!idxData) ++SkipnStrides;
     }
 
     glEnd();
@@ -306,10 +301,9 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
 }
 
 /* GL locking is done by the caller */
-static inline void send_attribute(IWineD3DDeviceImpl *This, WINED3DFORMAT format, const UINT index, const void *ptr)
+static inline void send_attribute(const struct wined3d_gl_info *gl_info,
+        enum wined3d_format_id format, const UINT index, const void *ptr)
 {
-    const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
-
     switch(format)
     {
         case WINED3DFMT_R32_FLOAT:
@@ -417,17 +411,15 @@ static inline void send_attribute(IWineD3DDeviceImpl *This, WINED3DFORMAT format
 }
 
 /* GL locking is done by the caller */
-static void drawStridedSlowVs(IWineD3DDevice *iface, const struct wined3d_stream_info *si, UINT numberOfVertices,
-        GLenum glPrimitiveType, const void *idxData, UINT idxSize, UINT startIdx)
+static void drawStridedSlowVs(const struct wined3d_gl_info *gl_info, const struct wined3d_state *state,
+        const struct wined3d_stream_info *si, UINT numberOfVertices, GLenum glPrimitiveType,
+        const void *idxData, UINT idxSize, UINT startIdx)
 {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
-    const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
-    LONG                      SkipnStrides = startIdx + This->stateBlock->loadBaseVertexIndex;
-    const WORD                *pIdxBufS     = NULL;
-    const DWORD               *pIdxBufL     = NULL;
+    LONG SkipnStrides = startIdx + state->load_base_vertex_index;
+    const DWORD *pIdxBufL = NULL;
+    const WORD *pIdxBufS = NULL;
     UINT vx_index;
     int i;
-    IWineD3DStateBlockImpl *stateblock = This->stateBlock;
     const BYTE *ptr;
 
     if (idxSize)
@@ -437,7 +429,7 @@ static void drawStridedSlowVs(IWineD3DDevice *iface, const struct wined3d_stream
          * supported or other reason), or with user pointer drawing idxData
          * will be non-NULL. */
         if (!idxData)
-            idxData = buffer_get_sysmem((struct wined3d_buffer *)This->stateBlock->pIndexData, gl_info);
+            idxData = buffer_get_sysmem(state->index_buffer, gl_info);
 
         if (idxSize == 2) pIdxBufS = idxData;
         else pIdxBufL = idxData;
@@ -449,25 +441,25 @@ static void drawStridedSlowVs(IWineD3DDevice *iface, const struct wined3d_stream
     /* Start drawing in GL */
     glBegin(glPrimitiveType);
 
-    for (vx_index = 0; vx_index < numberOfVertices; ++vx_index) {
-        if (idxData != NULL) {
-
+    for (vx_index = 0; vx_index < numberOfVertices; ++vx_index)
+    {
+        if (idxData)
+        {
             /* Indexed so work out the number of strides to skip */
             if (idxSize == 2)
-                SkipnStrides = pIdxBufS[startIdx + vx_index] + stateblock->loadBaseVertexIndex;
+                SkipnStrides = pIdxBufS[startIdx + vx_index] + state->load_base_vertex_index;
             else
-                SkipnStrides = pIdxBufL[startIdx + vx_index] + stateblock->loadBaseVertexIndex;
+                SkipnStrides = pIdxBufL[startIdx + vx_index] + state->load_base_vertex_index;
         }
 
         for (i = MAX_ATTRIBS - 1; i >= 0; i--)
         {
             if (!(si->use_map & (1 << i))) continue;
 
-            ptr = si->elements[i].data +
-                  si->elements[i].stride * SkipnStrides +
-                  stateblock->streamOffset[si->elements[i].stream_idx];
+            ptr = si->elements[i].data + si->elements[i].stride * SkipnStrides
+                    + state->streams[si->elements[i].stream_idx].offset;
 
-            send_attribute(This, si->elements[i].format_desc->format, i, ptr);
+            send_attribute(gl_info, si->elements[i].format->id, i, ptr);
         }
         SkipnStrides++;
     }
@@ -476,17 +468,16 @@ static void drawStridedSlowVs(IWineD3DDevice *iface, const struct wined3d_stream
 }
 
 /* GL locking is done by the caller */
-static inline void drawStridedInstanced(IWineD3DDevice *iface, const struct wined3d_stream_info *si,
-        UINT numberOfVertices, GLenum glPrimitiveType, const void *idxData, UINT idxSize,
-        UINT startIdx)
+static void drawStridedInstanced(const struct wined3d_gl_info *gl_info, const struct wined3d_state *state,
+        const struct wined3d_stream_info *si, UINT numberOfVertices, GLenum glPrimitiveType,
+        const void *idxData, UINT idxSize, UINT startIdx)
 {
     UINT numInstances = 0, i;
     int numInstancedAttribs = 0, j;
     UINT instancedData[sizeof(si->elements) / sizeof(*si->elements) /* 16 */];
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
-    IWineD3DStateBlockImpl *stateblock = This->stateBlock;
 
-    if (idxSize == 0) {
+    if (!idxSize)
+    {
         /* This is a nasty thing. MSDN says no hardware supports that and apps have to use software vertex processing.
          * We don't support this for now
          *
@@ -497,19 +488,19 @@ static inline void drawStridedInstanced(IWineD3DDevice *iface, const struct wine
         return;
     }
 
-    TRACE("(%p) : glElements(%x, %d, ...)\n", This, glPrimitiveType, numberOfVertices);
-
     /* First, figure out how many instances we have to draw */
-    for(i = 0; i < MAX_STREAMS; i++) {
+    for (i = 0; i < MAX_STREAMS; ++i)
+    {
         /* Look at the streams and take the first one which matches */
-        if(((stateblock->streamFlags[i] & WINED3DSTREAMSOURCE_INSTANCEDATA) || (stateblock->streamFlags[i] & WINED3DSTREAMSOURCE_INDEXEDDATA)) && stateblock->streamSource[i]) {
-            /* D3D9 could set streamFreq 0 with (INSTANCEDATA or INDEXEDDATA) and then it is handled as 1. See d3d9/tests/visual.c-> stream_test() */
-            if(stateblock->streamFreq[i] == 0){
-                numInstances = 1;
-            } else {
-                numInstances = stateblock->streamFreq[i]; /* use the specified number of instances from the first matched stream. See d3d9/tests/visual.c-> stream_test() */
-            }
-            break; /* break, because only the first suitable value is interesting */
+        if (state->streams[i].buffer
+                && ((state->streams[i].flags & WINED3DSTREAMSOURCE_INSTANCEDATA)
+                || (state->streams[i].flags & WINED3DSTREAMSOURCE_INDEXEDDATA)))
+        {
+            /* Use the specified number of instances from the first matched
+             * stream. A streamFreq of 0 (with INSTANCEDATA or INDEXEDDATA)
+             * is handled as 1. See d3d9/tests/visual.c-> stream_test(). */
+            numInstances = state->streams[i].frequency ? state->streams[i].frequency : 1;
+            break;
         }
     }
 
@@ -517,7 +508,7 @@ static inline void drawStridedInstanced(IWineD3DDevice *iface, const struct wine
     {
         if (!(si->use_map & (1 << i))) continue;
 
-        if (stateblock->streamFlags[si->elements[i].stream_idx] & WINED3DSTREAMSOURCE_INSTANCEDATA)
+        if (state->streams[si->elements[i].stream_idx].flags & WINED3DSTREAMSOURCE_INSTANCEDATA)
         {
             instancedData[numInstancedAttribs] = i;
             numInstancedAttribs++;
@@ -528,17 +519,16 @@ static inline void drawStridedInstanced(IWineD3DDevice *iface, const struct wine
     for(i = 0; i < numInstances; i++) {
         /* Specify the instanced attributes using immediate mode calls */
         for(j = 0; j < numInstancedAttribs; j++) {
-            const BYTE *ptr = si->elements[instancedData[j]].data +
-                        si->elements[instancedData[j]].stride * i +
-                        stateblock->streamOffset[si->elements[instancedData[j]].stream_idx];
+            const BYTE *ptr = si->elements[instancedData[j]].data
+                    + si->elements[instancedData[j]].stride * i
+                    + state->streams[si->elements[instancedData[j]].stream_idx].offset;
             if (si->elements[instancedData[j]].buffer_object)
             {
-                struct wined3d_buffer *vb =
-                        (struct wined3d_buffer *)stateblock->streamSource[si->elements[instancedData[j]].stream_idx];
-                ptr += (ULONG_PTR)buffer_get_sysmem(vb, &This->adapter->gl_info);
+                struct wined3d_buffer *vb = state->streams[si->elements[instancedData[j]].stream_idx].buffer;
+                ptr += (ULONG_PTR)buffer_get_sysmem(vb, gl_info);
             }
 
-            send_attribute(This, si->elements[instancedData[j]].format_desc->format, instancedData[j], ptr);
+            send_attribute(gl_info, si->elements[instancedData[j]].format->id, instancedData[j], ptr);
         }
 
         glDrawElements(glPrimitiveType, numberOfVertices, idxSize == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT,
@@ -547,8 +537,8 @@ static inline void drawStridedInstanced(IWineD3DDevice *iface, const struct wine
     }
 }
 
-static inline void remove_vbos(IWineD3DDeviceImpl *This, const struct wined3d_gl_info *gl_info,
-        struct wined3d_stream_info *s)
+static void remove_vbos(const struct wined3d_gl_info *gl_info,
+        const struct wined3d_state *state, struct wined3d_stream_info *s)
 {
     unsigned int i;
 
@@ -561,7 +551,7 @@ static inline void remove_vbos(IWineD3DDeviceImpl *This, const struct wined3d_gl
         e = &s->elements[i];
         if (e->buffer_object)
         {
-            struct wined3d_buffer *vb = (struct wined3d_buffer *)This->stateBlock->streamSource[e->stream_idx];
+            struct wined3d_buffer *vb = state->streams[e->stream_idx].buffer;
             e->buffer_object = 0;
             e->data = (BYTE *)((ULONG_PTR)e->data + (ULONG_PTR)buffer_get_sysmem(vb, gl_info));
         }
@@ -573,21 +563,22 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
 {
 
     IWineD3DDeviceImpl           *This = (IWineD3DDeviceImpl *)iface;
+    const struct wined3d_state *state = &This->stateBlock->state;
     struct wined3d_context *context;
     unsigned int i;
 
     if (!index_count) return;
 
-    if (This->stateBlock->renderState[WINED3DRS_COLORWRITEENABLE])
+    if (state->render_states[WINED3DRS_COLORWRITEENABLE])
     {
         /* Invalidate the back buffer memory so LockRect will read it the next time */
         for (i = 0; i < This->adapter->gl_info.limits.buffers; ++i)
         {
-            IWineD3DSurface *target = (IWineD3DSurface *)This->render_targets[i];
+            IWineD3DSurfaceImpl *target = This->render_targets[i];
             if (target)
             {
-                IWineD3DSurface_LoadLocation(target, SFLAG_INDRAWABLE, NULL);
-                IWineD3DSurface_ModifyLocation(target, SFLAG_INDRAWABLE, TRUE);
+                surface_load_location(target, SFLAG_INDRAWABLE, NULL);
+                surface_modify_location(target, SFLAG_INDRAWABLE, TRUE);
             }
         }
     }
@@ -613,8 +604,7 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
          * depthstencil for D3DCMP_NEVER and D3DCMP_ALWAYS as well. Also note
          * that we never copy the stencil data.*/
         DWORD location = context->render_offscreen ? SFLAG_DS_OFFSCREEN : SFLAG_DS_ONSCREEN;
-        if (This->stateBlock->renderState[WINED3DRS_ZWRITEENABLE]
-                || This->stateBlock->renderState[WINED3DRS_ZENABLE])
+        if (state->render_states[WINED3DRS_ZWRITEENABLE] || state->render_states[WINED3DRS_ZENABLE])
         {
             RECT current_rect, draw_rect, r;
 
@@ -634,28 +624,37 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
             if (!EqualRect(&r, &draw_rect))
                 surface_load_ds_location(This->depth_stencil, context, location);
 
-            if (This->stateBlock->renderState[WINED3DRS_ZWRITEENABLE])
+            if (state->render_states[WINED3DRS_ZWRITEENABLE])
             {
                 surface_modify_ds_location(This->depth_stencil, location,
                         This->depth_stencil->ds_current_size.cx,
                         This->depth_stencil->ds_current_size.cy);
-                IWineD3DSurface_ModifyLocation((IWineD3DSurface *)This->depth_stencil, SFLAG_INDRAWABLE, TRUE);
+                surface_modify_location(This->depth_stencil, SFLAG_INDRAWABLE, TRUE);
             }
         }
     }
 
+    if ((!context->gl_info->supported[WINED3D_GL_VERSION_2_0]
+            || (!glPointParameteri && !context->gl_info->supported[NV_POINT_SPRITE]))
+            && context->render_offscreen
+            && state->render_states[WINED3DRS_POINTSPRITEENABLE]
+            && state->gl_primitive_type == GL_POINTS)
+    {
+        FIXME("Point sprite coordinate origin switching not supported.\n");
+    }
+
     /* Ok, we will be updating the screen from here onwards so grab the lock */
     ENTER_GL();
     {
-        GLenum glPrimType = This->stateBlock->gl_primitive_type;
+        GLenum glPrimType = state->gl_primitive_type;
         BOOL emulation = FALSE;
         const struct wined3d_stream_info *stream_info = &This->strided_streams;
         struct wined3d_stream_info stridedlcl;
 
-        if (!use_vs(This->stateBlock))
+        if (!use_vs(state))
         {
             if (!This->strided_streams.position_transformed && context->num_untracked_materials
-                    && This->stateBlock->renderState[WINED3DRS_LIGHTING])
+                    && state->render_states[WINED3DRS_LIGHTING])
             {
                 static BOOL warned;
                 if (!warned) {
@@ -666,7 +665,7 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
                 }
                 emulation = TRUE;
             }
-            else if (context->fog_coord && This->stateBlock->renderState[WINED3DRS_FOGENABLE])
+            else if (context->fog_coord && state->render_states[WINED3DRS_FOGENABLE])
             {
                 /* Either write a pipeline replacement shader or convert the specular alpha from unsigned byte
                  * to a float in the vertex buffer
@@ -684,13 +683,14 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
             if(emulation) {
                 stream_info = &stridedlcl;
                 memcpy(&stridedlcl, &This->strided_streams, sizeof(stridedlcl));
-                remove_vbos(This, context->gl_info, &stridedlcl);
+                remove_vbos(context->gl_info, state, &stridedlcl);
             }
         }
 
-        if (This->useDrawStridedSlow || emulation) {
+        if (This->useDrawStridedSlow || emulation)
+        {
             /* Immediate mode drawing */
-            if (use_vs(This->stateBlock))
+            if (use_vs(state))
             {
                 static BOOL warned;
                 if (!warned) {
@@ -699,17 +699,24 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
                 } else {
                     TRACE("Using immediate mode with vertex shaders for half float emulation\n");
                 }
-                drawStridedSlowVs(iface, stream_info, index_count, glPrimType, idxData, idxSize, StartIdx);
-            } else {
+                drawStridedSlowVs(context->gl_info, state, stream_info,
+                        index_count, glPrimType, idxData, idxSize, StartIdx);
+            }
+            else
+            {
                 drawStridedSlow(iface, context, stream_info, index_count,
                         glPrimType, idxData, idxSize, StartIdx);
             }
-        } else if(This->instancedDraw) {
+        }
+        else if (This->instancedDraw)
+        {
             /* Instancing emulation with mixing immediate mode and arrays */
-            drawStridedInstanced(iface, &This->strided_streams, index_count,
-                    glPrimType, idxData, idxSize, StartIdx);
-        } else {
-            drawStridedFast(iface, glPrimType, index_count, idxSize, idxData, StartIdx);
+            drawStridedInstanced(context->gl_info, state, stream_info,
+                    index_count, glPrimType, idxData, idxSize, StartIdx);
+        }
+        else
+        {
+            drawStridedFast(glPrimType, index_count, idxSize, idxData, StartIdx);
         }
     }
 
@@ -727,46 +734,6 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
 
     TRACE("Done all gl drawing\n");
 
-    /* Diagnostics */
-#ifdef SHOW_FRAME_MAKEUP
-    {
-        static LONG primCounter = 0;
-        /* NOTE: set primCounter to the value reported by drawprim
-           before you want to to write frame makeup to /tmp */
-        if (primCounter >= 0) {
-            WINED3DLOCKED_RECT r;
-            char buffer[80];
-            IWineD3DSurface_LockRect(This->render_targets[0], &r, NULL, WINED3DLOCK_READONLY);
-            sprintf(buffer, "/tmp/backbuffer_%d.tga", primCounter);
-            TRACE("Saving screenshot %s\n", buffer);
-            IWineD3DSurface_SaveSnapshot(This->render_targets[0], buffer);
-            IWineD3DSurface_UnlockRect(This->render_targets[0]);
-
-#ifdef SHOW_TEXTURE_MAKEUP
-           {
-            IWineD3DSurface *pSur;
-            int textureNo;
-            for (textureNo = 0; textureNo < MAX_COMBINED_SAMPLERS; ++textureNo) {
-                if (This->stateBlock->textures[textureNo] != NULL) {
-                    sprintf(buffer, "/tmp/texture_%p_%d_%d.tga", This->stateBlock->textures[textureNo], primCounter, textureNo);
-                    TRACE("Saving texture %s\n", buffer);
-                    if (IWineD3DBaseTexture_GetType(This->stateBlock->textures[textureNo]) == WINED3DRTYPE_TEXTURE) {
-                            IWineD3DTexture_GetSurfaceLevel(This->stateBlock->textures[textureNo], 0, &pSur);
-                            IWineD3DSurface_SaveSnapshot(pSur, buffer);
-                            IWineD3DSurface_Release(pSur);
-                    } else  {
-                        FIXME("base Texture isn't of type texture %d\n", IWineD3DBaseTexture_GetType(This->stateBlock->textures[textureNo]));
-                    }
-                }
-            }
-           }
-#endif
-        }
-        TRACE("drawprim #%d\n", primCounter);
-        ++primCounter;
-    }
-#endif
-
     /* Control goes back to the device, stateblock values may change again */
     This->isInDraw = FALSE;
 }
@@ -774,7 +741,7 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
 static void normalize_normal(float *n) {
     float length = n[0] * n[0] + n[1] * n[1] + n[2] * n[2];
     if (length == 0.0f) return;
-    length = sqrt(length);
+    length = sqrtf(length);
     n[0] = n[0] / length;
     n[1] = n[1] / length;
     n[2] = n[2] / length;
@@ -829,8 +796,7 @@ HRESULT tesselate_rectpatch(IWineD3DDeviceImpl *This,
     e = &stream_info.elements[WINED3D_FFP_POSITION];
     if (e->buffer_object)
     {
-        struct wined3d_buffer *vb;
-        vb = (struct wined3d_buffer *)This->stateBlock->streamSource[e->stream_idx];
+        struct wined3d_buffer *vb = This->stateBlock->state.streams[e->stream_idx].buffer;
         e->data = (BYTE *)((ULONG_PTR)e->data + (ULONG_PTR)buffer_get_sysmem(vb, context->gl_info));
     }
     vtxStride = e->stride;
@@ -859,9 +825,9 @@ HRESULT tesselate_rectpatch(IWineD3DDeviceImpl *This,
     for(j = 0; j < info->Height; j++) {
         for(i = 0; i < info->Width; i++) {
             const float *v = (const float *)(data + vtxStride * i + vtxStride * info->Stride * j);
-            if(fabs(v[0]) > max_x) max_x = fabs(v[0]);
-            if(fabs(v[1]) > max_y) max_y = fabs(v[1]);
-            if(fabs(v[2]) > max_z) max_z = fabs(v[2]);
+            if(fabs(v[0]) > max_x) max_x = fabsf(v[0]);
+            if(fabs(v[1]) > max_y) max_y = fabsf(v[1]);
+            if(fabs(v[2]) > max_z) max_z = fabsf(v[2]);
             if(v[2] < neg_z) neg_z = v[2];
         }
     }
index 056e9ad..0b5bb36 100644 (file)
@@ -203,10 +203,13 @@ static void print_glsl_info_log(const struct wined3d_gl_info *gl_info, GLhandleA
         "Fragment shader was successfully compiled to run on hardware.\n",  /* fglrx, with \n */
         "Fragment shader was successfully compiled to run on hardware.",    /* fglrx, no \n   */
         "Fragment shader(s) linked, vertex shader(s) linked. \n ",          /* fglrx, with \n */
+        "Fragment shader(s) linked, vertex shader(s) linked. \n",           /* fglrx, with \n */
         "Fragment shader(s) linked, vertex shader(s) linked.",              /* fglrx, no \n   */
         "Vertex shader(s) linked, no fragment shader(s) defined. \n ",      /* fglrx, with \n */
+        "Vertex shader(s) linked, no fragment shader(s) defined. \n",       /* fglrx, with \n */
         "Vertex shader(s) linked, no fragment shader(s) defined.",          /* fglrx, no \n   */
         "Fragment shader(s) linked, no vertex shader(s) defined. \n ",      /* fglrx, with \n */
+        "Fragment shader(s) linked, no vertex shader(s) defined. \n",       /* fglrx, with \n */
         "Fragment shader(s) linked, no vertex shader(s) defined.",          /* fglrx, no \n   */
     };
 
@@ -229,8 +232,10 @@ static void print_glsl_info_log(const struct wined3d_gl_info *gl_info, GLhandleA
         GL_EXTCALL(glGetInfoLogARB(obj, infologLength, NULL, infoLog));
         is_spam = FALSE;
 
-        for(i = 0; i < sizeof(spam) / sizeof(spam[0]); i++) {
-            if(strcmp(infoLog, spam[i]) == 0) {
+        for (i = 0; i < sizeof(spam) / sizeof(*spam); ++i)
+        {
+            if (!strcmp(infoLog, spam[i]))
+            {
                 is_spam = TRUE;
                 break;
             }
@@ -251,6 +256,17 @@ static void print_glsl_info_log(const struct wined3d_gl_info *gl_info, GLhandleA
     }
 }
 
+/* GL locking is done by the caller. */
+static void shader_glsl_compile(const struct wined3d_gl_info *gl_info, GLhandleARB shader, const char *src)
+{
+    TRACE("Compiling shader object %u.\n", shader);
+    GL_EXTCALL(glShaderSourceARB(shader, 1, &src, NULL));
+    checkGLcall("glShaderSourceARB");
+    GL_EXTCALL(glCompileShaderARB(shader));
+    checkGLcall("glCompileShaderARB");
+    print_glsl_info_log(gl_info, shader);
+}
+
 /* GL locking is done by the caller. */
 static void shader_glsl_dump_program_source(const struct wined3d_gl_info *gl_info, GLhandleARB program)
 {
@@ -692,11 +708,12 @@ static void shader_glsl_load_np2fixup_constants(
 
         for (i = 0; fixup; fixup >>= 1, ++i) {
             const unsigned char idx = prog->np2Fixup_info->idx[i];
-            const IWineD3DBaseTextureImpl* const tex = (const IWineD3DBaseTextureImpl*) stateBlock->textures[i];
-            GLfloattex_dim = &np2fixup_constants[(idx >> 1) * 4];
+            const IWineD3DBaseTextureImpl *tex = stateBlock->state.textures[i];
+            GLfloat *tex_dim = &np2fixup_constants[(idx >> 1) * 4];
 
-            if (!tex) {
-                FIXME("Nonexistent texture is flagged for NP2 texcoord fixup\n");
+            if (!tex)
+            {
+                ERR("Nonexistent texture is flagged for NP2 texcoord fixup.\n");
                 continue;
             }
 
@@ -735,19 +752,20 @@ static void shader_glsl_load_constants(const struct wined3d_context *context,
     programId = prog->programId;
     constant_version = prog->constant_version;
 
-    if (useVertexShader) {
-        IWineD3DBaseShaderImpl* vshader = (IWineD3DBaseShaderImpl*) stateBlock->vertexShader;
+    if (useVertexShader)
+    {
+        IWineD3DBaseShaderImpl *vshader = (IWineD3DBaseShaderImpl *)stateBlock->state.vertex_shader;
 
         /* Load DirectX 9 float constants/uniforms for vertex shader */
-        shader_glsl_load_constantsF(vshader, gl_info, stateBlock->vertexShaderConstantF,
+        shader_glsl_load_constantsF(vshader, gl_info, stateBlock->state.vs_consts_f,
                 prog->vuniformF_locations, &priv->vconst_heap, priv->stack, constant_version);
 
         /* Load DirectX 9 integer constants/uniforms for vertex shader */
-        shader_glsl_load_constantsI(vshader, gl_info, prog->vuniformI_locations, stateBlock->vertexShaderConstantI,
+        shader_glsl_load_constantsI(vshader, gl_info, prog->vuniformI_locations, stateBlock->state.vs_consts_i,
                 stateBlock->changed.vertexShaderConstantsI & vshader->baseShader.reg_maps.integer_constants);
 
         /* Load DirectX 9 boolean constants/uniforms for vertex shader */
-        shader_glsl_load_constantsB(vshader, gl_info, programId, stateBlock->vertexShaderConstantB,
+        shader_glsl_load_constantsB(vshader, gl_info, programId, stateBlock->state.vs_consts_b,
                 stateBlock->changed.vertexShaderConstantsB & vshader->baseShader.reg_maps.boolean_constants);
 
         /* Upload the position fixup params */
@@ -755,20 +773,20 @@ static void shader_glsl_load_constants(const struct wined3d_context *context,
         checkGLcall("glUniform4fvARB");
     }
 
-    if (usePixelShader) {
-
-        IWineD3DBaseShaderImpl* pshader = (IWineD3DBaseShaderImpl*) stateBlock->pixelShader;
+    if (usePixelShader)
+    {
+        IWineD3DBaseShaderImpl *pshader = (IWineD3DBaseShaderImpl *)stateBlock->state.pixel_shader;
 
         /* Load DirectX 9 float constants/uniforms for pixel shader */
-        shader_glsl_load_constantsF(pshader, gl_info, stateBlock->pixelShaderConstantF,
+        shader_glsl_load_constantsF(pshader, gl_info, stateBlock->state.ps_consts_f,
                 prog->puniformF_locations, &priv->pconst_heap, priv->stack, constant_version);
 
         /* Load DirectX 9 integer constants/uniforms for pixel shader */
-        shader_glsl_load_constantsI(pshader, gl_info, prog->puniformI_locations, stateBlock->pixelShaderConstantI,
+        shader_glsl_load_constantsI(pshader, gl_info, prog->puniformI_locations, stateBlock->state.ps_consts_i,
                 stateBlock->changed.pixelShaderConstantsI & pshader->baseShader.reg_maps.integer_constants);
 
         /* Load DirectX 9 boolean constants/uniforms for pixel shader */
-        shader_glsl_load_constantsB(pshader, gl_info, programId, stateBlock->pixelShaderConstantB,
+        shader_glsl_load_constantsB(pshader, gl_info, programId, stateBlock->state.ps_consts_b,
                 stateBlock->changed.pixelShaderConstantsB & pshader->baseShader.reg_maps.boolean_constants);
 
         /* Upload the environment bump map matrix if needed. The needsbumpmat member specifies the texture stage to load the matrix from.
@@ -779,16 +797,17 @@ static void shader_glsl_load_constants(const struct wined3d_context *context,
 
             if(prog->bumpenvmat_location[i] == -1) continue;
 
-            data = (const float *)&stateBlock->textureState[i][WINED3DTSS_BUMPENVMAT00];
+            data = (const float *)&stateBlock->state.texture_states[i][WINED3DTSS_BUMPENVMAT00];
             GL_EXTCALL(glUniformMatrix2fvARB(prog->bumpenvmat_location[i], 1, 0, data));
             checkGLcall("glUniformMatrix2fvARB");
 
-            /* texbeml needs the luminance scale and offset too. If texbeml is used, needsbumpmat
-             * is set too, so we can check that in the needsbumpmat check
-             */
-            if(prog->luminancescale_location[i] != -1) {
-                const GLfloat *scale = (const GLfloat *)&stateBlock->textureState[i][WINED3DTSS_BUMPENVLSCALE];
-                const GLfloat *offset = (const GLfloat *)&stateBlock->textureState[i][WINED3DTSS_BUMPENVLOFFSET];
+            /* texbeml needs the luminance scale and offset too. If texbeml
+             * is used, needsbumpmat is set too, so we can check that in the
+             * needsbumpmat check. */
+            if (prog->luminancescale_location[i] != -1)
+            {
+                const GLfloat *scale = (const GLfloat *)&stateBlock->state.texture_states[i][WINED3DTSS_BUMPENVLSCALE];
+                const GLfloat *offset = (const GLfloat *)&stateBlock->state.texture_states[i][WINED3DTSS_BUMPENVLOFFSET];
 
                 GL_EXTCALL(glUniform1fvARB(prog->luminancescale_location[i], 1, scale));
                 checkGLcall("glUniform1fvARB");
@@ -898,6 +917,7 @@ static void shader_generate_glsl_declarations(const struct wined3d_context *cont
 {
     IWineD3DBaseShaderImpl* This = (IWineD3DBaseShaderImpl*) iface;
     IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *) This->baseShader.device;
+    const struct wined3d_state *state = &device->stateBlock->state;
     const struct ps_compile_args *ps_args = ctx_priv->cur_ps_args;
     const struct wined3d_gl_info *gl_info = context->gl_info;
     unsigned int i, extra_constants_needed = 0;
@@ -977,25 +997,13 @@ static void shader_generate_glsl_declarations(const struct wined3d_context *cont
     if (This->baseShader.limits.constant_bool > 0 && This->baseShader.reg_maps.boolean_constants)
         shader_addline(buffer, "uniform bool %cB[%u];\n", prefix, This->baseShader.limits.constant_bool);
 
-    if(!pshader) {
+    if (!pshader)
+    {
         shader_addline(buffer, "uniform vec4 posFixup;\n");
-        /* Predeclaration; This function is added at link time based on the pixel shader.
-         * VS 3.0 shaders have an array OUT[] the shader writes to, earlier versions don't have
-         * that. We know the input to the reorder function at vertex shader compile time, so
-         * we can deal with that. The reorder function for a 1.x and 2.x vertex shader can just
-         * read gl_FrontColor. The output depends on the pixel shader. The reorder function for a
-         * 1.x and 2.x pshader or for fixed function will write gl_FrontColor, and for a 3.0 shader
-         * it will write to the varying array. Here we depend on the shader optimizer on sorting that
-         * out. The nvidia driver only does that if the parameter is inout instead of out, hence the
-         * inout.
-         */
-        if (reg_maps->shader_version.major >= 3)
-        {
-            shader_addline(buffer, "void order_ps_input(in vec4[%u]);\n", MAX_REG_OUTPUT);
-        } else {
-            shader_addline(buffer, "void order_ps_input();\n");
-        }
-    } else {
+        shader_addline(buffer, "void order_ps_input(in vec4[%u]);\n", MAX_REG_OUTPUT);
+    }
+    else
+    {
         for (i = 0, map = reg_maps->bumpmat; map; map >>= 1, ++i)
         {
             if (!(map & 1)) continue;
@@ -1044,6 +1052,8 @@ static void shader_generate_glsl_declarations(const struct wined3d_context *cont
     for (i = 0; i < This->baseShader.limits.sampler; i++) {
         if (reg_maps->sampler_type[i])
         {
+            IWineD3DBaseTextureImpl *texture;
+
             switch (reg_maps->sampler_type[i])
             {
                 case WINED3DSTT_1D:
@@ -1053,20 +1063,17 @@ static void shader_generate_glsl_declarations(const struct wined3d_context *cont
                         shader_addline(buffer, "uniform sampler1D %csampler%u;\n", prefix, i);
                     break;
                 case WINED3DSTT_2D:
+                    texture = state->textures[i];
                     if (pshader && ps_args->shadow & (1 << i))
                     {
-                        if (device->stateBlock->textures[i]
-                                && IWineD3DBaseTexture_GetTextureDimensions(device->stateBlock->textures[i])
-                                == GL_TEXTURE_RECTANGLE_ARB)
+                        if (texture && texture->baseTexture.target == GL_TEXTURE_RECTANGLE_ARB)
                             shader_addline(buffer, "uniform sampler2DRectShadow %csampler%u;\n", prefix, i);
                         else
                             shader_addline(buffer, "uniform sampler2DShadow %csampler%u;\n", prefix, i);
                     }
                     else
                     {
-                        if (device->stateBlock->textures[i]
-                                && IWineD3DBaseTexture_GetTextureDimensions(device->stateBlock->textures[i])
-                                == GL_TEXTURE_RECTANGLE_ARB)
+                        if (texture && texture->baseTexture.target == GL_TEXTURE_RECTANGLE_ARB)
                             shader_addline(buffer, "uniform sampler2DRect %csampler%u;\n", prefix, i);
                         else
                             shader_addline(buffer, "uniform sampler2D %csampler%u;\n", prefix, i);
@@ -1136,7 +1143,7 @@ static void shader_generate_glsl_declarations(const struct wined3d_context *cont
      */
     if (pshader && reg_maps->shader_version.major >= 3)
     {
-        if (use_vs(device->stateBlock))
+        if (use_vs(state))
         {
             shader_addline(buffer, "varying vec4 IN[%u];\n", vec4_varyings(reg_maps->shader_version.major, gl_info));
         } else {
@@ -1188,8 +1195,6 @@ static void shader_generate_glsl_declarations(const struct wined3d_context *cont
         }
     }
 
-    shader_addline(buffer, "const float FLT_MAX = 1e38;\n");
-
     /* Start the main program */
     shader_addline(buffer, "void main() {\n");
     if(pshader && reg_maps->vpos) {
@@ -1298,7 +1303,7 @@ static void shader_glsl_get_register_name(const struct wined3d_shader_register *
         char *register_name, BOOL *is_color, const struct wined3d_shader_instruction *ins)
 {
     /* oPos, oFog and oPts in D3D */
-    static const char * const hwrastout_reg_names[] = { "gl_Position", "gl_FogFragCoord", "gl_PointSize" };
+    static const char * const hwrastout_reg_names[] = {"OUT[10]", "OUT[11].x", "OUT[11].y"};
 
     IWineD3DBaseShaderImpl *This = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
     const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
@@ -1373,7 +1378,7 @@ static void shader_glsl_get_register_name(const struct wined3d_shader_register *
             }
             else
             {
-                if (reg->idx == 0) strcpy(register_name, "gl_Color");
+                if (!reg->idx) strcpy(register_name, "gl_Color");
                 else strcpy(register_name, "gl_SecondaryColor");
                 break;
             }
@@ -1441,18 +1446,17 @@ static void shader_glsl_get_register_name(const struct wined3d_shader_register *
             break;
 
         case WINED3DSPR_ATTROUT:
-            if (reg->idx == 0) sprintf(register_name, "gl_FrontColor");
-            else sprintf(register_name, "gl_FrontSecondaryColor");
+            if (!reg->idx) sprintf(register_name, "OUT[8]");
+            else sprintf(register_name, "OUT[9]");
             break;
 
         case WINED3DSPR_TEXCRDOUT:
             /* Vertex shaders >= 3.0: WINED3DSPR_OUTPUT */
-            if (This->baseShader.reg_maps.shader_version.major >= 3) sprintf(register_name, "OUT[%u]", reg->idx);
-            else sprintf(register_name, "gl_TexCoord[%u]", reg->idx);
+            sprintf(register_name, "OUT[%u]", reg->idx);
             break;
 
         case WINED3DSPR_MISCTYPE:
-            if (reg->idx == 0)
+            if (!reg->idx)
             {
                 /* vPos */
                 sprintf(register_name, "vpos");
@@ -1473,11 +1477,11 @@ static void shader_glsl_get_register_name(const struct wined3d_shader_register *
         case WINED3DSPR_IMMCONST:
             switch (reg->immconst_type)
             {
-                case WINED3D_IMMCONST_FLOAT:
+                case WINED3D_IMMCONST_SCALAR:
                     sprintf(register_name, "%.8e", *(const float *)reg->immconst_data);
                     break;
 
-                case WINED3D_IMMCONST_FLOAT4:
+                case WINED3D_IMMCONST_VEC4:
                     sprintf(register_name, "vec4(%.8e, %.8e, %.8e, %.8e)",
                             *(const float *)&reg->immconst_data[0], *(const float *)&reg->immconst_data[1],
                             *(const float *)&reg->immconst_data[2], *(const float *)&reg->immconst_data[3]);
@@ -1829,7 +1833,7 @@ static void shader_glsl_get_sample_function(const struct wined3d_shader_context
         case WINED3DSTT_CUBE:
             if (shadow)
             {
-                FIXME("Unsupported Cube shadow function.\n ");
+                FIXME("Unsupported Cube shadow function.\n");
                 sample_function->name = "unsupportedCubeShadow";
                 sample_function->coord_mask = 0;
             }
@@ -1862,7 +1866,7 @@ static void shader_glsl_get_sample_function(const struct wined3d_shader_context
         case WINED3DSTT_VOLUME:
             if (shadow)
             {
-                FIXME("Unsupported 3D shadow function.\n ");
+                FIXME("Unsupported 3D shadow function.\n");
                 sample_function->name = "unsupported3DShadow";
                 sample_function->coord_mask = 0;
             }
@@ -2213,10 +2217,15 @@ static void shader_glsl_pow(const struct wined3d_shader_instruction *ins)
     shader_glsl_add_src_param(ins, &ins->src[0], WINED3DSP_WRITEMASK_0, &src0_param);
     shader_glsl_add_src_param(ins, &ins->src[1], WINED3DSP_WRITEMASK_0, &src1_param);
 
-    if (dst_size > 1) {
-        shader_addline(buffer, "vec%d(pow(abs(%s), %s)));\n", dst_size, src0_param.param_str, src1_param.param_str);
-    } else {
-        shader_addline(buffer, "pow(abs(%s), %s));\n", src0_param.param_str, src1_param.param_str);
+    if (dst_size > 1)
+    {
+        shader_addline(buffer, "vec%u(pow(abs(%s), %s)));\n",
+                dst_size, src0_param.param_str, src1_param.param_str);
+    }
+    else
+    {
+        shader_addline(buffer, "pow(abs(%s), %s));\n",
+                src0_param.param_str, src1_param.param_str);
     }
 }
 
@@ -2237,13 +2246,13 @@ static void shader_glsl_log(const struct wined3d_shader_instruction *ins)
 
     if (dst_size > 1)
     {
-        shader_addline(buffer, "vec%d(%s == 0.0 ? -FLT_MAX : log2(abs(%s))));\n",
-                dst_size, src0_param.param_str, src0_param.param_str);
+        shader_addline(buffer, "vec%u(log2(abs(%s))));\n",
+                dst_size, src0_param.param_str);
     }
     else
     {
-        shader_addline(buffer, "%s == 0.0 ? -FLT_MAX : log2(abs(%s)));\n",
-                src0_param.param_str, src0_param.param_str);
+        shader_addline(buffer, "log2(abs(%s)));\n",
+                src0_param.param_str);
     }
 }
 
@@ -2371,13 +2380,13 @@ static void shader_glsl_rcp(const struct wined3d_shader_instruction *ins)
 
     if (mask_size > 1)
     {
-        shader_addline(ins->ctx->buffer, "vec%d(%s == 0.0 ? FLT_MAX : 1.0 / %s));\n",
-                mask_size, src_param.param_str, src_param.param_str);
+        shader_addline(ins->ctx->buffer, "vec%u(1.0 / %s));\n",
+                mask_size, src_param.param_str);
     }
     else
     {
-        shader_addline(ins->ctx->buffer, "%s == 0.0 ? FLT_MAX : 1.0 / %s);\n",
-                src_param.param_str, src_param.param_str);
+        shader_addline(ins->ctx->buffer, "1.0 / %s);\n",
+                src_param.param_str);
     }
 }
 
@@ -2395,13 +2404,13 @@ static void shader_glsl_rsq(const struct wined3d_shader_instruction *ins)
 
     if (mask_size > 1)
     {
-        shader_addline(buffer, "vec%d(%s == 0.0 ? FLT_MAX : inversesqrt(abs(%s))));\n",
-                mask_size, src_param.param_str, src_param.param_str);
+        shader_addline(buffer, "vec%u(inversesqrt(abs(%s))));\n",
+                mask_size, src_param.param_str);
     }
     else
     {
-        shader_addline(buffer, "%s == 0.0 ? FLT_MAX : inversesqrt(abs(%s)));\n",
-                src_param.param_str, src_param.param_str);
+        shader_addline(buffer, "inversesqrt(abs(%s)));\n",
+                src_param.param_str);
     }
 }
 
@@ -3009,6 +3018,7 @@ static void shader_glsl_tex(const struct wined3d_shader_instruction *ins)
     DWORD shader_version = WINED3D_SHADER_VERSION(ins->ctx->reg_maps->shader_version.major,
             ins->ctx->reg_maps->shader_version.minor);
     glsl_sample_function_t sample_function;
+    IWineD3DBaseTextureImpl *texture;
     DWORD sample_flags = 0;
     DWORD sampler_idx;
     DWORD mask = 0, swizzle;
@@ -3017,16 +3027,19 @@ static void shader_glsl_tex(const struct wined3d_shader_instruction *ins)
      * 2.0+: Use provided sampler source. */
     if (shader_version < WINED3D_SHADER_VERSION(2,0)) sampler_idx = ins->dst[0].reg.idx;
     else sampler_idx = ins->src[1].reg.idx;
+    texture = deviceImpl->stateBlock->state.textures[sampler_idx];
 
     if (shader_version < WINED3D_SHADER_VERSION(1,4))
     {
-        DWORD flags = deviceImpl->stateBlock->textureState[sampler_idx][WINED3DTSS_TEXTURETRANSFORMFLAGS];
+        const struct shader_glsl_ctx_priv *priv = ins->ctx->backend_data;
+        DWORD flags = (priv->cur_ps_args->tex_transform >> sampler_idx * WINED3D_PSARGS_TEXTRANSFORM_SHIFT)
+                & WINED3D_PSARGS_TEXTRANSFORM_MASK;
         WINED3DSAMPLER_TEXTURE_TYPE sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
 
         /* Projected cube textures don't make a lot of sense, the resulting coordinates stay the same. */
-        if (flags & WINED3DTTFF_PROJECTED && sampler_type != WINED3DSTT_CUBE) {
+        if (flags & WINED3D_PSARGS_PROJECTED && sampler_type != WINED3DSTT_CUBE) {
             sample_flags |= WINED3D_GLSL_SAMPLE_PROJECTED;
-            switch (flags & ~WINED3DTTFF_PROJECTED) {
+            switch (flags & ~WINED3D_PSARGS_PROJECTED) {
                 case WINED3DTTFF_COUNT1: FIXME("WINED3DTTFF_PROJECTED with WINED3DTTFF_COUNT1?\n"); break;
                 case WINED3DTTFF_COUNT2: mask = WINED3DSP_WRITEMASK_1; break;
                 case WINED3DTTFF_COUNT3: mask = WINED3DSP_WRITEMASK_2; break;
@@ -3055,10 +3068,8 @@ static void shader_glsl_tex(const struct wined3d_shader_instruction *ins)
         }
     }
 
-    if(deviceImpl->stateBlock->textures[sampler_idx] &&
-       IWineD3DBaseTexture_GetTextureDimensions(deviceImpl->stateBlock->textures[sampler_idx]) == GL_TEXTURE_RECTANGLE_ARB) {
+    if (texture && texture->baseTexture.target == GL_TEXTURE_RECTANGLE_ARB)
         sample_flags |= WINED3D_GLSL_SAMPLE_RECT;
-    }
 
     shader_glsl_get_sample_function(ins->ctx, sampler_idx, sample_flags, &sample_function);
     mask |= sample_function.coord_mask;
@@ -3100,18 +3111,19 @@ static void shader_glsl_texldd(const struct wined3d_shader_instruction *ins)
     DWORD sample_flags = WINED3D_GLSL_SAMPLE_GRAD;
     DWORD sampler_idx;
     DWORD swizzle = ins->src[1].swizzle;
+    IWineD3DBaseTextureImpl *texture;
 
     if (!gl_info->supported[ARB_SHADER_TEXTURE_LOD] && !gl_info->supported[EXT_GPU_SHADER4])
     {
         FIXME("texldd used, but not supported by hardware. Falling back to regular tex\n");
-        return shader_glsl_tex(ins);
+        shader_glsl_tex(ins);
+        return;
     }
 
     sampler_idx = ins->src[1].reg.idx;
-    if(deviceImpl->stateBlock->textures[sampler_idx] &&
-       IWineD3DBaseTexture_GetTextureDimensions(deviceImpl->stateBlock->textures[sampler_idx]) == GL_TEXTURE_RECTANGLE_ARB) {
+    texture = deviceImpl->stateBlock->state.textures[sampler_idx];
+    if (texture && texture->baseTexture.target == GL_TEXTURE_RECTANGLE_ARB)
         sample_flags |= WINED3D_GLSL_SAMPLE_RECT;
-    }
 
     shader_glsl_get_sample_function(ins->ctx, sampler_idx, sample_flags, &sample_function);
     shader_glsl_add_src_param(ins, &ins->src[0], sample_function.coord_mask, &coord_param);
@@ -3132,12 +3144,13 @@ static void shader_glsl_texldl(const struct wined3d_shader_instruction *ins)
     DWORD sample_flags = WINED3D_GLSL_SAMPLE_LOD;
     DWORD sampler_idx;
     DWORD swizzle = ins->src[1].swizzle;
+    IWineD3DBaseTextureImpl *texture;
 
     sampler_idx = ins->src[1].reg.idx;
-    if(deviceImpl->stateBlock->textures[sampler_idx] &&
-       IWineD3DBaseTexture_GetTextureDimensions(deviceImpl->stateBlock->textures[sampler_idx]) == GL_TEXTURE_RECTANGLE_ARB) {
+    texture = deviceImpl->stateBlock->state.textures[sampler_idx];
+    if (texture && texture->baseTexture.target == GL_TEXTURE_RECTANGLE_ARB)
         sample_flags |= WINED3D_GLSL_SAMPLE_RECT;
-    }
+
     shader_glsl_get_sample_function(ins->ctx, sampler_idx, sample_flags, &sample_function);
     shader_glsl_add_src_param(ins, &ins->src[0], sample_function.coord_mask, &coord_param);
 
@@ -3456,8 +3469,7 @@ static void shader_glsl_texm3x3vspec(const struct wined3d_shader_instruction *in
  */
 static void shader_glsl_texbem(const struct wined3d_shader_instruction *ins)
 {
-    IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
-    IWineD3DDeviceImpl *deviceImpl = (IWineD3DDeviceImpl *)shader->baseShader.device;
+    const struct shader_glsl_ctx_priv *priv = ins->ctx->backend_data;
     glsl_sample_function_t sample_function;
     glsl_src_param_t coord_param;
     DWORD sampler_idx;
@@ -3466,7 +3478,8 @@ static void shader_glsl_texbem(const struct wined3d_shader_instruction *ins)
     char coord_mask[6];
 
     sampler_idx = ins->dst[0].reg.idx;
-    flags = deviceImpl->stateBlock->textureState[sampler_idx][WINED3DTSS_TEXTURETRANSFORMFLAGS];
+    flags = (priv->cur_ps_args->tex_transform >> sampler_idx * WINED3D_PSARGS_TEXTRANSFORM_SHIFT)
+            & WINED3D_PSARGS_TEXTRANSFORM_MASK;
 
     /* Dependent read, not valid with conditional NP2 */
     shader_glsl_get_sample_function(ins->ctx, sampler_idx, 0, &sample_function);
@@ -3477,10 +3490,10 @@ static void shader_glsl_texbem(const struct wined3d_shader_instruction *ins)
     /* with projective textures, texbem only divides the static texture coord, not the displacement,
          * so we can't let the GL handle this.
          */
-    if (flags & WINED3DTTFF_PROJECTED) {
+    if (flags & WINED3D_PSARGS_PROJECTED) {
         DWORD div_mask=0;
         char coord_div_mask[3];
-        switch (flags & ~WINED3DTTFF_PROJECTED) {
+        switch (flags & ~WINED3D_PSARGS_PROJECTED) {
             case WINED3DTTFF_COUNT1: FIXME("WINED3DTTFF_PROJECTED with WINED3DTTFF_COUNT1?\n"); break;
             case WINED3DTTFF_COUNT2: div_mask = WINED3DSP_WRITEMASK_1; break;
             case WINED3DTTFF_COUNT3: div_mask = WINED3DSP_WRITEMASK_2; break;
@@ -3649,7 +3662,7 @@ static void shader_glsl_input_pack(IWineD3DPixelShader *iface, struct wined3d_sh
         }
         else if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_COLOR))
         {
-            if (semantic_idx == 0)
+            if (!semantic_idx)
                 shader_addline(buffer, "IN[%u]%s = vec4(gl_Color)%s;\n",
                         This->input_reg_map[i], reg_mask, reg_mask);
             else if (semantic_idx == 1)
@@ -3725,37 +3738,28 @@ static void handle_ps3_input(struct wined3d_shader_buffer *buffer, const struct
         const struct wined3d_shader_signature_element *output_signature, const struct shader_reg_maps *reg_maps_out)
 {
     unsigned int i, j;
-    const char *semantic_name_in, *semantic_name_out;
-    UINT semantic_idx_in, semantic_idx_out;
+    const char *semantic_name_in;
+    UINT semantic_idx_in;
     DWORD *set;
     DWORD in_idx;
     unsigned int in_count = vec4_varyings(3, gl_info);
-    char reg_mask[6], reg_mask_out[6];
+    char reg_mask[6];
     char destination[50];
     WORD input_map, output_map;
 
     set = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*set) * (in_count + 2));
 
-    if (!output_signature)
-    {
-        /* Save gl_FrontColor & gl_FrontSecondaryColor before overwriting them. */
-        shader_addline(buffer, "vec4 front_color = gl_FrontColor;\n");
-        shader_addline(buffer, "vec4 front_secondary_color = gl_FrontSecondaryColor;\n");
-    }
-
     input_map = reg_maps_in->input_registers;
     for (i = 0; input_map; input_map >>= 1, ++i)
     {
         if (!(input_map & 1)) continue;
 
         in_idx = map[i];
-        if (in_idx >= (in_count + 2)) {
-            FIXME("More input varyings declared than supported, expect issues\n");
-            continue;
-        }
-        else if (map[i] == ~0U)
+        /* Declared, but not read register */
+        if (in_idx == ~0U) continue;
+        if (in_idx >= (in_count + 2))
         {
-            /* Declared, but not read register */
+            FIXME("More input varyings declared than supported, expect issues.\n");
             continue;
         }
 
@@ -3769,113 +3773,49 @@ static void handle_ps3_input(struct wined3d_shader_buffer *buffer, const struct
 
         semantic_name_in = input_signature[i].semantic_name;
         semantic_idx_in = input_signature[i].semantic_idx;
-        set[map[i]] = input_signature[i].mask;
-        shader_glsl_write_mask_to_str(input_signature[i].mask, reg_mask);
+        set[in_idx] = ~0U;
 
-        if (!output_signature)
+        output_map = reg_maps_out->output_registers;
+        for (j = 0; output_map; output_map >>= 1, ++j)
         {
-            if (shader_match_semantic(semantic_name_in, WINED3DDECLUSAGE_COLOR))
-            {
-                if (semantic_idx_in == 0)
-                    shader_addline(buffer, "%s%s = front_color%s;\n",
-                            destination, reg_mask, reg_mask);
-                else if (semantic_idx_in == 1)
-                    shader_addline(buffer, "%s%s = front_secondary_color%s;\n",
-                            destination, reg_mask, reg_mask);
-                else
-                    shader_addline(buffer, "%s%s = vec4(0.0, 0.0, 0.0, 0.0)%s;\n",
-                            destination, reg_mask, reg_mask);
-            }
-            else if (shader_match_semantic(semantic_name_in, WINED3DDECLUSAGE_TEXCOORD))
-            {
-                if (semantic_idx_in < 8)
-                {
-                    shader_addline(buffer, "%s%s = gl_TexCoord[%u]%s;\n",
-                            destination, reg_mask, semantic_idx_in, reg_mask);
-                }
-                else
-                {
-                    shader_addline(buffer, "%s%s = vec4(0.0, 0.0, 0.0, 0.0)%s;\n",
-                            destination, reg_mask, reg_mask);
-                }
-            }
-            else if (shader_match_semantic(semantic_name_in, WINED3DDECLUSAGE_FOG))
-            {
-                shader_addline(buffer, "%s%s = vec4(gl_FogFragCoord, 0.0, 0.0, 0.0)%s;\n",
-                        destination, reg_mask, reg_mask);
-            }
-            else
-            {
-                shader_addline(buffer, "%s%s = vec4(0.0, 0.0, 0.0, 0.0)%s;\n",
-                        destination, reg_mask, reg_mask);
-            }
-        } else {
-            BOOL found = FALSE;
+            DWORD mask;
 
-            output_map = reg_maps_out->output_registers;
-            for (j = 0; output_map; output_map >>= 1, ++j)
-            {
-                if (!(output_map & 1)) continue;
+            if (!(output_map & 1)
+                    || semantic_idx_in != output_signature[j].semantic_idx
+                    || strcmp(semantic_name_in, output_signature[j].semantic_name)
+                    || !(mask = input_signature[i].mask & output_signature[j].mask))
+                continue;
 
-                semantic_name_out = output_signature[j].semantic_name;
-                semantic_idx_out = output_signature[j].semantic_idx;
-                shader_glsl_write_mask_to_str(output_signature[j].mask, reg_mask_out);
+            set[in_idx] = mask;
+            shader_glsl_write_mask_to_str(mask, reg_mask);
 
-                if (semantic_idx_in == semantic_idx_out
-                        && !strcmp(semantic_name_in, semantic_name_out))
-                {
-                    shader_addline(buffer, "%s%s = OUT[%u]%s;\n",
-                            destination, reg_mask, j, reg_mask);
-                    found = TRUE;
-                }
-            }
-            if(!found) {
-                shader_addline(buffer, "%s%s = vec4(0.0, 0.0, 0.0, 0.0)%s;\n",
-                               destination, reg_mask, reg_mask);
-            }
+            shader_addline(buffer, "%s%s = clamp(OUT[%u]%s, -FLT_MAX, FLT_MAX);\n",
+                    destination, reg_mask, j, reg_mask);
         }
     }
 
-    /* This is solely to make the compiler / linker happy and avoid warning about undefined
-     * varyings. It shouldn't result in any real code executed on the GPU, since all read
-     * input varyings are assigned above, if the optimizer works properly.
-     */
-    for(i = 0; i < in_count + 2; i++) {
-        if (set[i] && set[i] != WINED3DSP_WRITEMASK_ALL)
-        {
-            unsigned int size = 0;
-            memset(reg_mask, 0, sizeof(reg_mask));
-            if(!(set[i] & WINED3DSP_WRITEMASK_0)) {
-                reg_mask[size] = 'x';
-                size++;
-            }
-            if(!(set[i] & WINED3DSP_WRITEMASK_1)) {
-                reg_mask[size] = 'y';
-                size++;
-            }
-            if(!(set[i] & WINED3DSP_WRITEMASK_2)) {
-                reg_mask[size] = 'z';
-                size++;
-            }
-            if(!(set[i] & WINED3DSP_WRITEMASK_3)) {
-                reg_mask[size] = 'w';
-                size++;
-            }
+    for (i = 0; i < in_count + 2; ++i)
+    {
+        unsigned int size;
 
-            if (i == in_count) {
-                sprintf(destination, "gl_FrontColor");
-            } else if (i == in_count + 1) {
-                sprintf(destination, "gl_FrontSecondaryColor");
-            } else {
-                sprintf(destination, "IN[%u]", i);
-            }
+        if (!set[i] || set[i] == WINED3DSP_WRITEMASK_ALL)
+            continue;
 
-            if (size == 1) {
-                shader_addline(buffer, "%s.%s = 0.0;\n", destination, reg_mask);
-            } else {
-                shader_addline(buffer, "%s.%s = vec%u(0.0);\n", destination, reg_mask, size);
-            }
-        }
+        if (set[i] == ~0U) set[i] = 0;
+
+        size = 0;
+        if (!(set[i] & WINED3DSP_WRITEMASK_0)) reg_mask[size++] = 'x';
+        if (!(set[i] & WINED3DSP_WRITEMASK_1)) reg_mask[size++] = 'y';
+        if (!(set[i] & WINED3DSP_WRITEMASK_2)) reg_mask[size++] = 'z';
+        if (!(set[i] & WINED3DSP_WRITEMASK_3)) reg_mask[size++] = 'w';
+        reg_mask[size] = '\0';
+
+        if (i == in_count) sprintf(destination, "gl_FrontColor");
+        else if (i == in_count + 1) sprintf(destination, "gl_FrontSecondaryColor");
+        else sprintf(destination, "IN[%u]", i);
+
+        if (size == 1) shader_addline(buffer, "%s.%s = 0.0;\n", destination, reg_mask);
+        else shader_addline(buffer, "%s.%s = vec%u(0.0);\n", destination, reg_mask, size);
     }
 
     HeapFree(GetProcessHeap(), 0, set);
@@ -3888,45 +3828,23 @@ static GLhandleARB generate_param_reorder_function(struct wined3d_shader_buffer
     GLhandleARB ret = 0;
     IWineD3DVertexShaderImpl *vs = (IWineD3DVertexShaderImpl *) vertexshader;
     IWineD3DPixelShaderImpl *ps = (IWineD3DPixelShaderImpl *) pixelshader;
-    IWineD3DDeviceImpl *device;
-    DWORD vs_major = vs->baseShader.reg_maps.shader_version.major;
     DWORD ps_major = ps ? ps->baseShader.reg_maps.shader_version.major : 0;
     unsigned int i;
     const char *semantic_name;
     UINT semantic_idx;
     char reg_mask[6];
-    const struct wined3d_shader_signature_element *output_signature;
+    const struct wined3d_shader_signature_element *output_signature = vs->baseShader.output_signature;
+    WORD map = vs->baseShader.reg_maps.output_registers;
 
     shader_buffer_clear(buffer);
 
     shader_addline(buffer, "#version 120\n");
+    shader_addline(buffer, "const float FLT_MAX = 1e38;\n");
 
-    if(vs_major < 3 && ps_major < 3) {
-        /* That one is easy: The vertex shader writes to the builtin varyings, the pixel shader reads from them.
-         * Take care about the texcoord .w fixup though if we're using the fixed function fragment pipeline
-         */
-        device = (IWineD3DDeviceImpl *) vs->baseShader.device;
-        if ((gl_info->quirks & WINED3D_QUIRK_SET_TEXCOORD_W)
-                && ps_major == 0 && vs_major > 0 && !device->frag_pipe->ffp_proj_control)
-        {
-            shader_addline(buffer, "void order_ps_input() {\n");
-            for(i = 0; i < min(8, MAX_REG_TEXCRD); i++) {
-                if(vs->baseShader.reg_maps.texcoord_mask[i] != 0 &&
-                   vs->baseShader.reg_maps.texcoord_mask[i] != WINED3DSP_WRITEMASK_ALL) {
-                    shader_addline(buffer, "gl_TexCoord[%u].w = 1.0;\n", i);
-                }
-            }
-            shader_addline(buffer, "}\n");
-        } else {
-            shader_addline(buffer, "void order_ps_input() { /* do nothing */ }\n");
-        }
-    } else if(ps_major < 3 && vs_major >= 3) {
-        WORD map = vs->baseShader.reg_maps.output_registers;
-
-        /* The vertex shader writes to its own varyings, the pixel shader needs them in the builtin ones */
-        output_signature = vs->baseShader.output_signature;
-
+    if (ps_major < 3)
+    {
         shader_addline(buffer, "void order_ps_input(in vec4 OUT[%u]) {\n", MAX_REG_OUTPUT);
+
         for (i = 0; map; map >>= 1, ++i)
         {
             DWORD write_mask;
@@ -3940,14 +3858,17 @@ static GLhandleARB generate_param_reorder_function(struct wined3d_shader_buffer
 
             if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_COLOR))
             {
-                if (semantic_idx == 0)
-                    shader_addline(buffer, "gl_FrontColor%s = OUT[%u]%s;\n", reg_mask, i, reg_mask);
+                if (!semantic_idx)
+                    shader_addline(buffer, "gl_FrontColor%s = clamp(OUT[%u]%s, -FLT_MAX, FLT_MAX);\n",
+                            reg_mask, i, reg_mask);
                 else if (semantic_idx == 1)
-                    shader_addline(buffer, "gl_FrontSecondaryColor%s = OUT[%u]%s;\n", reg_mask, i, reg_mask);
+                    shader_addline(buffer, "gl_FrontSecondaryColor%s = clamp(OUT[%u]%s, -FLT_MAX, FLT_MAX);\n",
+                            reg_mask, i, reg_mask);
             }
             else if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_POSITION))
             {
-                shader_addline(buffer, "gl_Position%s = OUT[%u]%s;\n", reg_mask, i, reg_mask);
+                shader_addline(buffer, "gl_Position%s = clamp(OUT[%u]%s, -FLT_MAX, FLT_MAX);\n",
+                        reg_mask, i, reg_mask);
             }
             else if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_TEXCOORD))
             {
@@ -3956,7 +3877,7 @@ static GLhandleARB generate_param_reorder_function(struct wined3d_shader_buffer
                     if (!(gl_info->quirks & WINED3D_QUIRK_SET_TEXCOORD_W) || ps_major > 0)
                         write_mask |= WINED3DSP_WRITEMASK_3;
 
-                    shader_addline(buffer, "gl_TexCoord[%u]%s = OUT[%u]%s;\n",
+                    shader_addline(buffer, "gl_TexCoord[%u]%s = clamp(OUT[%u]%s, -FLT_MAX, FLT_MAX);\n",
                             semantic_idx, reg_mask, i, reg_mask);
                     if (!(write_mask & WINED3DSP_WRITEMASK_3))
                         shader_addline(buffer, "gl_TexCoord[%u].w = 1.0;\n", semantic_idx);
@@ -3964,20 +3885,18 @@ static GLhandleARB generate_param_reorder_function(struct wined3d_shader_buffer
             }
             else if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_PSIZE))
             {
-                shader_addline(buffer, "gl_PointSize = OUT[%u].x;\n", i);
+                shader_addline(buffer, "gl_PointSize = clamp(OUT[%u].%c, -FLT_MAX, FLT_MAX);\n", i, reg_mask[1]);
             }
             else if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_FOG))
             {
-                shader_addline(buffer, "gl_FogFragCoord = OUT[%u].%c;\n", i, reg_mask[1]);
+                shader_addline(buffer, "gl_FogFragCoord = clamp(OUT[%u].%c, -FLT_MAX, FLT_MAX);\n", i, reg_mask[1]);
             }
         }
         shader_addline(buffer, "}\n");
 
-    } else if(ps_major >= 3 && vs_major >= 3) {
-        WORD map = vs->baseShader.reg_maps.output_registers;
-
-        output_signature = vs->baseShader.output_signature;
-
+    }
+    else
+    {
         /* This one is tricky: a 3.0 pixel shader reads from a 3.0 vertex shader */
         shader_addline(buffer, "varying vec4 IN[%u];\n", vec4_varyings(3, gl_info));
         shader_addline(buffer, "void order_ps_input(in vec4 OUT[%u]) {\n", MAX_REG_OUTPUT);
@@ -3992,11 +3911,12 @@ static GLhandleARB generate_param_reorder_function(struct wined3d_shader_buffer
 
             if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_POSITION))
             {
-                shader_addline(buffer, "gl_Position%s = OUT[%u]%s;\n", reg_mask, i, reg_mask);
+                shader_addline(buffer, "gl_Position%s = clamp(OUT[%u]%s, -FLT_MAX, FLT_MAX);\n",
+                        reg_mask, i, reg_mask);
             }
             else if (shader_match_semantic(semantic_name, WINED3DDECLUSAGE_PSIZE))
             {
-                shader_addline(buffer, "gl_PointSize = OUT[%u].x;\n", i);
+                shader_addline(buffer, "gl_PointSize = clamp(OUT[%u].%c, -FLT_MAX, FLT_MAX);\n", i, reg_mask[1]);
             }
         }
 
@@ -4005,26 +3925,11 @@ static GLhandleARB generate_param_reorder_function(struct wined3d_shader_buffer
                 &ps->baseShader.reg_maps, output_signature, &vs->baseShader.reg_maps);
 
         shader_addline(buffer, "}\n");
-    } else if(ps_major >= 3 && vs_major < 3) {
-        shader_addline(buffer, "varying vec4 IN[%u];\n", vec4_varyings(3, gl_info));
-        shader_addline(buffer, "void order_ps_input() {\n");
-        /* The vertex shader wrote to the builtin varyings. There is no need to figure out position and
-         * point size, but we depend on the optimizers kindness to find out that the pixel shader doesn't
-         * read gl_TexCoord and gl_ColorX, otherwise we'll run out of varyings
-         */
-        handle_ps3_input(buffer, gl_info, ps->input_reg_map, ps->baseShader.input_signature,
-                &ps->baseShader.reg_maps, NULL, NULL);
-        shader_addline(buffer, "}\n");
-    } else {
-        ERR("Unexpected vertex and pixel shader version condition: vs: %d, ps: %d\n", vs_major, ps_major);
     }
 
     ret = GL_EXTCALL(glCreateShaderObjectARB(GL_VERTEX_SHADER_ARB));
     checkGLcall("glCreateShaderObjectARB(GL_VERTEX_SHADER_ARB)");
-    GL_EXTCALL(glShaderSourceARB(ret, 1, (const char**)&buffer->buffer, NULL));
-    checkGLcall("glShaderSourceARB(ret, 1, &buffer->buffer, NULL)");
-    GL_EXTCALL(glCompileShaderARB(ret));
-    checkGLcall("glCompileShaderARB(ret)");
+    shader_glsl_compile(gl_info, ret, buffer->buffer);
 
     return ret;
 }
@@ -4145,9 +4050,7 @@ static GLuint shader_glsl_generate_pshader(const struct wined3d_context *context
     shader_addline(buffer, "}\n");
 
     TRACE("Compiling shader object %u\n", shader_obj);
-    GL_EXTCALL(glShaderSourceARB(shader_obj, 1, (const char**)&buffer->buffer, NULL));
-    GL_EXTCALL(glCompileShaderARB(shader_obj));
-    print_glsl_info_log(gl_info, shader_obj);
+    shader_glsl_compile(gl_info, shader_obj, buffer->buffer);
 
     /* Store the shader object */
     return shader_obj;
@@ -4182,9 +4085,8 @@ static GLuint shader_glsl_generate_vshader(const struct wined3d_context *context
     /* Base Shader Body */
     shader_generate_main((IWineD3DBaseShader*)This, buffer, reg_maps, function, &priv_ctx);
 
-    /* Unpack 3.0 outputs */
-    if (reg_maps->shader_version.major >= 3) shader_addline(buffer, "order_ps_input(OUT);\n");
-    else shader_addline(buffer, "order_ps_input();\n");
+    /* Unpack outputs */
+    shader_addline(buffer, "order_ps_input(OUT);\n");
 
     /* The D3DRS_FOGTABLEMODE render state defines if the shader-generated fog coord is used
      * or if the fragment depth is used. If the fragment depth is used(FOGTABLEMODE != NONE),
@@ -4221,9 +4123,7 @@ static GLuint shader_glsl_generate_vshader(const struct wined3d_context *context
     shader_addline(buffer, "}\n");
 
     TRACE("Compiling shader object %u\n", shader_obj);
-    GL_EXTCALL(glShaderSourceARB(shader_obj, 1, (const char**)&buffer->buffer, NULL));
-    GL_EXTCALL(glCompileShaderARB(shader_obj));
-    print_glsl_info_log(gl_info, shader_obj);
+    shader_glsl_compile(gl_info, shader_obj, buffer->buffer);
 
     return shader_obj;
 }
@@ -4232,6 +4132,7 @@ static GLhandleARB find_glsl_pshader(const struct wined3d_context *context,
         struct wined3d_shader_buffer *buffer, IWineD3DPixelShaderImpl *shader,
         const struct ps_compile_args *args, const struct ps_np2fixup_info **np2fixup_info)
 {
+    struct wined3d_state *state = &((IWineD3DDeviceImpl *)shader->baseShader.device)->stateBlock->state;
     UINT i;
     DWORD new_size;
     struct glsl_ps_compiled_shader *new_array;
@@ -4254,9 +4155,11 @@ static GLhandleARB find_glsl_pshader(const struct wined3d_context *context,
      * so a linear search is more performant than a hashmap or a binary search
      * (cache coherency etc)
      */
-    for(i = 0; i < shader_data->num_gl_shaders; i++) {
-        if(memcmp(&shader_data->gl_shaders[i].args, args, sizeof(*args)) == 0) {
-            if(args->np2_fixup) *np2fixup_info = &shader_data->gl_shaders[i].np2fixup;
+    for (i = 0; i < shader_data->num_gl_shaders; ++i)
+    {
+        if (!memcmp(&shader_data->gl_shaders[i].args, args, sizeof(*args)))
+        {
+            if (args->np2_fixup) *np2fixup_info = &shader_data->gl_shaders[i].np2fixup;
             return shader_data->gl_shaders[i].prgId;
         }
     }
@@ -4286,8 +4189,7 @@ static GLhandleARB find_glsl_pshader(const struct wined3d_context *context,
     memset(&shader_data->gl_shaders[shader_data->num_gl_shaders].np2fixup, 0, sizeof(struct ps_np2fixup_info));
     if (args->np2_fixup) np2fixup = &shader_data->gl_shaders[shader_data->num_gl_shaders].np2fixup;
 
-    pixelshader_update_samplers(&shader->baseShader.reg_maps,
-            ((IWineD3DDeviceImpl *)shader->baseShader.device)->stateBlock->textures);
+    pixelshader_update_samplers(&shader->baseShader.reg_maps, (IWineD3DBaseTexture **)state->textures);
 
     shader_buffer_clear(buffer);
     ret = shader_glsl_generate_pshader(context, buffer, shader, args, np2fixup);
@@ -4379,8 +4281,9 @@ static GLhandleARB find_glsl_vshader(const struct wined3d_context *context,
 static void set_glsl_shader_program(const struct wined3d_context *context,
         IWineD3DDeviceImpl *device, BOOL use_ps, BOOL use_vs)
 {
-    IWineD3DVertexShader *vshader = use_vs ? device->stateBlock->vertexShader : NULL;
-    IWineD3DPixelShader *pshader = use_ps ? device->stateBlock->pixelShader : NULL;
+    const struct wined3d_state *state = &device->stateBlock->state;
+    IWineD3DVertexShader *vshader = use_vs ? (IWineD3DVertexShader *)state->vertex_shader : NULL;
+    IWineD3DPixelShader *pshader = use_ps ? (IWineD3DPixelShader *)state->pixel_shader : NULL;
     const struct wined3d_gl_info *gl_info = context->gl_info;
     struct shader_glsl_priv *priv = device->shader_priv;
     struct glsl_shader_prog_link *entry    = NULL;
@@ -4391,8 +4294,8 @@ static void set_glsl_shader_program(const struct wined3d_context *context,
     struct ps_compile_args ps_compile_args;
     struct vs_compile_args vs_compile_args;
 
-    if (vshader) find_vs_compile_args((IWineD3DVertexShaderImpl *)vshader, device->stateBlock, &vs_compile_args);
-    if (pshader) find_ps_compile_args((IWineD3DPixelShaderImpl *)pshader, device->stateBlock, &ps_compile_args);
+    if (vshader) find_vs_compile_args(state, (IWineD3DVertexShaderImpl *)vshader, &vs_compile_args);
+    if (pshader) find_ps_compile_args(state, (IWineD3DPixelShaderImpl *)pshader, &ps_compile_args);
 
     entry = get_glsl_program_entry(priv, vshader, pshader, &vs_compile_args, &ps_compile_args);
     if (entry) {
@@ -4574,18 +4477,16 @@ static GLhandleARB create_glsl_blt_shader(const struct wined3d_gl_info *gl_info,
     GLhandleARB vshader_id, pshader_id;
     const char *blt_pshader;
 
-    static const char *blt_vshader[] =
-    {
+    static const char *blt_vshader =
         "#version 120\n"
         "void main(void)\n"
         "{\n"
         "    gl_Position = gl_Vertex;\n"
         "    gl_FrontColor = vec4(1.0);\n"
         "    gl_TexCoord[0] = gl_MultiTexCoord0;\n"
-        "}\n"
-    };
+        "}\n";
 
-    static const char *blt_pshaders_full[tex_type_count] =
+    static const char * const blt_pshaders_full[tex_type_count] =
     {
         /* tex_1d */
         NULL,
@@ -4615,7 +4516,7 @@ static GLhandleARB create_glsl_blt_shader(const struct wined3d_gl_info *gl_info,
         "}\n",
     };
 
-    static const char *blt_pshaders_masked[tex_type_count] =
+    static const char * const blt_pshaders_masked[tex_type_count] =
     {
         /* tex_1d */
         NULL,
@@ -4659,12 +4560,10 @@ static GLhandleARB create_glsl_blt_shader(const struct wined3d_gl_info *gl_info,
     }
 
     vshader_id = GL_EXTCALL(glCreateShaderObjectARB(GL_VERTEX_SHADER_ARB));
-    GL_EXTCALL(glShaderSourceARB(vshader_id, 1, blt_vshader, NULL));
-    GL_EXTCALL(glCompileShaderARB(vshader_id));
+    shader_glsl_compile(gl_info, vshader_id, blt_vshader);
 
     pshader_id = GL_EXTCALL(glCreateShaderObjectARB(GL_FRAGMENT_SHADER_ARB));
-    GL_EXTCALL(glShaderSourceARB(pshader_id, 1, &blt_pshader, NULL));
-    GL_EXTCALL(glCompileShaderARB(pshader_id));
+    shader_glsl_compile(gl_info, pshader_id, blt_pshader);
 
     program_id = GL_EXTCALL(glCreateProgramObjectARB());
     GL_EXTCALL(glAttachObjectARB(program_id, vshader_id));
@@ -4785,7 +4684,7 @@ static void shader_glsl_destroy(IWineD3DBaseShader *iface) {
     if(pshader) {
         struct glsl_pshader_private *shader_data;
         shader_data = This->baseShader.backend_data;
-        if(!shader_data || shader_data->num_gl_shaders == 0)
+        if (!shader_data || !shader_data->num_gl_shaders)
         {
             HeapFree(GetProcessHeap(), 0, shader_data);
             This->baseShader.backend_data = NULL;
@@ -4804,7 +4703,7 @@ static void shader_glsl_destroy(IWineD3DBaseShader *iface) {
     } else {
         struct glsl_vshader_private *shader_data;
         shader_data = This->baseShader.backend_data;
-        if(!shader_data || shader_data->num_gl_shaders == 0)
+        if (!shader_data || !shader_data->num_gl_shaders)
         {
             HeapFree(GetProcessHeap(), 0, shader_data);
             This->baseShader.backend_data = NULL;
@@ -5092,6 +4991,7 @@ static const SHADER_HANDLER shader_glsl_instruction_handler_table[WINED3DSIH_TAB
 {
     /* WINED3DSIH_ABS           */ shader_glsl_map2gl,
     /* WINED3DSIH_ADD           */ shader_glsl_arith,
+    /* WINED3DSIH_AND           */ NULL,
     /* WINED3DSIH_BEM           */ shader_glsl_bem,
     /* WINED3DSIH_BREAK         */ shader_glsl_break,
     /* WINED3DSIH_BREAKC        */ shader_glsl_breakc,
@@ -5124,6 +5024,7 @@ static const SHADER_HANDLER shader_glsl_instruction_handler_table[WINED3DSIH_TAB
     /* WINED3DSIH_IF            */ shader_glsl_if,
     /* WINED3DSIH_IFC           */ shader_glsl_ifc,
     /* WINED3DSIH_IGE           */ NULL,
+    /* WINED3DSIH_IMUL          */ NULL,
     /* WINED3DSIH_LABEL         */ shader_glsl_label,
     /* WINED3DSIH_LIT           */ shader_glsl_lit,
     /* WINED3DSIH_LOG           */ shader_glsl_log,
@@ -5141,6 +5042,7 @@ static const SHADER_HANDLER shader_glsl_instruction_handler_table[WINED3DSIH_TAB
     /* WINED3DSIH_MIN           */ shader_glsl_map2gl,
     /* WINED3DSIH_MOV           */ shader_glsl_mov,
     /* WINED3DSIH_MOVA          */ shader_glsl_mov,
+    /* WINED3DSIH_MOVC          */ NULL,
     /* WINED3DSIH_MUL           */ shader_glsl_arith,
     /* WINED3DSIH_NOP           */ NULL,
     /* WINED3DSIH_NRM           */ shader_glsl_nrm,
index 24cba32..00a51f8 100644 (file)
@@ -30,20 +30,23 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d);
 
 /* GL locking for state handlers is done by the caller. */
 
-static void nvts_activate_dimensions(DWORD stage, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void nvts_activate_dimensions(const struct wined3d_state *state, DWORD stage, struct wined3d_context *context)
 {
     BOOL bumpmap = FALSE;
 
-    if(stage > 0 && (stateblock->textureState[stage - 1][WINED3DTSS_COLOROP] == WINED3DTOP_BUMPENVMAPLUMINANCE ||
-                     stateblock->textureState[stage - 1][WINED3DTSS_COLOROP] == WINED3DTOP_BUMPENVMAP)) {
+    if (stage > 0 && (state->texture_states[stage - 1][WINED3DTSS_COLOROP] == WINED3DTOP_BUMPENVMAPLUMINANCE
+            || state->texture_states[stage - 1][WINED3DTSS_COLOROP] == WINED3DTOP_BUMPENVMAP))
+    {
         bumpmap = TRUE;
         context->texShaderBumpMap |= (1 << stage);
     } else {
         context->texShaderBumpMap &= ~(1 << stage);
     }
 
-    if(stateblock->textures[stage]) {
-        switch(IWineD3DBaseTexture_GetTextureDimensions(stateblock->textures[stage])) {
+    if (state->textures[stage])
+    {
+        switch (state->textures[stage]->baseTexture.target)
+        {
             case GL_TEXTURE_2D:
                 glTexEnvi(GL_TEXTURE_SHADER_NV, GL_SHADER_OPERATION_NV, bumpmap ? GL_OFFSET_TEXTURE_2D_NV : GL_TEXTURE_2D);
                 checkGLcall("glTexEnvi(GL_TEXTURE_SHADER_NV, GL_SHADER_OPERATION_NV, ...)");
@@ -128,9 +131,9 @@ static void get_src_and_opr_nvrc(DWORD stage, DWORD arg, BOOL is_alpha, GLenum*
     *input = d3dta_to_combiner_input(arg & WINED3DTA_SELECTMASK, stage, texture_idx);
 }
 
-void set_tex_op_nvrc(IWineD3DDevice *iface, BOOL is_alpha, int stage, WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3, INT texture_idx, DWORD dst) {
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl*)iface;
-    const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
+void set_tex_op_nvrc(const struct wined3d_gl_info *gl_info, const struct wined3d_state *state, BOOL is_alpha,
+        int stage, WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3, INT texture_idx, DWORD dst)
+{
     tex_op_args tex_op_args = {{0}, {0}, {0}};
     GLenum portion = is_alpha ? GL_ALPHA : GL_RGB;
     GLenum target = GL_COMBINER0_NV + stage;
@@ -141,7 +144,8 @@ void set_tex_op_nvrc(IWineD3DDevice *iface, BOOL is_alpha, int stage, WINED3DTEX
 
     /* If a texture stage references an invalid texture unit the stage just
     * passes through the result from the previous stage */
-    if (is_invalid_op(This, stage, op, arg1, arg2, arg3)) {
+    if (is_invalid_op(state, stage, op, arg1, arg2, arg3))
+    {
         arg1 = WINED3DTA_CURRENT;
         op = WINED3DTOP_SELECTARG1;
     }
@@ -452,17 +456,18 @@ void set_tex_op_nvrc(IWineD3DDevice *iface, BOOL is_alpha, int stage, WINED3DTEX
 }
 
 
-static void nvrc_colorop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void nvrc_colorop(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
+    DWORD stage = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
     BOOL tex_used = stateblock->device->fixed_function_usage_map & (1 << stage);
     DWORD mapped_stage = stateblock->device->texUnitMap[stage];
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
 
-    TRACE("Setting color op for stage %d\n", stage);
+    TRACE("Setting color op for stage %u.\n", stage);
 
     /* Using a pixel shader? Don't care for anything here, the shader applying does it */
-    if (use_ps(stateblock)) return;
+    if (use_ps(state)) return;
 
     if (stage != mapped_stage) WARN("Using non 1:1 mapping: %d -> %d!\n", stage, mapped_stage);
 
@@ -477,13 +482,17 @@ static void nvrc_colorop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         checkGLcall("glActiveTextureARB");
     }
 
-    if(stateblock->lowest_disabled_stage > 0) {
+    if (state->lowest_disabled_stage > 0)
+    {
         glEnable(GL_REGISTER_COMBINERS_NV);
-        GL_EXTCALL(glCombinerParameteriNV(GL_NUM_GENERAL_COMBINERS_NV, stateblock->lowest_disabled_stage));
-    } else {
+        GL_EXTCALL(glCombinerParameteriNV(GL_NUM_GENERAL_COMBINERS_NV, state->lowest_disabled_stage));
+    }
+    else
+    {
         glDisable(GL_REGISTER_COMBINERS_NV);
     }
-    if(stage >= stateblock->lowest_disabled_stage) {
+    if (stage >= state->lowest_disabled_stage)
+    {
         TRACE("Stage disabled\n");
         if (mapped_stage != WINED3D_UNMAPPED_STAGE)
         {
@@ -520,56 +529,58 @@ static void nvrc_colorop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         {
             if (gl_info->supported[NV_TEXTURE_SHADER2])
             {
-                nvts_activate_dimensions(stage, stateblock, context);
+                nvts_activate_dimensions(state, stage, context);
             }
             else
             {
-                texture_activate_dimensions(stage, stateblock, context);
+                texture_activate_dimensions(state->textures[stage], gl_info);
             }
         }
     }
 
     /* Set the texture combiners */
-    set_tex_op_nvrc((IWineD3DDevice *)stateblock->device, FALSE, stage,
-                        stateblock->textureState[stage][WINED3DTSS_COLOROP],
-                        stateblock->textureState[stage][WINED3DTSS_COLORARG1],
-                        stateblock->textureState[stage][WINED3DTSS_COLORARG2],
-                        stateblock->textureState[stage][WINED3DTSS_COLORARG0],
-                        mapped_stage,
-                        stateblock->textureState[stage][WINED3DTSS_RESULTARG]);
+    set_tex_op_nvrc(gl_info, state, FALSE, stage,
+            state->texture_states[stage][WINED3DTSS_COLOROP],
+            state->texture_states[stage][WINED3DTSS_COLORARG1],
+            state->texture_states[stage][WINED3DTSS_COLORARG2],
+            state->texture_states[stage][WINED3DTSS_COLORARG0],
+            mapped_stage,
+            state->texture_states[stage][WINED3DTSS_RESULTARG]);
 
     /* In register combiners bump mapping is done in the stage AFTER the one that has the bump map operation set,
      * thus the texture shader may have to be updated
      */
     if (gl_info->supported[NV_TEXTURE_SHADER2])
     {
-        BOOL usesBump = (stateblock->textureState[stage][WINED3DTSS_COLOROP] == WINED3DTOP_BUMPENVMAPLUMINANCE ||
-                            stateblock->textureState[stage][WINED3DTSS_COLOROP] == WINED3DTOP_BUMPENVMAP) ? TRUE : FALSE;
-        BOOL usedBump = (context->texShaderBumpMap & 1 << (stage + 1)) ? TRUE : FALSE;
-        if(usesBump != usedBump) {
+        BOOL usesBump = (state->texture_states[stage][WINED3DTSS_COLOROP] == WINED3DTOP_BUMPENVMAPLUMINANCE
+                || state->texture_states[stage][WINED3DTSS_COLOROP] == WINED3DTOP_BUMPENVMAP);
+        BOOL usedBump = !!(context->texShaderBumpMap & 1 << (stage + 1));
+        if (usesBump != usedBump)
+        {
             GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage + 1));
             checkGLcall("glActiveTextureARB");
-            nvts_activate_dimensions(stage + 1, stateblock, context);
+            nvts_activate_dimensions(state, stage + 1, context);
             GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
             checkGLcall("glActiveTextureARB");
         }
     }
 }
 
-static void nvts_texdim(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void nvts_texdim(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD sampler = state - STATE_SAMPLER(0);
+    DWORD sampler = state_id - STATE_SAMPLER(0);
     DWORD mapped_stage = stateblock->device->texUnitMap[sampler];
+    const struct wined3d_state *state = &stateblock->state;
 
     /* No need to enable / disable anything here for unused samplers. The tex_colorop
     * handler takes care. Also no action is needed with pixel shaders, or if tex_colorop
     * will take care of this business
     */
     if (mapped_stage == WINED3D_UNMAPPED_STAGE || mapped_stage >= context->gl_info->limits.textures) return;
-    if(sampler >= stateblock->lowest_disabled_stage) return;
-    if(isStateDirty(context, STATE_TEXTURESTAGE(sampler, WINED3DTSS_COLOROP))) return;
+    if (sampler >= state->lowest_disabled_stage) return;
+    if (isStateDirty(context, STATE_TEXTURESTAGE(sampler, WINED3DTSS_COLOROP))) return;
 
-    nvts_activate_dimensions(sampler, stateblock, context);
+    nvts_activate_dimensions(state, sampler, context);
 }
 
 static void nvts_bumpenvmat(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
@@ -590,14 +601,13 @@ static void nvts_bumpenvmat(DWORD state, IWineD3DStateBlockImpl *stateblock, str
         GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
         checkGLcall("GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage))");
 
-        /* We can't just pass a pointer to the stateblock to GL due to the different matrix
-         * format(column major vs row major)
-         */
-        mat[0][0] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT00]);
-        mat[1][0] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT01]);
-        mat[0][1] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT10]);
-        mat[1][1] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT11]);
-        glTexEnvfv(GL_TEXTURE_SHADER_NV, GL_OFFSET_TEXTURE_MATRIX_NV, (float *) mat);
+        /* We can't just pass a pointer to the stateblock to GL due to the
+         * different matrix format (column major vs row major). */
+        mat[0][0] = *((float *)&stateblock->state.texture_states[stage][WINED3DTSS_BUMPENVMAT00]);
+        mat[1][0] = *((float *)&stateblock->state.texture_states[stage][WINED3DTSS_BUMPENVMAT01]);
+        mat[0][1] = *((float *)&stateblock->state.texture_states[stage][WINED3DTSS_BUMPENVMAT10]);
+        mat[1][1] = *((float *)&stateblock->state.texture_states[stage][WINED3DTSS_BUMPENVMAT11]);
+        glTexEnvfv(GL_TEXTURE_SHADER_NV, GL_OFFSET_TEXTURE_MATRIX_NV, (float *)mat);
         checkGLcall("glTexEnvfv(GL_TEXTURE_SHADER_NV, GL_OFFSET_TEXTURE_MATRIX_NV, mat)");
     }
 }
@@ -606,7 +616,7 @@ static void nvrc_texfactor(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
     float col[4];
-    D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_TEXTUREFACTOR], col);
+    D3DCOLORTOGLFLOAT4(stateblock->state.render_states[WINED3DRS_TEXTUREFACTOR], col);
     GL_EXTCALL(glCombinerParameterfvNV(GL_CONSTANT_COLOR0_NV, &col[0]));
 }
 
index 3fd8be9..2b7ce2c 100644 (file)
@@ -74,7 +74,7 @@ static ULONG  WINAPI IWineD3DPaletteImpl_Release(IWineD3DPalette *iface) {
 }
 
 /* Not called from the vtable */
-static DWORD IWineD3DPaletteImpl_Size(DWORD dwFlags)
+static WORD IWineD3DPaletteImpl_Size(DWORD dwFlags)
 {
     switch (dwFlags & SIZE_BITS) {
         case WINEDDPCAPS_1BIT: return 2;
@@ -92,7 +92,7 @@ static HRESULT  WINAPI IWineD3DPaletteImpl_GetEntries(IWineD3DPalette *iface, DW
 
     TRACE("(%p)->(%08x,%d,%d,%p)\n",This,Flags,Start,Count,PalEnt);
 
-    if (Flags != 0) return WINED3DERR_INVALIDCALL; /* unchecked */
+    if (Flags) return WINED3DERR_INVALIDCALL; /* unchecked */
     if (Start + Count > IWineD3DPaletteImpl_Size(This->Flags))
         return WINED3DERR_INVALIDCALL;
 
@@ -149,8 +149,8 @@ static HRESULT  WINAPI IWineD3DPaletteImpl_SetEntries(IWineD3DPalette *iface,
 #if 0
     /* Now, if we are in 'depth conversion mode', update the screen palette */
     /* FIXME: we need to update the image or we won't get palette fading. */
-    if (This->ddraw->d->palette_convert != NULL)
-        This->ddraw->d->palette_convert(palent,This->screen_palents,start,count);
+    if (This->ddraw->d->palette_convert)
+            This->ddraw->d->palette_convert(palent,This->screen_palents,start,count);
 #endif
 
     /* If the palette is attached to the render target, update all render targets */
@@ -175,13 +175,11 @@ static HRESULT  WINAPI IWineD3DPaletteImpl_GetCaps(IWineD3DPalette *iface, DWORD
     return WINED3D_OK;
 }
 
-static HRESULT  WINAPI IWineD3DPaletteImpl_GetParent(IWineD3DPalette *iface, IUnknown **Parent) {
-    IWineD3DPaletteImpl *This = (IWineD3DPaletteImpl *)iface;
-    TRACE("(%p)->(%p)\n", This, Parent);
+static void * WINAPI IWineD3DPaletteImpl_GetParent(IWineD3DPalette *iface)
+{
+    TRACE("iface %p.\n", iface);
 
-    *Parent = This->parent;
-    IUnknown_AddRef(This->parent);
-    return WINED3D_OK;
+    return ((IWineD3DPaletteImpl *)iface)->parent;
 }
 
 static const IWineD3DPaletteVtbl IWineD3DPalette_Vtbl =
@@ -198,7 +196,7 @@ static const IWineD3DPaletteVtbl IWineD3DPalette_Vtbl =
 };
 
 HRESULT wined3d_palette_init(IWineD3DPaletteImpl *palette, IWineD3DDeviceImpl *device,
-        DWORD flags, const PALETTEENTRY *entries, IUnknown *parent)
+        DWORD flags, const PALETTEENTRY *entries, void *parent)
 {
     HRESULT hr;
 
index b3c77ea..254efbe 100644 (file)
@@ -46,7 +46,7 @@ enum wined3d_event_query_result wined3d_event_query_test(struct wined3d_event_qu
 
     TRACE("(%p) : device %p\n", query, device);
 
-    if (query->context == NULL)
+    if (!query->context)
     {
         TRACE("Query not started\n");
         return WINED3D_EVENT_QUERY_NOT_STARTED;
@@ -230,27 +230,21 @@ void wined3d_event_query_issue(struct wined3d_event_query *query, IWineD3DDevice
     context_release(context);
 }
 
-/*
- * Occlusion Queries:
- * http://www.gris.uni-tuebingen.de/~bartz/Publications/paper/hww98.pdf
- * http://oss.sgi.com/projects/ogl-sample/registry/ARB/occlusion_query.txt
- */
-
-/* *******************************************
-   IWineD3DQuery IUnknown parts follow
-   ******************************************* */
-static HRESULT  WINAPI IWineD3DQueryImpl_QueryInterface(IWineD3DQuery *iface, REFIID riid, LPVOID *ppobj)
+static HRESULT  WINAPI IWineD3DQueryImpl_QueryInterface(IWineD3DQuery *iface, REFIID riid, void **object)
 {
-    IWineD3DQueryImpl *This = (IWineD3DQueryImpl *)iface;
-    TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(riid),ppobj);
-    if (IsEqualGUID(riid, &IID_IUnknown)
-        || IsEqualGUID(riid, &IID_IWineD3DBase)
-        || IsEqualGUID(riid, &IID_IWineD3DQuery)) {
+    TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object);
+
+    if (IsEqualGUID(riid, &IID_IWineD3DQuery)
+            || IsEqualGUID(riid, &IID_IUnknown))
+    {
         IUnknown_AddRef(iface);
-        *ppobj = This;
+        *object = iface;
         return S_OK;
     }
-    *ppobj = NULL;
+
+    WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
+
+    *object = NULL;
     return E_NOINTERFACE;
 }
 
@@ -265,7 +259,9 @@ static ULONG  WINAPI IWineD3DQueryImpl_Release(IWineD3DQuery *iface) {
     ULONG ref;
     TRACE("(%p) : Releasing from %d\n", This, This->ref);
     ref = InterlockedDecrement(&This->ref);
-    if (ref == 0) {
+
+    if (!ref)
+    {
         /* Queries are specific to the GL context that created them. Not
          * deleting the query will obviously leak it, but that's still better
          * than potentially deleting a different query with the same id in this
@@ -288,21 +284,6 @@ static ULONG  WINAPI IWineD3DQueryImpl_Release(IWineD3DQuery *iface) {
     return ref;
 }
 
-/* *******************************************
-   IWineD3DQuery IWineD3DQuery parts follow
-   ******************************************* */
-static HRESULT WINAPI IWineD3DQueryImpl_GetParent(IWineD3DQuery *iface, IUnknown **parent)
-{
-    TRACE("iface %p, parent %p.\n", iface, parent);
-
-    *parent = (IUnknown *)parent;
-    IUnknown_AddRef(*parent);
-
-    TRACE("Returning %p.\n", *parent);
-
-    return WINED3D_OK;
-}
-
 static HRESULT  WINAPI IWineD3DOcclusionQueryImpl_GetData(IWineD3DQuery* iface, void* pData, DWORD dwSize, DWORD dwGetDataFlags) {
     IWineD3DQueryImpl *This = (IWineD3DQueryImpl *) iface;
     struct wined3d_occlusion_query *query = This->extendedData;
@@ -554,7 +535,6 @@ static const IWineD3DQueryVtbl IWineD3DEventQuery_Vtbl =
     IWineD3DQueryImpl_AddRef,
     IWineD3DQueryImpl_Release,
     /*** IWineD3Dquery methods ***/
-    IWineD3DQueryImpl_GetParent,
     IWineD3DEventQueryImpl_GetData,
     IWineD3DEventQueryImpl_GetDataSize,
     IWineD3DQueryImpl_GetType,
@@ -568,15 +548,13 @@ static const IWineD3DQueryVtbl IWineD3DOcclusionQuery_Vtbl =
     IWineD3DQueryImpl_AddRef,
     IWineD3DQueryImpl_Release,
     /*** IWineD3Dquery methods ***/
-    IWineD3DQueryImpl_GetParent,
     IWineD3DOcclusionQueryImpl_GetData,
     IWineD3DOcclusionQueryImpl_GetDataSize,
     IWineD3DQueryImpl_GetType,
     IWineD3DOcclusionQueryImpl_Issue
 };
 
-HRESULT query_init(IWineD3DQueryImpl *query, IWineD3DDeviceImpl *device,
-        WINED3DQUERYTYPE type, IUnknown *parent)
+HRESULT query_init(IWineD3DQueryImpl *query, IWineD3DDeviceImpl *device, WINED3DQUERYTYPE type)
 {
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
 
@@ -638,7 +616,6 @@ HRESULT query_init(IWineD3DQueryImpl *query, IWineD3DDeviceImpl *device,
     query->type = type;
     query->state = QUERY_CREATED;
     query->device = device;
-    query->parent = parent;
     query->ref = 1;
 
     return WINED3D_OK;
index 67622a3..c95cf1b 100644 (file)
 WINE_DEFAULT_DEBUG_CHANNEL(d3d);
 
 HRESULT resource_init(IWineD3DResource *iface, WINED3DRESOURCETYPE resource_type,
-        IWineD3DDeviceImpl *device, UINT size, DWORD usage, const struct wined3d_format_desc *format_desc,
-        WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        IWineD3DDeviceImpl *device, UINT size, DWORD usage, const struct wined3d_format *format,
+        WINED3DPOOL pool, void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     struct IWineD3DResourceClass *resource = &((IWineD3DResourceImpl *)iface)->resource;
 
     resource->device = device;
-    resource->parent = parent;
     resource->resourceType = resource_type;
     resource->ref = 1;
     resource->pool = pool;
-    resource->format_desc = format_desc;
+    resource->format = format;
     resource->usage = usage;
     resource->size = size;
     resource->priority = 0;
+    resource->parent = parent;
     resource->parent_ops = parent_ops;
     list_init(&resource->privateData);
 
@@ -105,6 +105,12 @@ void resource_cleanup(IWineD3DResource *iface)
     if (This->resource.device) device_resource_released(This->resource.device, iface);
 }
 
+void resource_unload(IWineD3DResourceImpl *resource)
+{
+    context_resource_unloaded(resource->resource.device, (IWineD3DResource *)resource,
+            resource->resource.resourceType);
+}
+
 static PrivateData* resource_find_private_data(IWineD3DResourceImpl *This, REFGUID tag)
 {
     PrivateData *data;
@@ -133,7 +139,7 @@ HRESULT resource_set_private_data(IWineD3DResource *iface, REFGUID refguid,
     resource_free_private_data(iface, refguid);
 
     data = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*data));
-    if (NULL == data) return E_OUTOFMEMORY;
+    if (!data) return E_OUTOFMEMORY;
 
     data->tag = *refguid;
     data->flags = Flags;
@@ -151,7 +157,8 @@ HRESULT resource_set_private_data(IWineD3DResource *iface, REFGUID refguid,
     else
     {
         data->ptr.data = HeapAlloc(GetProcessHeap(), 0, SizeOfData);
-        if (NULL == data->ptr.data) {
+        if (!data->ptr.data)
+        {
             HeapFree(GetProcessHeap(), 0, data);
             return E_OUTOFMEMORY;
         }
@@ -170,7 +177,7 @@ HRESULT resource_get_private_data(IWineD3DResource *iface, REFGUID refguid, void
 
     TRACE("(%p) : %p %p %p\n", This, refguid, pData, pSizeOfData);
     data = resource_find_private_data(This, refguid);
-    if (data == NULL) return WINED3DERR_NOTFOUND;
+    if (!data) return WINED3DERR_NOTFOUND;
 
     if (*pSizeOfData < data->size) {
         *pSizeOfData = data->size;
@@ -201,13 +208,15 @@ HRESULT resource_free_private_data(IWineD3DResource *iface, REFGUID refguid)
 
     TRACE("(%p) : %s\n", This, debugstr_guid(refguid));
     data = resource_find_private_data(This, refguid);
-    if (data == NULL) return WINED3DERR_NOTFOUND;
+    if (!data) return WINED3DERR_NOTFOUND;
 
     if (data->flags & WINED3DSPD_IUNKNOWN)
     {
-        if (data->ptr.object != NULL)
+        if (data->ptr.object)
             IUnknown_Release(data->ptr.object);
-    } else {
+    }
+    else
+    {
         HeapFree(GetProcessHeap(), 0, data->ptr.data);
     }
     list_remove(&data->entry);
@@ -239,11 +248,3 @@ WINED3DRESOURCETYPE resource_get_type(IWineD3DResource *iface)
     TRACE("(%p) : returning %d\n", This, This->resource.resourceType);
     return This->resource.resourceType;
 }
-
-HRESULT resource_get_parent(IWineD3DResource *iface, IUnknown **pParent)
-{
-    IWineD3DResourceImpl *This = (IWineD3DResourceImpl *)iface;
-    IUnknown_AddRef(This->resource.parent);
-    *pParent = This->resource.parent;
-    return WINED3D_OK;
-}
index f26122a..bc39b3b 100644 (file)
 WINE_DEFAULT_DEBUG_CHANNEL(d3d_shader);
 WINE_DECLARE_DEBUG_CHANNEL(d3d);
 
-static const char *shader_opcode_names[] =
+static const char * const shader_opcode_names[] =
 {
     /* WINED3DSIH_ABS           */ "abs",
     /* WINED3DSIH_ADD           */ "add",
+    /* WINED3DSIH_AND           */ "and",
     /* WINED3DSIH_BEM           */ "bem",
     /* WINED3DSIH_BREAK         */ "break",
     /* WINED3DSIH_BREAKC        */ "breakc",
@@ -69,6 +70,7 @@ static const char *shader_opcode_names[] =
     /* WINED3DSIH_IF            */ "if",
     /* WINED3DSIH_IFC           */ "ifc",
     /* WINED3DSIH_IGE           */ "ige",
+    /* WINED3DSIH_IMUL          */ "imul",
     /* WINED3DSIH_LABEL         */ "label",
     /* WINED3DSIH_LIT           */ "lit",
     /* WINED3DSIH_LOG           */ "log",
@@ -86,6 +88,7 @@ static const char *shader_opcode_names[] =
     /* WINED3DSIH_MIN           */ "min",
     /* WINED3DSIH_MOV           */ "mov",
     /* WINED3DSIH_MOVA          */ "mova",
+    /* WINED3DSIH_MOVC          */ "movc",
     /* WINED3DSIH_MUL           */ "mul",
     /* WINED3DSIH_NOP           */ "nop",
     /* WINED3DSIH_NRM           */ "nrm",
@@ -125,7 +128,7 @@ static const char *shader_opcode_names[] =
     /* WINED3DSIH_TEXREG2RGB    */ "texreg2rgb",
 };
 
-static const char *semantic_names[] =
+static const char * const semantic_names[] =
 {
     /* WINED3DDECLUSAGE_POSITION        */ "SV_POSITION",
     /* WINED3DDECLUSAGE_BLENDWEIGHT     */ "BLENDWEIGHT",
@@ -182,6 +185,17 @@ static void shader_signature_from_semantic(struct wined3d_shader_signature_eleme
     e->mask = s->reg.write_mask;
 }
 
+static void shader_signature_from_usage(struct wined3d_shader_signature_element *e,
+        WINED3DDECLUSAGE usage, UINT usage_idx, UINT reg_idx, DWORD write_mask)
+{
+    e->semantic_name = shader_semantic_name_from_usage(usage);
+    e->semantic_idx = usage_idx;
+    e->sysval_semantic = 0;
+    e->component_type = 0;
+    e->register_idx = reg_idx;
+    e->mask = write_mask;
+}
+
 static const struct wined3d_shader_frontend *shader_select_frontend(DWORD version_token)
 {
     switch (version_token >> 16)
@@ -275,7 +289,7 @@ int shader_addline(struct wined3d_shader_buffer *buffer, const char *format, ...
 }
 
 static void shader_init(struct IWineD3DBaseShaderClass *shader, IWineD3DDeviceImpl *device,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     shader->ref = 1;
     shader->device = (IWineD3DDevice *)device;
@@ -367,7 +381,7 @@ static void shader_record_register_usage(IWineD3DBaseShaderImpl *shader, struct
         case WINED3DSPR_MISCTYPE:
             if (shader_type == WINED3D_SHADER_TYPE_PIXEL)
             {
-                if (reg->idx == 0) reg_maps->vpos = 1;
+                if (!reg->idx) reg_maps->vpos = 1;
                 else if (reg->idx == 1) reg_maps->usesfacing = 1;
             }
             break;
@@ -628,7 +642,7 @@ static HRESULT shader_get_registers_used(IWineD3DBaseShader *iface, const struct
              * Relative addressing tokens are ignored, but that's
              * okay, since we'll catch any address registers when
              * they are initialized (required by spec). */
-            if (ins.dst_count)
+            for (i = 0; i < ins.dst_count; ++i)
             {
                 struct wined3d_shader_src_param dst_rel_addr;
                 struct wined3d_shader_dst_param dst_param;
@@ -640,17 +654,77 @@ static HRESULT shader_get_registers_used(IWineD3DBaseShader *iface, const struct
                 /* WINED3DSPR_TEXCRDOUT is the same as WINED3DSPR_OUTPUT. _OUTPUT can be > MAX_REG_TEXCRD and
                  * is used in >= 3.0 shaders. Filter 3.0 shaders to prevent overflows, and also filter pixel
                  * shaders because TECRDOUT isn't used in them, but future register types might cause issues */
-                if (shader_version.type == WINED3D_SHADER_TYPE_VERTEX && shader_version.major < 3
-                        && dst_param.reg.type == WINED3DSPR_TEXCRDOUT)
+                if (shader_version.type == WINED3D_SHADER_TYPE_VERTEX && shader_version.major < 3)
                 {
-                    reg_maps->texcoord_mask[dst_param.reg.idx] |= dst_param.write_mask;
+                    UINT idx = dst_param.reg.idx;
+
+                    switch (dst_param.reg.type)
+                    {
+                        case WINED3DSPR_RASTOUT:
+                            switch (idx)
+                            {
+                                case 0: /* oPos */
+                                    reg_maps->output_registers |= 1 << 10;
+                                    shader_signature_from_usage(&output_signature[10],
+                                            WINED3DDECLUSAGE_POSITION, 0, 10, WINED3DSP_WRITEMASK_ALL);
+                                    break;
+
+                                case 1: /* oFog */
+                                    reg_maps->output_registers |= 1 << 11;
+                                    shader_signature_from_usage(&output_signature[11],
+                                            WINED3DDECLUSAGE_FOG, 0, 11, WINED3DSP_WRITEMASK_0);
+                                    break;
+
+                                case 2: /* oPts */
+                                    reg_maps->output_registers |= 1 << 11;
+                                    shader_signature_from_usage(&output_signature[11],
+                                            WINED3DDECLUSAGE_PSIZE, 0, 11, WINED3DSP_WRITEMASK_1);
+                                    break;
+                            }
+                            break;
+
+                        case WINED3DSPR_ATTROUT:
+                            if (idx < 2)
+                            {
+                                idx += 8;
+                                if (reg_maps->output_registers & (1 << idx))
+                                {
+                                    output_signature[idx].mask |= dst_param.write_mask;
+                                }
+                                else
+                                {
+                                    reg_maps->output_registers |= 1 << idx;
+                                    shader_signature_from_usage(&output_signature[idx],
+                                            WINED3DDECLUSAGE_COLOR, idx - 8, idx, dst_param.write_mask);
+                                }
+                            }
+                            break;
+
+                        case WINED3DSPR_TEXCRDOUT:
+
+                            reg_maps->texcoord_mask[idx] |= dst_param.write_mask;
+                            if (reg_maps->output_registers & (1 << idx))
+                            {
+                                output_signature[idx].mask |= dst_param.write_mask;
+                            }
+                            else
+                            {
+                                reg_maps->output_registers |= 1 << idx;
+                                shader_signature_from_usage(&output_signature[idx],
+                                        WINED3DDECLUSAGE_TEXCOORD, idx, idx, dst_param.write_mask);
+                            }
+                            break;
+
+                        default:
+                            break;
+                    }
                 }
 
                 if (shader_version.type == WINED3D_SHADER_TYPE_PIXEL)
                 {
                     IWineD3DPixelShaderImpl *ps = (IWineD3DPixelShaderImpl *)shader;
 
-                    if (dst_param.reg.type == WINED3DSPR_COLOROUT && dst_param.reg.idx == 0)
+                    if (dst_param.reg.type == WINED3DSPR_COLOROUT && !dst_param.reg.idx)
                     {
                     /* Many 2.0 and 3.0 pixel shaders end with a MOV from a temp register to
                      * COLOROUT 0. If we know this in advance, the ARB shader backend can skip
@@ -661,7 +735,8 @@ static HRESULT shader_get_registers_used(IWineD3DBaseShader *iface, const struct
                      * COLOROUT 0 is overwritten partially later, the marker is dropped again. */
 
                         ps->color0_mov = FALSE;
-                        if (ins.handler_idx == WINED3DSIH_MOV)
+                        if (ins.handler_idx == WINED3DSIH_MOV
+                                && dst_param.write_mask == WINED3DSP_WRITEMASK_ALL)
                         {
                             /* Used later when the source register is read. */
                             color0_mov = TRUE;
@@ -813,7 +888,7 @@ static void shader_dump_decl_usage(const struct wined3d_shader_semantic *semanti
                 break;
 
             case WINED3DDECLUSAGE_COLOR:
-                if (semantic->usage_idx == 0) TRACE("color");
+                if (!semantic->usage_idx) TRACE("color");
                 else TRACE("specular%u", (semantic->usage_idx - 1));
                 break;
 
@@ -944,6 +1019,10 @@ static void shader_dump_register(const struct wined3d_shader_register *reg,
             TRACE("cb");
             break;
 
+        case WINED3DSPR_NULL:
+            TRACE("null");
+            break;
+
         default:
             TRACE("unhandled_rtype(%#x)", reg->type);
             break;
@@ -954,11 +1033,11 @@ static void shader_dump_register(const struct wined3d_shader_register *reg,
         TRACE("(");
         switch (reg->immconst_type)
         {
-            case WINED3D_IMMCONST_FLOAT:
+            case WINED3D_IMMCONST_SCALAR:
                 TRACE("%.8e", *(const float *)reg->immconst_data);
                 break;
 
-            case WINED3D_IMMCONST_FLOAT4:
+            case WINED3D_IMMCONST_VEC4:
                 TRACE("%.8e, %.8e, %.8e, %.8e",
                         *(const float *)&reg->immconst_data[0], *(const float *)&reg->immconst_data[1],
                         *(const float *)&reg->immconst_data[2], *(const float *)&reg->immconst_data[3]);
@@ -970,7 +1049,9 @@ static void shader_dump_register(const struct wined3d_shader_register *reg,
         }
         TRACE(")");
     }
-    else if (reg->type != WINED3DSPR_RASTOUT && reg->type != WINED3DSPR_MISCTYPE)
+    else if (reg->type != WINED3DSPR_RASTOUT
+            && reg->type != WINED3DSPR_MISCTYPE
+            && reg->type != WINED3DSPR_NULL)
     {
         if (reg->array_idx != ~0U)
         {
@@ -1003,7 +1084,7 @@ void shader_dump_dst_param(const struct wined3d_shader_dst_param *param,
 
     shader_dump_register(&param->reg, shader_version);
 
-    if (write_mask != WINED3DSP_WRITEMASK_ALL)
+    if (write_mask && write_mask != WINED3DSP_WRITEMASK_ALL)
     {
         static const char *write_mask_chars = "xyzw";
 
@@ -1090,11 +1171,11 @@ void shader_generate_main(IWineD3DBaseShader *iface, struct wined3d_shader_buffe
     IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)shader->baseShader.device;
     const struct wined3d_shader_frontend *fe = shader->baseShader.frontend;
     void *fe_data = shader->baseShader.frontend_data;
+    struct wined3d_shader_src_param dst_rel_addr[2];
     struct wined3d_shader_src_param src_rel_addr[4];
+    struct wined3d_shader_dst_param dst_param[2];
     struct wined3d_shader_src_param src_param[4];
     struct wined3d_shader_version shader_version;
-    struct wined3d_shader_src_param dst_rel_addr;
-    struct wined3d_shader_dst_param dst_param;
     struct wined3d_shader_instruction ins;
     struct wined3d_shader_context ctx;
     const DWORD *ptr = byte_code;
@@ -1108,7 +1189,7 @@ void shader_generate_main(IWineD3DBaseShader *iface, struct wined3d_shader_buffe
     ctx.backend_data = backend_ctx;
 
     ins.ctx = &ctx;
-    ins.dst = &dst_param;
+    ins.dst = dst_param;
     ins.src = src_param;
     shader->baseShader.parse_state.current_row = 0;
 
@@ -1147,8 +1228,11 @@ void shader_generate_main(IWineD3DBaseShader *iface, struct wined3d_shader_buffe
             continue;
         }
 
-        /* Destination token */
-        if (ins.dst_count) fe->shader_read_dst_param(fe_data, &ptr, &dst_param, &dst_rel_addr);
+        /* Destination tokens */
+        for (i = 0; i < ins.dst_count; ++i)
+        {
+            fe->shader_read_dst_param(fe_data, &ptr, &dst_param[i], &dst_rel_addr[i]);
+        }
 
         /* Predication token */
         if (ins.predicate)
@@ -1319,13 +1403,14 @@ static void shader_trace_init(const struct wined3d_shader_frontend *fe, void *fe
         }
         else
         {
-            struct wined3d_shader_src_param dst_rel_addr, src_rel_addr;
-            struct wined3d_shader_dst_param dst_param;
+            struct wined3d_shader_src_param dst_rel_addr[2];
+            struct wined3d_shader_src_param src_rel_addr;
+            struct wined3d_shader_dst_param dst_param[2];
             struct wined3d_shader_src_param src_param;
 
-            if (ins.dst_count)
+            for (i = 0; i < ins.dst_count; ++i)
             {
-                fe->shader_read_dst_param(fe_data, &ptr, &dst_param, &dst_rel_addr);
+                fe->shader_read_dst_param(fe_data, &ptr, &dst_param[i], &dst_rel_addr[i]);
             }
 
             /* Print out predication source token first - it follows
@@ -1364,12 +1449,12 @@ static void shader_trace_init(const struct wined3d_shader_frontend *fe, void *fe
                 TRACE("p");
             }
 
-            /* We already read the destination token, print it. */
-            if (ins.dst_count)
+            /* We already read the destination tokens, print them. */
+            for (i = 0; i < ins.dst_count; ++i)
             {
-                shader_dump_ins_modifiers(&dst_param);
-                TRACE(" ");
-                shader_dump_dst_param(&dst_param, &shader_version);
+                shader_dump_ins_modifiers(&dst_param[i]);
+                TRACE(!i ? " " : ", ");
+                shader_dump_dst_param(&dst_param[i], &shader_version);
             }
 
             /* Other source tokens */
@@ -1462,13 +1547,6 @@ const shader_backend_t none_shader_backend = {
     shader_none_color_fixup_supported,
 };
 
-static void shader_get_parent(IWineD3DBaseShaderImpl *shader, IUnknown **parent)
-{
-    *parent = shader->baseShader.parent;
-    IUnknown_AddRef(*parent);
-    TRACE("shader %p, returning %p.\n", shader, *parent);
-}
-
 static HRESULT shader_get_function(IWineD3DBaseShaderImpl *shader, void *data, UINT *data_size)
 {
     if (!data)
@@ -1565,6 +1643,7 @@ static ULONG STDMETHODCALLTYPE vertexshader_AddRef(IWineD3DVertexShader *iface)
     return refcount;
 }
 
+/* Do not call while under the GL lock. */
 static ULONG STDMETHODCALLTYPE vertexshader_Release(IWineD3DVertexShader *iface)
 {
     IWineD3DVertexShaderImpl *shader = (IWineD3DVertexShaderImpl *)iface;
@@ -1582,13 +1661,11 @@ static ULONG STDMETHODCALLTYPE vertexshader_Release(IWineD3DVertexShader *iface)
     return refcount;
 }
 
-static HRESULT STDMETHODCALLTYPE vertexshader_GetParent(IWineD3DVertexShader *iface, IUnknown **parent)
+static void * STDMETHODCALLTYPE vertexshader_GetParent(IWineD3DVertexShader *iface)
 {
-    TRACE("iface %p, parent %p.\n", iface, parent);
-
-    shader_get_parent((IWineD3DBaseShaderImpl *)iface, parent);
+    TRACE("iface %p.\n", iface);
 
-    return WINED3D_OK;
+    return ((IWineD3DBaseShaderImpl *)iface)->baseShader.parent;
 }
 
 static HRESULT STDMETHODCALLTYPE vertexshader_GetFunction(IWineD3DVertexShader *iface, void *data, UINT *data_size)
@@ -1642,12 +1719,13 @@ static const IWineD3DVertexShaderVtbl IWineD3DVertexShader_Vtbl =
     vertexshader_SetLocalConstantsF,
 };
 
-void find_vs_compile_args(IWineD3DVertexShaderImpl *shader,
-        IWineD3DStateBlockImpl *stateblock, struct vs_compile_args *args)
+void find_vs_compile_args(const struct wined3d_state *state,
+        IWineD3DVertexShaderImpl *shader, struct vs_compile_args *args)
 {
-    args->fog_src = stateblock->renderState[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE ? VS_FOG_COORD : VS_FOG_Z;
-    args->clip_enabled = stateblock->renderState[WINED3DRS_CLIPPING]
-            && stateblock->renderState[WINED3DRS_CLIPPLANEENABLE];
+    args->fog_src = state->render_states[WINED3DRS_FOGTABLEMODE]
+            == WINED3DFOG_NONE ? VS_FOG_COORD : VS_FOG_Z;
+    args->clip_enabled = state->render_states[WINED3DRS_CLIPPING]
+            && state->render_states[WINED3DRS_CLIPPLANEENABLE];
     args->swizzle_map = ((IWineD3DDeviceImpl *)shader->baseShader.device)->strided_streams.swizzle_map;
 }
 
@@ -1661,9 +1739,9 @@ static BOOL match_usage(BYTE usage1, BYTE usage_idx1, BYTE usage2, BYTE usage_id
     return FALSE;
 }
 
-BOOL vshader_get_input(IWineD3DVertexShader *iface, BYTE usage_req, BYTE usage_idx_req, unsigned int *regnum)
+BOOL vshader_get_input(struct IWineD3DVertexShaderImpl *shader,
+        BYTE usage_req, BYTE usage_idx_req, unsigned int *regnum)
 {
-    IWineD3DVertexShaderImpl *shader = (IWineD3DVertexShaderImpl *)iface;
     WORD map = shader->baseShader.reg_maps.input_registers;
     unsigned int i;
 
@@ -1699,7 +1777,7 @@ static void vertexshader_set_limits(IWineD3DVertexShaderImpl *shader)
             shader->baseShader.limits.constant_bool = 0;
             shader->baseShader.limits.constant_int = 0;
             shader->baseShader.limits.address = 1;
-            shader->baseShader.limits.packed_output = 0;
+            shader->baseShader.limits.packed_output = 12;
             shader->baseShader.limits.sampler = 0;
             shader->baseShader.limits.label = 0;
             /* TODO: vs_1_1 has a minimum of 96 constants. What happens when
@@ -1714,7 +1792,7 @@ static void vertexshader_set_limits(IWineD3DVertexShaderImpl *shader)
             shader->baseShader.limits.constant_bool = 16;
             shader->baseShader.limits.constant_int = 16;
             shader->baseShader.limits.address = 1;
-            shader->baseShader.limits.packed_output = 0;
+            shader->baseShader.limits.packed_output = 12;
             shader->baseShader.limits.sampler = 0;
             shader->baseShader.limits.label = 16;
             shader->baseShader.limits.constant_float = min(256, device->d3d_vshader_constantF);
@@ -1745,7 +1823,7 @@ static void vertexshader_set_limits(IWineD3DVertexShaderImpl *shader)
             shader->baseShader.limits.constant_bool = 16;
             shader->baseShader.limits.constant_int = 16;
             shader->baseShader.limits.address = 1;
-            shader->baseShader.limits.packed_output = 0;
+            shader->baseShader.limits.packed_output = 12;
             shader->baseShader.limits.sampler = 0;
             shader->baseShader.limits.label = 16;
             shader->baseShader.limits.constant_float = min(256, device->d3d_vshader_constantF);
@@ -1757,7 +1835,7 @@ static void vertexshader_set_limits(IWineD3DVertexShaderImpl *shader)
 
 HRESULT vertexshader_init(IWineD3DVertexShaderImpl *shader, IWineD3DDeviceImpl *device,
         const DWORD *byte_code, const struct wined3d_shader_signature *output_signature,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
     struct shader_reg_maps *reg_maps = &shader->baseShader.reg_maps;
@@ -1862,6 +1940,7 @@ static ULONG STDMETHODCALLTYPE geometryshader_AddRef(IWineD3DGeometryShader *ifa
     return refcount;
 }
 
+/* Do not call while under the GL lock. */
 static ULONG STDMETHODCALLTYPE geometryshader_Release(IWineD3DGeometryShader *iface)
 {
     struct wined3d_geometryshader *shader = (struct wined3d_geometryshader *)iface;
@@ -1879,13 +1958,11 @@ static ULONG STDMETHODCALLTYPE geometryshader_Release(IWineD3DGeometryShader *if
     return refcount;
 }
 
-static HRESULT STDMETHODCALLTYPE geometryshader_GetParent(IWineD3DGeometryShader *iface, IUnknown **parent)
+static void * STDMETHODCALLTYPE geometryshader_GetParent(IWineD3DGeometryShader *iface)
 {
-    TRACE("iface %p, parent %p.\n", iface, parent);
+    TRACE("iface %p.\n", iface);
 
-    shader_get_parent((IWineD3DBaseShaderImpl *)iface, parent);
-
-    return WINED3D_OK;
+    return ((IWineD3DBaseShaderImpl *)iface)->baseShader.parent;
 }
 
 static HRESULT STDMETHODCALLTYPE geometryshader_GetFunction(IWineD3DGeometryShader *iface, void *data, UINT *data_size)
@@ -1909,7 +1986,7 @@ static const IWineD3DGeometryShaderVtbl wined3d_geometryshader_vtbl =
 
 HRESULT geometryshader_init(struct wined3d_geometryshader *shader, IWineD3DDeviceImpl *device,
         const DWORD *byte_code, const struct wined3d_shader_signature *output_signature,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     HRESULT hr;
 
@@ -1959,6 +2036,7 @@ static ULONG STDMETHODCALLTYPE pixelshader_AddRef(IWineD3DPixelShader *iface)
     return refcount;
 }
 
+/* Do not call while under the GL lock. */
 static ULONG STDMETHODCALLTYPE pixelshader_Release(IWineD3DPixelShader *iface)
 {
     IWineD3DPixelShaderImpl *shader = (IWineD3DPixelShaderImpl *)iface;
@@ -1976,13 +2054,11 @@ static ULONG STDMETHODCALLTYPE pixelshader_Release(IWineD3DPixelShader *iface)
     return refcount;
 }
 
-static HRESULT STDMETHODCALLTYPE pixelshader_GetParent(IWineD3DPixelShader *iface, IUnknown **parent)
+static void * STDMETHODCALLTYPE pixelshader_GetParent(IWineD3DPixelShader *iface)
 {
-    TRACE("iface %p, parent %p.\n", iface, parent);
+    TRACE("iface %p.\n", iface);
 
-    shader_get_parent((IWineD3DBaseShaderImpl *)iface, parent);
-
-    return WINED3D_OK;
+    return ((IWineD3DBaseShaderImpl *)iface)->baseShader.parent;
 }
 
 static HRESULT STDMETHODCALLTYPE pixelshader_GetFunction(IWineD3DPixelShader *iface, void *data, UINT *data_size)
@@ -2004,28 +2080,45 @@ static const IWineD3DPixelShaderVtbl IWineD3DPixelShader_Vtbl =
     pixelshader_GetFunction
 };
 
-void find_ps_compile_args(IWineD3DPixelShaderImpl *shader,
-        IWineD3DStateBlockImpl *stateblock, struct ps_compile_args *args)
+void find_ps_compile_args(const struct wined3d_state *state,
+        IWineD3DPixelShaderImpl *shader, struct ps_compile_args *args)
 {
+    IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *)shader->baseShader.device;
     IWineD3DBaseTextureImpl *texture;
     UINT i;
 
     memset(args, 0, sizeof(*args)); /* FIXME: Make sure all bits are set. */
-    args->srgb_correction = stateblock->renderState[WINED3DRS_SRGBWRITEENABLE] ? 1 : 0;
-    args->np2_fixup = 0;
+    if (state->render_states[WINED3DRS_SRGBWRITEENABLE])
+    {
+        IWineD3DSurfaceImpl *rt = device->render_targets[0];
+        if(rt->resource.format->Flags & WINED3DFMT_FLAG_SRGB_WRITE) args->srgb_correction = 1;
+    }
+
+    if (shader->baseShader.reg_maps.shader_version.major == 1
+            && shader->baseShader.reg_maps.shader_version.minor <= 3)
+    {
+        for (i = 0; i < 4; ++i)
+        {
+            DWORD flags = state->texture_states[i][WINED3DTSS_TEXTURETRANSFORMFLAGS];
+            DWORD tex_transform = flags & ~WINED3DTTFF_PROJECTED;
+            if (flags & WINED3DTTFF_PROJECTED)
+                tex_transform |= WINED3D_PSARGS_PROJECTED;
+            args->tex_transform |= tex_transform << i * WINED3D_PSARGS_TEXTRANSFORM_SHIFT;
+        }
+    }
 
     for (i = 0; i < MAX_FRAGMENT_SAMPLERS; ++i)
     {
         if (!shader->baseShader.reg_maps.sampler_type[i]) continue;
-        texture = (IWineD3DBaseTextureImpl *)stateblock->textures[i];
+        texture = state->textures[i];
         if (!texture)
         {
             args->color_fixup[i] = COLOR_FIXUP_IDENTITY;
             continue;
         }
-        args->color_fixup[i] = texture->resource.format_desc->color_fixup;
+        args->color_fixup[i] = texture->resource.format->color_fixup;
 
-        if (texture->resource.format_desc->Flags & WINED3DFMT_FLAG_SHADOW)
+        if (texture->resource.format->Flags & WINED3DFMT_FLAG_SHADOW)
             args->shadow |= 1 << i;
 
         /* Flag samplers that need NP2 texcoord fixup. */
@@ -2036,11 +2129,11 @@ void find_ps_compile_args(IWineD3DPixelShaderImpl *shader,
     }
     if (shader->baseShader.reg_maps.shader_version.major >= 3)
     {
-        if (((IWineD3DDeviceImpl *)shader->baseShader.device)->strided_streams.position_transformed)
+        if (device->strided_streams.position_transformed)
         {
             args->vp_mode = pretransformed;
         }
-        else if (use_vs(stateblock))
+        else if (use_vs(state))
         {
             args->vp_mode = vertexshader;
         }
@@ -2053,19 +2146,18 @@ void find_ps_compile_args(IWineD3DPixelShaderImpl *shader,
     else
     {
         args->vp_mode = vertexshader;
-        if (stateblock->renderState[WINED3DRS_FOGENABLE])
+        if (state->render_states[WINED3DRS_FOGENABLE])
         {
-            switch (stateblock->renderState[WINED3DRS_FOGTABLEMODE])
+            switch (state->render_states[WINED3DRS_FOGTABLEMODE])
             {
                 case WINED3DFOG_NONE:
-                    if (((IWineD3DDeviceImpl *)shader->baseShader.device)->strided_streams.position_transformed
-                            || use_vs(stateblock))
+                    if (device->strided_streams.position_transformed || use_vs(state))
                     {
                         args->fog = FOG_LINEAR;
                         break;
                     }
 
-                    switch (stateblock->renderState[WINED3DRS_FOGVERTEXMODE])
+                    switch (state->render_states[WINED3DRS_FOGVERTEXMODE])
                     {
                         case WINED3DFOG_NONE: /* Fall through. */
                         case WINED3DFOG_LINEAR: args->fog = FOG_LINEAR; break;
@@ -2176,7 +2268,7 @@ static void pixelshader_set_limits(IWineD3DPixelShaderImpl *shader)
 
 HRESULT pixelshader_init(IWineD3DPixelShaderImpl *shader, IWineD3DDeviceImpl *device,
         const DWORD *byte_code, const struct wined3d_shader_signature *output_signature,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
     unsigned int i, highest_reg_used = 0, num_regs_used = 0;
@@ -2261,7 +2353,7 @@ void pixelshader_update_samplers(struct shader_reg_maps *reg_maps, IWineD3DBaseT
             continue;
         }
 
-        switch (IWineD3DBaseTexture_GetTextureDimensions(textures[i]))
+        switch (((IWineD3DBaseTextureImpl *)textures[i])->baseTexture.target)
         {
             case GL_TEXTURE_RECTANGLE_ARB:
             case GL_TEXTURE_2D:
@@ -2281,7 +2373,7 @@ void pixelshader_update_samplers(struct shader_reg_maps *reg_maps, IWineD3DBaseT
 
             default:
                 FIXME("Unrecognized texture type %#x, using 2D.\n",
-                        IWineD3DBaseTexture_GetTextureDimensions(textures[i]));
+                        ((IWineD3DBaseTextureImpl *)textures[i])->baseTexture.target);
                 sampler_type[i] = WINED3DSTT_2D;
         }
     }
index b463790..a438614 100644 (file)
@@ -49,6 +49,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d_shader);
 enum wined3d_sm4_opcode
 {
     WINED3D_SM4_OP_ADD      = 0x00,
+    WINED3D_SM4_OP_AND      = 0x01,
     WINED3D_SM4_OP_BREAK    = 0x02,
     WINED3D_SM4_OP_BREAKC   = 0x03,
     WINED3D_SM4_OP_CUT      = 0x09,
@@ -58,14 +59,19 @@ enum wined3d_sm4_opcode
     WINED3D_SM4_OP_ENDIF    = 0x15,
     WINED3D_SM4_OP_ENDLOOP  = 0x16,
     WINED3D_SM4_OP_EXP      = 0x19,
+    WINED3D_SM4_OP_FRC      = 0x1a,
     WINED3D_SM4_OP_IADD     = 0x1e,
     WINED3D_SM4_OP_IF       = 0x1f,
     WINED3D_SM4_OP_IGE      = 0x21,
+    WINED3D_SM4_OP_IMUL     = 0x26,
     WINED3D_SM4_OP_LOG      = 0x2f,
+    WINED3D_SM4_OP_LOOP     = 0x30,
     WINED3D_SM4_OP_LT       = 0x31,
+    WINED3D_SM4_OP_MAD      = 0x32,
     WINED3D_SM4_OP_MIN      = 0x33,
     WINED3D_SM4_OP_MAX      = 0x34,
     WINED3D_SM4_OP_MOV      = 0x36,
+    WINED3D_SM4_OP_MOVC     = 0x37,
     WINED3D_SM4_OP_MUL      = 0x38,
     WINED3D_SM4_OP_RET      = 0x3e,
     WINED3D_SM4_OP_RSQ      = 0x44,
@@ -79,12 +85,13 @@ enum wined3d_sm4_register_type
     WINED3D_SM4_RT_OUTPUT       = 0x2,
     WINED3D_SM4_RT_IMMCONST     = 0x4,
     WINED3D_SM4_RT_CONSTBUFFER  = 0x8,
+    WINED3D_SM4_RT_NULL         = 0xd,
 };
 
 enum wined3d_sm4_immconst_type
 {
-    WINED3D_SM4_IMMCONST_FLOAT  = 0x1,
-    WINED3D_SM4_IMMCONST_FLOAT4 = 0x2,
+    WINED3D_SM4_IMMCONST_SCALAR = 0x1,
+    WINED3D_SM4_IMMCONST_VEC4   = 0x2,
 };
 
 struct wined3d_sm4_data
@@ -112,6 +119,7 @@ struct sysval_map
 static const struct wined3d_sm4_opcode_info opcode_table[] =
 {
     {WINED3D_SM4_OP_ADD,    WINED3DSIH_ADD,         1,  2},
+    {WINED3D_SM4_OP_AND,    WINED3DSIH_AND,         1,  2},
     {WINED3D_SM4_OP_BREAK,  WINED3DSIH_BREAK,       0,  0},
     {WINED3D_SM4_OP_BREAKC, WINED3DSIH_BREAKP,      0,  1},
     {WINED3D_SM4_OP_CUT,    WINED3DSIH_CUT,         0,  0},
@@ -121,18 +129,23 @@ static const struct wined3d_sm4_opcode_info opcode_table[] =
     {WINED3D_SM4_OP_ENDIF,  WINED3DSIH_ENDIF,       0,  0},
     {WINED3D_SM4_OP_ENDLOOP,WINED3DSIH_ENDLOOP,     0,  0},
     {WINED3D_SM4_OP_EXP,    WINED3DSIH_EXP,         1,  1},
+    {WINED3D_SM4_OP_FRC,    WINED3DSIH_FRC,         1,  1},
     {WINED3D_SM4_OP_IADD,   WINED3DSIH_IADD,        1,  2},
     {WINED3D_SM4_OP_IF,     WINED3DSIH_IF,          0,  1},
     {WINED3D_SM4_OP_IGE,    WINED3DSIH_IGE,         1,  2},
+    {WINED3D_SM4_OP_IMUL,   WINED3DSIH_IMUL,        2,  2},
     {WINED3D_SM4_OP_LOG,    WINED3DSIH_LOG,         1,  1},
+    {WINED3D_SM4_OP_LOOP,   WINED3DSIH_LOOP,        0,  0},
     {WINED3D_SM4_OP_LT,     WINED3DSIH_LT,          1,  2},
+    {WINED3D_SM4_OP_MAD,    WINED3DSIH_MAD,         1,  3},
     {WINED3D_SM4_OP_MIN,    WINED3DSIH_MIN,         1,  2},
     {WINED3D_SM4_OP_MAX,    WINED3DSIH_MAX,         1,  2},
     {WINED3D_SM4_OP_MOV,    WINED3DSIH_MOV,         1,  1},
+    {WINED3D_SM4_OP_MOVC,   WINED3DSIH_MOVC,        1,  3},
     {WINED3D_SM4_OP_MUL,    WINED3DSIH_MUL,         1,  2},
     {WINED3D_SM4_OP_RET,    WINED3DSIH_RET,         0,  0},
     {WINED3D_SM4_OP_RSQ,    WINED3DSIH_RSQ,         1,  1},
-    {WINED3D_SM4_OP_SINCOS, WINED3DSIH_SINCOS,      1,  2},
+    {WINED3D_SM4_OP_SINCOS, WINED3DSIH_SINCOS,      2,  1},
 };
 
 static const WINED3DSHADER_PARAM_REGISTER_TYPE register_type_table[] =
@@ -146,6 +159,11 @@ static const WINED3DSHADER_PARAM_REGISTER_TYPE register_type_table[] =
     /* UNKNOWN */                       0,
     /* UNKNOWN */                       0,
     /* WINED3D_SM4_RT_CONSTBUFFER */    WINED3DSPR_CONSTBUFFER,
+    /* UNKNOWN */                       0,
+    /* UNKNOWN */                       0,
+    /* UNKNOWN */                       0,
+    /* UNKNOWN */                       0,
+    /* WINED3D_SM4_RT_NULL */           WINED3DSPR_NULL,
 };
 
 static const struct sysval_map sysval_map[] =
@@ -336,14 +354,14 @@ static void shader_sm4_read_src_param(void *data, const DWORD **ptr, struct wine
 
         switch(immconst_type)
         {
-            case WINED3D_SM4_IMMCONST_FLOAT:
-                src_param->reg.immconst_type = WINED3D_IMMCONST_FLOAT;
+            case WINED3D_SM4_IMMCONST_SCALAR:
+                src_param->reg.immconst_type = WINED3D_IMMCONST_SCALAR;
                 memcpy(src_param->reg.immconst_data, *ptr, 1 * sizeof(DWORD));
                 *ptr += 1;
                 break;
 
-            case WINED3D_SM4_IMMCONST_FLOAT4:
-                src_param->reg.immconst_type = WINED3D_IMMCONST_FLOAT4;
+            case WINED3D_SM4_IMMCONST_VEC4:
+                src_param->reg.immconst_type = WINED3D_IMMCONST_VEC4;
                 memcpy(src_param->reg.immconst_data, *ptr, 4 * sizeof(DWORD));
                 *ptr += 4;
                 break;
index 4c6d5bf..6a415ee 100644 (file)
@@ -51,7 +51,7 @@ static void state_nop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wi
 
 static void state_fillmode(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    WINED3DFILLMODE Value = stateblock->renderState[WINED3DRS_FILLMODE];
+    WINED3DFILLMODE Value = stateblock->state.render_states[WINED3DRS_FILLMODE];
 
     switch(Value) {
         case WINED3DFILL_POINT:
@@ -83,7 +83,7 @@ static void state_lighting(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
         return;
     }
 
-    if (stateblock->renderState[WINED3DRS_LIGHTING]
+    if (stateblock->state.render_states[WINED3DRS_LIGHTING]
             && !stateblock->device->strided_streams.position_transformed)
     {
         glEnable(GL_LIGHTING);
@@ -105,7 +105,8 @@ static void state_zenable(DWORD state, IWineD3DStateBlockImpl *stateblock, struc
         return;
     }
 
-    switch ((WINED3DZBUFFERTYPE) stateblock->renderState[WINED3DRS_ZENABLE]) {
+    switch (stateblock->state.render_states[WINED3DRS_ZENABLE])
+    {
         case WINED3DZB_FALSE:
             glDisable(GL_DEPTH_TEST);
             checkGLcall("glDisable GL_DEPTH_TEST");
@@ -120,16 +121,17 @@ static void state_zenable(DWORD state, IWineD3DStateBlockImpl *stateblock, struc
             FIXME("W buffer is not well handled\n");
             break;
         default:
-            FIXME("Unrecognized D3DZBUFFERTYPE value %d\n", stateblock->renderState[WINED3DRS_ZENABLE]);
+            FIXME("Unrecognized D3DZBUFFERTYPE value %#x.\n",
+                    stateblock->state.render_states[WINED3DRS_ZENABLE]);
     }
 }
 
 static void state_cullmode(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    /* glFrontFace() is set in context.c at context init and on an offscreen / onscreen rendering
-     * switch
-     */
-    switch ((WINED3DCULL) stateblock->renderState[WINED3DRS_CULLMODE]) {
+    /* glFrontFace() is set in context.c at context init and on an
+     * offscreen / onscreen rendering switch. */
+    switch (stateblock->state.render_states[WINED3DRS_CULLMODE])
+    {
         case WINED3DCULL_NONE:
             glDisable(GL_CULL_FACE);
             checkGLcall("glDisable GL_CULL_FACE");
@@ -147,13 +149,15 @@ static void state_cullmode(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
             checkGLcall("glCullFace(GL_BACK)");
             break;
         default:
-            FIXME("Unrecognized/Unhandled WINED3DCULL value %d\n", stateblock->renderState[WINED3DRS_CULLMODE]);
+            FIXME("Unrecognized/Unhandled WINED3DCULL value %#x.\n",
+                    stateblock->state.render_states[WINED3DRS_CULLMODE]);
     }
 }
 
 static void state_shademode(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    switch ((WINED3DSHADEMODE) stateblock->renderState[WINED3DRS_SHADEMODE]) {
+    switch (stateblock->state.render_states[WINED3DRS_SHADEMODE])
+    {
         case WINED3DSHADE_FLAT:
             glShadeModel(GL_FLAT);
             checkGLcall("glShadeModel(GL_FLAT)");
@@ -166,16 +170,20 @@ static void state_shademode(DWORD state, IWineD3DStateBlockImpl *stateblock, str
             FIXME("WINED3DSHADE_PHONG isn't supported\n");
             break;
         default:
-            FIXME("Unrecognized/Unhandled WINED3DSHADEMODE value %d\n", stateblock->renderState[WINED3DRS_SHADEMODE]);
+            FIXME("Unrecognized/Unhandled WINED3DSHADEMODE value %#x.\n",
+                    stateblock->state.render_states[WINED3DRS_SHADEMODE]);
     }
 }
 
 static void state_ditherenable(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if (stateblock->renderState[WINED3DRS_DITHERENABLE]) {
+    if (stateblock->state.render_states[WINED3DRS_DITHERENABLE])
+    {
         glEnable(GL_DITHER);
         checkGLcall("glEnable GL_DITHER");
-    } else {
+    }
+    else
+    {
         glDisable(GL_DITHER);
         checkGLcall("glDisable GL_DITHER");
     }
@@ -183,13 +191,15 @@ static void state_ditherenable(DWORD state, IWineD3DStateBlockImpl *stateblock,
 
 static void state_zwritenable(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    /* TODO: Test if in d3d z writing is enabled even if ZENABLE is off. If yes,
-     * this has to be merged with ZENABLE and ZFUNC
-     */
-    if (stateblock->renderState[WINED3DRS_ZWRITEENABLE]) {
+    /* TODO: Test if in d3d z writing is enabled even if ZENABLE is off.
+     * If yes, this has to be merged with ZENABLE and ZFUNC. */
+    if (stateblock->state.render_states[WINED3DRS_ZWRITEENABLE])
+    {
         glDepthMask(1);
         checkGLcall("glDepthMask(1)");
-    } else {
+    }
+    else
+    {
         glDepthMask(0);
         checkGLcall("glDepthMask(0)");
     }
@@ -197,32 +207,33 @@ static void state_zwritenable(DWORD state, IWineD3DStateBlockImpl *stateblock, s
 
 static void state_zfunc(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    int glParm = CompareFunc(stateblock->renderState[WINED3DRS_ZFUNC]);
+    GLenum depth_func = CompareFunc(stateblock->state.render_states[WINED3DRS_ZFUNC]);
 
-    if(glParm) {
-        if(glParm == GL_EQUAL || glParm == GL_NOTEQUAL) {
-            static BOOL once = FALSE;
-            /* There are a few issues with this: First, our inability to
-             * select a proper Z depth, most of the time we're stuck with
-             * D24S8, even if the app selects D32 or D16. There seem to be
-             * some other precision problems which have to be debugged to
-             * make NOTEQUAL and EQUAL work properly
-             */
-            if(!once) {
-                once = TRUE;
-                FIXME("D3DCMP_NOTEQUAL and D3DCMP_EQUAL do not work correctly yet\n");
-            }
-        }
+    if (!depth_func) return;
 
-        glDepthFunc(glParm);
-        checkGLcall("glDepthFunc");
+    if (depth_func == GL_EQUAL || depth_func == GL_NOTEQUAL)
+    {
+        static BOOL once;
+        /* There are a few issues with this: First, our inability to
+         * select a proper Z depth, most of the time we're stuck with
+         * D24S8, even if the app selects D32 or D16. There seem to be
+         * some other precision problems which have to be debugged to
+         * make NOTEQUAL and EQUAL work properly. */
+        if (!once)
+        {
+            once = TRUE;
+            FIXME("D3DCMP_NOTEQUAL and D3DCMP_EQUAL do not work correctly yet.\n");
+        }
     }
+
+    glDepthFunc(depth_func);
+    checkGLcall("glDepthFunc");
 }
 
 static void state_ambient(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     float col[4];
-    D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_AMBIENT], col);
+    D3DCOLORTOGLFLOAT4(stateblock->state.render_states[WINED3DRS_AMBIENT], col);
 
     TRACE("Setting ambient to (%f,%f,%f,%f)\n", col[0], col[1], col[2], col[3]);
     glLightModelfv(GL_LIGHT_MODEL_AMBIENT, col);
@@ -236,15 +247,17 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
     int srcBlend = GL_ZERO;
     int dstBlend = GL_ZERO;
 
-    /* GL_LINE_SMOOTH needs GL_BLEND to work, according to the red book, and special blending params */
-    if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE]      ||
-        stateblock->renderState[WINED3DRS_EDGEANTIALIAS]         ||
-        stateblock->renderState[WINED3DRS_ANTIALIASEDLINEENABLE]) {
-
-        /* Disable blending in all cases even without pixelshaders. With blending on we could face a big performance penalty.
+    /* According to the red book, GL_LINE_SMOOTH needs GL_BLEND with specific
+     * blending parameters to work. */
+    if (stateblock->state.render_states[WINED3DRS_ALPHABLENDENABLE]
+            || stateblock->state.render_states[WINED3DRS_EDGEANTIALIAS]
+            || stateblock->state.render_states[WINED3DRS_ANTIALIASEDLINEENABLE])
+    {
+        /* Disable blending in all cases even without pixelshaders.
+         * With blending on we could face a big performance penalty.
          * The d3d9 visual test confirms the behavior. */
         if (context->render_offscreen
-                && !(target->resource.format_desc->Flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING))
+                && !(target->resource.format->Flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING))
         {
             glDisable(GL_BLEND);
             checkGLcall("glDisable GL_BLEND");
@@ -260,7 +273,8 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         return;
     };
 
-    switch (stateblock->renderState[WINED3DRS_DESTBLEND]) {
+    switch (stateblock->state.render_states[WINED3DRS_DESTBLEND])
+    {
         case WINED3DBLEND_ZERO               : dstBlend = GL_ZERO;  break;
         case WINED3DBLEND_ONE                : dstBlend = GL_ONE;  break;
         case WINED3DBLEND_SRCCOLOR           : dstBlend = GL_SRC_COLOR;  break;
@@ -276,10 +290,10 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
          * returns 1.0, so D3DBLEND_DESTALPHA is GL_ONE, and D3DBLEND_INVDESTALPHA is GL_ZERO
          */
         case WINED3DBLEND_DESTALPHA          :
-            dstBlend = target->resource.format_desc->alpha_mask ? GL_DST_ALPHA : GL_ONE;
+            dstBlend = target->resource.format->alpha_mask ? GL_DST_ALPHA : GL_ONE;
             break;
         case WINED3DBLEND_INVDESTALPHA       :
-            dstBlend = target->resource.format_desc->alpha_mask ? GL_ONE_MINUS_DST_ALPHA : GL_ZERO;
+            dstBlend = target->resource.format->alpha_mask ? GL_ONE_MINUS_DST_ALPHA : GL_ZERO;
             break;
 
         case WINED3DBLEND_SRCALPHASAT        :
@@ -303,10 +317,12 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         case WINED3DBLEND_BLENDFACTOR        : dstBlend = GL_CONSTANT_COLOR;   break;
         case WINED3DBLEND_INVBLENDFACTOR     : dstBlend = GL_ONE_MINUS_CONSTANT_COLOR;  break;
         default:
-            FIXME("Unrecognized dst blend value %d\n", stateblock->renderState[WINED3DRS_DESTBLEND]);
+            FIXME("Unrecognized dst blend value %#x.\n",
+                    stateblock->state.render_states[WINED3DRS_DESTBLEND]);
     }
 
-    switch (stateblock->renderState[WINED3DRS_SRCBLEND]) {
+    switch (stateblock->state.render_states[WINED3DRS_SRCBLEND])
+    {
         case WINED3DBLEND_ZERO               : srcBlend = GL_ZERO;  break;
         case WINED3DBLEND_ONE                : srcBlend = GL_ONE;  break;
         case WINED3DBLEND_SRCCOLOR           : srcBlend = GL_SRC_COLOR;  break;
@@ -318,10 +334,10 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         case WINED3DBLEND_SRCALPHASAT        : srcBlend = GL_SRC_ALPHA_SATURATE;  break;
 
         case WINED3DBLEND_DESTALPHA          :
-            srcBlend = target->resource.format_desc->alpha_mask ? GL_DST_ALPHA : GL_ONE;
+            srcBlend = target->resource.format->alpha_mask ? GL_DST_ALPHA : GL_ONE;
             break;
         case WINED3DBLEND_INVDESTALPHA       :
-            srcBlend = target->resource.format_desc->alpha_mask ? GL_ONE_MINUS_DST_ALPHA : GL_ZERO;
+            srcBlend = target->resource.format->alpha_mask ? GL_ONE_MINUS_DST_ALPHA : GL_ZERO;
             break;
 
         case WINED3DBLEND_BOTHSRCALPHA       : srcBlend = GL_SRC_ALPHA;
@@ -335,11 +351,13 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         case WINED3DBLEND_BLENDFACTOR        : srcBlend = GL_CONSTANT_COLOR;   break;
         case WINED3DBLEND_INVBLENDFACTOR     : srcBlend = GL_ONE_MINUS_CONSTANT_COLOR;  break;
         default:
-            FIXME("Unrecognized src blend value %d\n", stateblock->renderState[WINED3DRS_SRCBLEND]);
+            FIXME("Unrecognized src blend value %#x.\n",
+                    stateblock->state.render_states[WINED3DRS_SRCBLEND]);
     }
 
-    if(stateblock->renderState[WINED3DRS_EDGEANTIALIAS] ||
-       stateblock->renderState[WINED3DRS_ANTIALIASEDLINEENABLE]) {
+    if (stateblock->state.render_states[WINED3DRS_EDGEANTIALIAS]
+            || stateblock->state.render_states[WINED3DRS_ANTIALIASEDLINEENABLE])
+    {
         glEnable(GL_LINE_SMOOTH);
         checkGLcall("glEnable(GL_LINE_SMOOTH)");
         if(srcBlend != GL_SRC_ALPHA) {
@@ -358,7 +376,8 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         state_blendop(STATE_RENDER(WINED3DRS_BLENDOPALPHA), stateblock, context);
     }
 
-    if(stateblock->renderState[WINED3DRS_SEPARATEALPHABLENDENABLE]) {
+    if (stateblock->state.render_states[WINED3DRS_SEPARATEALPHABLENDENABLE])
+    {
         int srcBlendAlpha = GL_ZERO;
         int dstBlendAlpha = GL_ZERO;
 
@@ -369,7 +388,8 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
             return;
         }
 
-        switch (stateblock->renderState[WINED3DRS_DESTBLENDALPHA]) {
+        switch (stateblock->state.render_states[WINED3DRS_DESTBLENDALPHA])
+        {
             case WINED3DBLEND_ZERO               : dstBlendAlpha = GL_ZERO;  break;
             case WINED3DBLEND_ONE                : dstBlendAlpha = GL_ONE;  break;
             case WINED3DBLEND_SRCCOLOR           : dstBlendAlpha = GL_SRC_COLOR;  break;
@@ -400,10 +420,12 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
             case WINED3DBLEND_BLENDFACTOR        : dstBlendAlpha = GL_CONSTANT_COLOR;   break;
             case WINED3DBLEND_INVBLENDFACTOR     : dstBlendAlpha = GL_ONE_MINUS_CONSTANT_COLOR;  break;
             default:
-                FIXME("Unrecognized dst blend alpha value %d\n", stateblock->renderState[WINED3DRS_DESTBLENDALPHA]);
+                FIXME("Unrecognized dst blend alpha value %#x.\n",
+                        stateblock->state.render_states[WINED3DRS_DESTBLENDALPHA]);
         }
 
-        switch (stateblock->renderState[WINED3DRS_SRCBLENDALPHA]) {
+        switch (stateblock->state.render_states[WINED3DRS_SRCBLENDALPHA])
+        {
             case WINED3DBLEND_ZERO               : srcBlendAlpha = GL_ZERO;  break;
             case WINED3DBLEND_ONE                : srcBlendAlpha = GL_ONE;  break;
             case WINED3DBLEND_SRCCOLOR           : srcBlendAlpha = GL_SRC_COLOR;  break;
@@ -426,7 +448,8 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
             case WINED3DBLEND_BLENDFACTOR        : srcBlendAlpha = GL_CONSTANT_COLOR;   break;
             case WINED3DBLEND_INVBLENDFACTOR     : srcBlendAlpha = GL_ONE_MINUS_CONSTANT_COLOR;  break;
             default:
-                FIXME("Unrecognized src blend alpha value %d\n", stateblock->renderState[WINED3DRS_SRCBLENDALPHA]);
+                FIXME("Unrecognized src blend alpha value %#x.\n",
+                        stateblock->state.render_states[WINED3DRS_SRCBLENDALPHA]);
         }
 
         GL_EXTCALL(glBlendFuncSeparateEXT(srcBlend, dstBlend, srcBlendAlpha, dstBlendAlpha));
@@ -439,7 +462,7 @@ static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
 
     /* colorkey fixup for stage 0 alphaop depends on WINED3DRS_ALPHABLENDENABLE state,
         so it may need updating */
-    if (stateblock->renderState[WINED3DRS_COLORKEYENABLE])
+    if (stateblock->state.render_states[WINED3DRS_COLORKEYENABLE])
         stateblock_apply_state(STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), stateblock, context);
 }
 
@@ -453,8 +476,8 @@ static void state_blendfactor(DWORD state, IWineD3DStateBlockImpl *stateblock, s
     const struct wined3d_gl_info *gl_info = context->gl_info;
     float col[4];
 
-    TRACE("Setting BlendFactor to %d\n", stateblock->renderState[WINED3DRS_BLENDFACTOR]);
-    D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_BLENDFACTOR], col);
+    TRACE("Setting blend factor to %#x.\n", stateblock->state.render_states[WINED3DRS_BLENDFACTOR]);
+    D3DCOLORTOGLFLOAT4(stateblock->state.render_states[WINED3DRS_BLENDFACTOR], col);
     GL_EXTCALL(glBlendColorEXT (col[0],col[1],col[2],col[3]));
     checkGLcall("glBlendColor");
 }
@@ -473,13 +496,13 @@ static void state_alpha(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
      * used WINED3DRS_COLORKEYENABLE state(which is d3d <= 3 only). The texture function will call alpha
      * in case it finds some texture+colorkeyenable combination which needs extra care.
      */
-    if (stateblock->textures[0])
+    if (stateblock->state.textures[0])
     {
-        UINT texture_dimensions = IWineD3DBaseTexture_GetTextureDimensions(stateblock->textures[0]);
+        IWineD3DBaseTextureImpl *texture = stateblock->state.textures[0];
+        GLenum texture_dimensions = texture->baseTexture.target;
 
         if (texture_dimensions == GL_TEXTURE_2D || texture_dimensions == GL_TEXTURE_RECTANGLE_ARB)
         {
-            IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)stateblock->textures[0];
             IWineD3DSurfaceImpl *surf = (IWineD3DSurfaceImpl *)texture->baseTexture.sub_resources[0];
 
             if (surf->CKeyFlags & WINEDDSD_CKSRCBLT)
@@ -487,7 +510,7 @@ static void state_alpha(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
                 /* The surface conversion does not do color keying conversion for surfaces that have an alpha
                  * channel on their own. Likewise, the alpha test shouldn't be set up for color keying if the
                  * surface has alpha bits */
-                if (!surf->resource.format_desc->alpha_mask) enable_ckey = TRUE;
+                if (!surf->resource.format->alpha_mask) enable_ckey = TRUE;
             }
         }
     }
@@ -496,8 +519,9 @@ static void state_alpha(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         stateblock_apply_state(STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), stateblock, context);
     context->last_was_ckey = enable_ckey;
 
-    if (stateblock->renderState[WINED3DRS_ALPHATESTENABLE] ||
-        (stateblock->renderState[WINED3DRS_COLORKEYENABLE] && enable_ckey)) {
+    if (stateblock->state.render_states[WINED3DRS_ALPHATESTENABLE]
+            || (stateblock->state.render_states[WINED3DRS_COLORKEYENABLE] && enable_ckey))
+    {
         glEnable(GL_ALPHA_TEST);
         checkGLcall("glEnable GL_ALPHA_TEST");
     } else {
@@ -509,12 +533,13 @@ static void state_alpha(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         return;
     }
 
-    if(stateblock->renderState[WINED3DRS_COLORKEYENABLE] && enable_ckey) {
+    if (stateblock->state.render_states[WINED3DRS_COLORKEYENABLE] && enable_ckey)
+    {
         glParm = GL_NOTEQUAL;
         ref = 0.0f;
     } else {
-        ref = ((float) stateblock->renderState[WINED3DRS_ALPHAREF]) / 255.0f;
-        glParm = CompareFunc(stateblock->renderState[WINED3DRS_ALPHAFUNC]);
+        ref = ((float)stateblock->state.render_states[WINED3DRS_ALPHAREF]) / 255.0f;
+        glParm = CompareFunc(stateblock->state.render_states[WINED3DRS_ALPHAFUNC]);
     }
     if(glParm) {
         glAlphaFunc(glParm, ref);
@@ -522,20 +547,22 @@ static void state_alpha(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
     }
 }
 
-static void state_clipping(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void state_clipping(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
     DWORD enable  = 0xFFFFFFFF;
     DWORD disable = 0x00000000;
 
-    if (!stateblock->device->vs_clipping && use_vs(stateblock))
+    if (!stateblock->device->vs_clipping && use_vs(state))
     {
         /* The spec says that opengl clipping planes are disabled when using shaders. Direct3D planes aren't,
          * so that is an issue. The MacOS ATI driver keeps clipping planes activated with shaders in some
          * conditions I got sick of tracking down. The shader state handler disables all clip planes because
          * of that - don't do anything here and keep them disabled
          */
-        if(stateblock->renderState[WINED3DRS_CLIPPLANEENABLE]) {
+        if (state->render_states[WINED3DRS_CLIPPLANEENABLE])
+        {
             static BOOL warned = FALSE;
             if(!warned) {
                 FIXME("Clipping not supported with vertex shaders\n");
@@ -552,9 +579,10 @@ static void state_clipping(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
     /* If enabling / disabling all
      * TODO: Is this correct? Doesn't D3DRS_CLIPPING disable clipping on the viewport frustrum?
      */
-    if (stateblock->renderState[WINED3DRS_CLIPPING]) {
-        enable  = stateblock->renderState[WINED3DRS_CLIPPLANEENABLE];
-        disable = ~stateblock->renderState[WINED3DRS_CLIPPLANEENABLE];
+    if (state->render_states[WINED3DRS_CLIPPING])
+    {
+        enable = state->render_states[WINED3DRS_CLIPPLANEENABLE];
+        disable = ~state->render_states[WINED3DRS_CLIPPLANEENABLE];
         if (gl_info->supported[ARB_DEPTH_CLAMP])
         {
             glDisable(GL_DEPTH_CLAMP);
@@ -589,12 +617,15 @@ static void state_clipping(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
     if (disable & WINED3DCLIPPLANE5) { glDisable(GL_CLIP_PLANE5); checkGLcall("glDisable(clip plane 5)"); }
 
     /** update clipping status */
-    if (enable) {
-        stateblock->clip_status.ClipUnion = 0;
-        stateblock->clip_status.ClipIntersection = 0xFFFFFFFF;
-    } else {
-        stateblock->clip_status.ClipUnion = 0;
-        stateblock->clip_status.ClipIntersection = 0;
+    if (enable)
+    {
+        stateblock->state.clip_status.ClipUnion = 0;
+        stateblock->state.clip_status.ClipIntersection = 0xFFFFFFFF;
+    }
+    else
+    {
+        stateblock->state.clip_status.ClipUnion = 0;
+        stateblock->state.clip_status.ClipIntersection = 0;
     }
 }
 
@@ -610,34 +641,39 @@ static void state_blendop(DWORD state, IWineD3DStateBlockImpl *stateblock, struc
     int blendEquationAlpha = GL_FUNC_ADD;
 
     /* BLENDOPALPHA requires GL_EXT_blend_equation_separate, so make sure it is around */
-    if (stateblock->renderState[WINED3DRS_BLENDOPALPHA]
+    if (stateblock->state.render_states[WINED3DRS_BLENDOPALPHA]
             && !gl_info->supported[EXT_BLEND_EQUATION_SEPARATE])
     {
         WARN("Unsupported in local OpenGL implementation: glBlendEquationSeparateEXT\n");
         return;
     }
 
-    switch ((WINED3DBLENDOP) stateblock->renderState[WINED3DRS_BLENDOP]) {
+    switch (stateblock->state.render_states[WINED3DRS_BLENDOP])
+    {
         case WINED3DBLENDOP_ADD              : blendEquation = GL_FUNC_ADD;              break;
         case WINED3DBLENDOP_SUBTRACT         : blendEquation = GL_FUNC_SUBTRACT;         break;
         case WINED3DBLENDOP_REVSUBTRACT      : blendEquation = GL_FUNC_REVERSE_SUBTRACT; break;
         case WINED3DBLENDOP_MIN              : blendEquation = GL_MIN;                   break;
         case WINED3DBLENDOP_MAX              : blendEquation = GL_MAX;                   break;
         default:
-            FIXME("Unrecognized/Unhandled D3DBLENDOP value %d\n", stateblock->renderState[WINED3DRS_BLENDOP]);
+            FIXME("Unrecognized/Unhandled D3DBLENDOP value %#x.\n",
+                    stateblock->state.render_states[WINED3DRS_BLENDOP]);
     }
 
-    switch ((WINED3DBLENDOP) stateblock->renderState[WINED3DRS_BLENDOPALPHA]) {
+    switch (stateblock->state.render_states[WINED3DRS_BLENDOPALPHA])
+    {
         case WINED3DBLENDOP_ADD              : blendEquationAlpha = GL_FUNC_ADD;              break;
         case WINED3DBLENDOP_SUBTRACT         : blendEquationAlpha = GL_FUNC_SUBTRACT;         break;
         case WINED3DBLENDOP_REVSUBTRACT      : blendEquationAlpha = GL_FUNC_REVERSE_SUBTRACT; break;
         case WINED3DBLENDOP_MIN              : blendEquationAlpha = GL_MIN;                   break;
         case WINED3DBLENDOP_MAX              : blendEquationAlpha = GL_MAX;                   break;
         default:
-            FIXME("Unrecognized/Unhandled D3DBLENDOP value %d\n", stateblock->renderState[WINED3DRS_BLENDOPALPHA]);
+            FIXME("Unrecognized/Unhandled D3DBLENDOP value %#x\n",
+                    stateblock->state.render_states[WINED3DRS_BLENDOPALPHA]);
     }
 
-    if(stateblock->renderState[WINED3DRS_SEPARATEALPHABLENDENABLE]) {
+    if (stateblock->state.render_states[WINED3DRS_SEPARATEALPHABLENDENABLE])
+    {
         TRACE("glBlendEquationSeparateEXT(%x, %x)\n", blendEquation, blendEquationAlpha);
         GL_EXTCALL(glBlendEquationSeparateEXT(blendEquation, blendEquationAlpha));
         checkGLcall("glBlendEquationSeparateEXT");
@@ -682,11 +718,12 @@ static void state_specularenable(DWORD state, IWineD3DStateBlockImpl *stateblock
      */
 
     TRACE("Setting specular enable state and materials\n");
-    if (stateblock->renderState[WINED3DRS_SPECULARENABLE]) {
-        glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, (float*) &stateblock->material.Specular);
+    if (stateblock->state.render_states[WINED3DRS_SPECULARENABLE])
+    {
+        glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, (float *)&stateblock->state.material.Specular);
         checkGLcall("glMaterialfv");
 
-        if (stateblock->material.Power > gl_info->limits.shininess)
+        if (stateblock->state.material.Power > gl_info->limits.shininess)
         {
             /* glMaterialf man page says that the material says that GL_SHININESS must be between 0.0
              * and 128.0, although in d3d neither -1 nor 129 produce an error. GL_NV_max_light_exponent
@@ -694,10 +731,12 @@ static void state_specularenable(DWORD state, IWineD3DStateBlockImpl *stateblock
              * value reported by the extension, otherwise 128. For values > gl_info->limits.shininess clamp
              * them, it should be safe to do so without major visual distortions.
              */
-            WARN("Material power = %f, limit %f\n", stateblock->material.Power, gl_info->limits.shininess);
+            WARN("Material power = %f, limit %f\n", stateblock->state.material.Power, gl_info->limits.shininess);
             glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, gl_info->limits.shininess);
-        } else {
-            glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, stateblock->material.Power);
+        }
+        else
+        {
+            glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, stateblock->state.material.Power);
         }
         checkGLcall("glMaterialf(GL_SHININESS)");
 
@@ -742,23 +781,23 @@ static void state_specularenable(DWORD state, IWineD3DStateBlockImpl *stateblock
     }
 
     TRACE("(%p) : Diffuse {%.8e, %.8e, %.8e, %.8e}\n", stateblock->device,
-            stateblock->material.Diffuse.r, stateblock->material.Diffuse.g,
-            stateblock->material.Diffuse.b, stateblock->material.Diffuse.a);
+            stateblock->state.material.Diffuse.r, stateblock->state.material.Diffuse.g,
+            stateblock->state.material.Diffuse.b, stateblock->state.material.Diffuse.a);
     TRACE("(%p) : Ambient {%.8e, %.8e, %.8e, %.8e}\n", stateblock->device,
-            stateblock->material.Ambient.r, stateblock->material.Ambient.g,
-            stateblock->material.Ambient.b, stateblock->material.Ambient.a);
+            stateblock->state.material.Ambient.r, stateblock->state.material.Ambient.g,
+            stateblock->state.material.Ambient.b, stateblock->state.material.Ambient.a);
     TRACE("(%p) : Specular {%.8e, %.8e, %.8e, %.8e}\n", stateblock->device,
-            stateblock->material.Specular.r, stateblock->material.Specular.g,
-            stateblock->material.Specular.b, stateblock->material.Specular.a);
+            stateblock->state.material.Specular.r, stateblock->state.material.Specular.g,
+            stateblock->state.material.Specular.b, stateblock->state.material.Specular.a);
     TRACE("(%p) : Emissive {%.8e, %.8e, %.8e, %.8e}\n", stateblock->device,
-            stateblock->material.Emissive.r, stateblock->material.Emissive.g,
-            stateblock->material.Emissive.b, stateblock->material.Emissive.a);
+            stateblock->state.material.Emissive.r, stateblock->state.material.Emissive.g,
+            stateblock->state.material.Emissive.b, stateblock->state.material.Emissive.a);
 
-    glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, (float*) &stateblock->material.Ambient);
+    glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, (float *)&stateblock->state.material.Ambient);
     checkGLcall("glMaterialfv(GL_AMBIENT)");
-    glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, (float*) &stateblock->material.Diffuse);
+    glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, (float *)&stateblock->state.material.Diffuse);
     checkGLcall("glMaterialfv(GL_DIFFUSE)");
-    glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, (float*) &stateblock->material.Emissive);
+    glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, (float *)&stateblock->state.material.Emissive);
     checkGLcall("glMaterialfv(GL_EMISSION)");
 }
 
@@ -771,7 +810,7 @@ static void state_texfactor(DWORD state, IWineD3DStateBlockImpl *stateblock, str
      * GL_TEXTURE_ENV_COLOR applies to active only
      */
     float col[4];
-    D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_TEXTUREFACTOR], col);
+    D3DCOLORTOGLFLOAT4(stateblock->state.render_states[WINED3DRS_TEXTUREFACTOR], col);
 
     /* And now the default texture color as well */
     for (i = 0; i < gl_info->limits.texture_stages; ++i)
@@ -826,20 +865,20 @@ static void state_stencil(DWORD state, IWineD3DStateBlockImpl *stateblock, struc
         return;
     }
 
-    onesided_enable = stateblock->renderState[WINED3DRS_STENCILENABLE];
-    twosided_enable = stateblock->renderState[WINED3DRS_TWOSIDEDSTENCILMODE];
-    if( !( func = CompareFunc(stateblock->renderState[WINED3DRS_STENCILFUNC]) ) )
+    onesided_enable = stateblock->state.render_states[WINED3DRS_STENCILENABLE];
+    twosided_enable = stateblock->state.render_states[WINED3DRS_TWOSIDEDSTENCILMODE];
+    if (!(func = CompareFunc(stateblock->state.render_states[WINED3DRS_STENCILFUNC])))
         func = GL_ALWAYS;
-    if( !( func_ccw = CompareFunc(stateblock->renderState[WINED3DRS_CCW_STENCILFUNC]) ) )
+    if (!(func_ccw = CompareFunc(stateblock->state.render_states[WINED3DRS_CCW_STENCILFUNC])))
         func_ccw = GL_ALWAYS;
-    ref = stateblock->renderState[WINED3DRS_STENCILREF];
-    mask = stateblock->renderState[WINED3DRS_STENCILMASK];
-    stencilFail = StencilOp(stateblock->renderState[WINED3DRS_STENCILFAIL]);
-    depthFail = StencilOp(stateblock->renderState[WINED3DRS_STENCILZFAIL]);
-    stencilPass = StencilOp(stateblock->renderState[WINED3DRS_STENCILPASS]);
-    stencilFail_ccw = StencilOp(stateblock->renderState[WINED3DRS_CCW_STENCILFAIL]);
-    depthFail_ccw = StencilOp(stateblock->renderState[WINED3DRS_CCW_STENCILZFAIL]);
-    stencilPass_ccw = StencilOp(stateblock->renderState[WINED3DRS_CCW_STENCILPASS]);
+    ref = stateblock->state.render_states[WINED3DRS_STENCILREF];
+    mask = stateblock->state.render_states[WINED3DRS_STENCILMASK];
+    stencilFail = StencilOp(stateblock->state.render_states[WINED3DRS_STENCILFAIL]);
+    depthFail = StencilOp(stateblock->state.render_states[WINED3DRS_STENCILZFAIL]);
+    stencilPass = StencilOp(stateblock->state.render_states[WINED3DRS_STENCILPASS]);
+    stencilFail_ccw = StencilOp(stateblock->state.render_states[WINED3DRS_CCW_STENCILFAIL]);
+    depthFail_ccw = StencilOp(stateblock->state.render_states[WINED3DRS_CCW_STENCILZFAIL]);
+    stencilPass_ccw = StencilOp(stateblock->state.render_states[WINED3DRS_CCW_STENCILPASS]);
 
     TRACE("(onesided %d, twosided %d, ref %x, mask %x, "
           "GL_FRONT: func: %x, fail %x, zfail %x, zpass %x "
@@ -902,7 +941,7 @@ static void state_stencil(DWORD state, IWineD3DStateBlockImpl *stateblock, struc
 
 static void state_stencilwrite2s(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD mask = stateblock->device->depth_stencil ? stateblock->renderState[WINED3DRS_STENCILWRITEMASK] : 0;
+    DWORD mask = stateblock->device->depth_stencil ? stateblock->state.render_states[WINED3DRS_STENCILWRITEMASK] : 0;
     const struct wined3d_gl_info *gl_info = context->gl_info;
 
     GL_EXTCALL(glActiveStencilFaceEXT(GL_BACK));
@@ -916,7 +955,7 @@ static void state_stencilwrite2s(DWORD state, IWineD3DStateBlockImpl *stateblock
 
 static void state_stencilwrite(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD mask = stateblock->device->depth_stencil ? stateblock->renderState[WINED3DRS_STENCILWRITEMASK] : 0;
+    DWORD mask = stateblock->device->depth_stencil ? stateblock->state.render_states[WINED3DRS_STENCILWRITEMASK] : 0;
 
     glStencilMask(mask);
     checkGLcall("glStencilMask");
@@ -927,10 +966,11 @@ static void state_fog_vertexpart(DWORD state, IWineD3DStateBlockImpl *stateblock
 
     TRACE("state %#x, stateblock %p, context %p\n", state, stateblock, context);
 
-    if (!stateblock->renderState[WINED3DRS_FOGENABLE]) return;
+    if (!stateblock->state.render_states[WINED3DRS_FOGENABLE]) return;
 
     /* Table fog on: Never use fog coords, and use per-fragment fog */
-    if(stateblock->renderState[WINED3DRS_FOGTABLEMODE] != WINED3DFOG_NONE) {
+    if (stateblock->state.render_states[WINED3DRS_FOGTABLEMODE] != WINED3DFOG_NONE)
+    {
         glHint(GL_FOG_HINT, GL_NICEST);
         if(context->fog_coord) {
             glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT);
@@ -943,7 +983,8 @@ static void state_fog_vertexpart(DWORD state, IWineD3DStateBlockImpl *stateblock
     /* Otherwise use per-vertex fog in any case */
     glHint(GL_FOG_HINT, GL_FASTEST);
 
-    if(stateblock->renderState[WINED3DRS_FOGVERTEXMODE] == WINED3DFOG_NONE || context->last_was_rhw) {
+    if (stateblock->state.render_states[WINED3DRS_FOGVERTEXMODE] == WINED3DFOG_NONE || context->last_was_rhw)
+    {
         /* No fog at all, or transformed vertices: Use fog coord */
         if(!context->fog_coord) {
             glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FOG_COORDINATE_EXT);
@@ -980,9 +1021,9 @@ void state_fogstartend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct w
             break;
 
         case FOGSOURCE_FFP:
-            tmpvalue.d = stateblock->renderState[WINED3DRS_FOGSTART];
+            tmpvalue.d = stateblock->state.render_states[WINED3DRS_FOGSTART];
             fogstart = tmpvalue.f;
-            tmpvalue.d = stateblock->renderState[WINED3DRS_FOGEND];
+            tmpvalue.d = stateblock->state.render_states[WINED3DRS_FOGEND];
             fogend = tmpvalue.f;
             /* In GL, fogstart == fogend disables fog, in D3D everything's fogged.*/
             if(fogstart == fogend) {
@@ -1009,13 +1050,15 @@ void state_fogstartend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct w
     TRACE("Fog End == %f\n", fogend);
 }
 
-void state_fog_fragpart(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+void state_fog_fragpart(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
+    const struct wined3d_state *state = &stateblock->state;
     enum fogsource new_source;
 
-    TRACE("state %#x, stateblock %p, context %p\n", state, stateblock, context);
+    TRACE("state_id %#x, stateblock %p, context %p\n", state_id, stateblock, context);
 
-    if (!stateblock->renderState[WINED3DRS_FOGENABLE]) {
+    if (!state->render_states[WINED3DRS_FOGENABLE])
+    {
         /* No fog? Disable it, and we're done :-) */
         glDisableWINE(GL_FOG);
         checkGLcall("glDisable GL_FOG");
@@ -1068,13 +1111,18 @@ void state_fog_fragpart(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
     /* DX 7 sdk: "If both render states(vertex and table fog) are set to valid modes,
      * the system will apply only pixel(=table) fog effects."
      */
-    if(stateblock->renderState[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE) {
-        if(use_vs(stateblock)) {
+    if (state->render_states[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE)
+    {
+        if (use_vs(state))
+        {
             glFogi(GL_FOG_MODE, GL_LINEAR);
             checkGLcall("glFogi(GL_FOG_MODE, GL_LINEAR)");
             new_source = FOGSOURCE_VS;
-        } else {
-            switch (stateblock->renderState[WINED3DRS_FOGVERTEXMODE]) {
+        }
+        else
+        {
+            switch (state->render_states[WINED3DRS_FOGVERTEXMODE])
+            {
                 /* If processed vertices are used, fall through to the NONE case */
                 case WINED3DFOG_EXP:
                     if(!context->last_was_rhw) {
@@ -1114,14 +1162,16 @@ void state_fog_fragpart(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
                     break;
 
                 default:
-                    FIXME("Unexpected WINED3DRS_FOGVERTEXMODE %d\n", stateblock->renderState[WINED3DRS_FOGVERTEXMODE]);
+                    FIXME("Unexpected WINED3DRS_FOGVERTEXMODE %#x.\n",
+                            state->render_states[WINED3DRS_FOGVERTEXMODE]);
                     new_source = FOGSOURCE_FFP; /* Make the compiler happy */
             }
         }
     } else {
         new_source = FOGSOURCE_FFP;
 
-        switch (stateblock->renderState[WINED3DRS_FOGTABLEMODE]) {
+        switch (state->render_states[WINED3DRS_FOGTABLEMODE])
+        {
             case WINED3DFOG_EXP:
                 glFogi(GL_FOG_MODE, GL_EXP);
                 checkGLcall("glFogi(GL_FOG_MODE, GL_EXP)");
@@ -1139,7 +1189,8 @@ void state_fog_fragpart(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
 
             case WINED3DFOG_NONE:   /* Won't happen */
             default:
-                FIXME("Unexpected WINED3DRS_FOGTABLEMODE %d\n", stateblock->renderState[WINED3DRS_FOGTABLEMODE]);
+                FIXME("Unexpected WINED3DRS_FOGTABLEMODE %#x.\n",
+                        state->render_states[WINED3DRS_FOGTABLEMODE]);
         }
     }
 
@@ -1153,14 +1204,14 @@ void state_fog_fragpart(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
 
 static void state_rangefog_w(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_RANGEFOGENABLE]) {
+    if (stateblock->state.render_states[WINED3DRS_RANGEFOGENABLE])
         WARN("Range fog enabled, but not supported by this opengl implementation\n");
-    }
 }
 
 static void state_rangefog(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_RANGEFOGENABLE]) {
+    if (stateblock->state.render_states[WINED3DRS_RANGEFOGENABLE])
+    {
         glFogi(GL_FOG_DISTANCE_MODE_NV, GL_EYE_RADIAL_NV);
         checkGLcall("glFogi(GL_FOG_DISTANCE_MODE_NV, GL_EYE_RADIAL_NV)");
     } else {
@@ -1172,7 +1223,7 @@ static void state_rangefog(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
 void state_fogcolor(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     float col[4];
-    D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_FOGCOLOR], col);
+    D3DCOLORTOGLFLOAT4(stateblock->state.render_states[WINED3DRS_FOGCOLOR], col);
     glFogfv(GL_FOG_COLOR, &col[0]);
     checkGLcall("glFog GL_FOG_COLOR");
 }
@@ -1183,13 +1234,14 @@ void state_fogdensity(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wi
         DWORD d;
         float f;
     } tmpvalue;
-    tmpvalue.d = stateblock->renderState[WINED3DRS_FOGDENSITY];
+    tmpvalue.d = stateblock->state.render_states[WINED3DRS_FOGDENSITY];
     glFogfv(GL_FOG_DENSITY, &tmpvalue.f);
     checkGLcall("glFogf(GL_FOG_DENSITY, (float) Value)");
 }
 
-static void state_colormat(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void state_colormat(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
+    const struct wined3d_state *state = &stateblock->state;
     IWineD3DDeviceImpl *device = stateblock->device;
     GLenum Parm = 0;
 
@@ -1203,45 +1255,56 @@ static void state_colormat(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
 
     context->num_untracked_materials = 0;
     if ((device->strided_streams.use_map & (1 << WINED3D_FFP_DIFFUSE))
-            && stateblock->renderState[WINED3DRS_COLORVERTEX])
+            && state->render_states[WINED3DRS_COLORVERTEX])
     {
         TRACE("diff %d, amb %d, emis %d, spec %d\n",
-              stateblock->renderState[WINED3DRS_DIFFUSEMATERIALSOURCE],
-              stateblock->renderState[WINED3DRS_AMBIENTMATERIALSOURCE],
-              stateblock->renderState[WINED3DRS_EMISSIVEMATERIALSOURCE],
-              stateblock->renderState[WINED3DRS_SPECULARMATERIALSOURCE]);
+                state->render_states[WINED3DRS_DIFFUSEMATERIALSOURCE],
+                state->render_states[WINED3DRS_AMBIENTMATERIALSOURCE],
+                state->render_states[WINED3DRS_EMISSIVEMATERIALSOURCE],
+                state->render_states[WINED3DRS_SPECULARMATERIALSOURCE]);
 
-        if (stateblock->renderState[WINED3DRS_DIFFUSEMATERIALSOURCE] == WINED3DMCS_COLOR1) {
-            if (stateblock->renderState[WINED3DRS_AMBIENTMATERIALSOURCE] == WINED3DMCS_COLOR1) {
+        if (state->render_states[WINED3DRS_DIFFUSEMATERIALSOURCE] == WINED3DMCS_COLOR1)
+        {
+            if (state->render_states[WINED3DRS_AMBIENTMATERIALSOURCE] == WINED3DMCS_COLOR1)
                 Parm = GL_AMBIENT_AND_DIFFUSE;
-            } else {
+            else
                 Parm = GL_DIFFUSE;
-            }
-            if(stateblock->renderState[WINED3DRS_EMISSIVEMATERIALSOURCE] == WINED3DMCS_COLOR1) {
+            if (state->render_states[WINED3DRS_EMISSIVEMATERIALSOURCE] == WINED3DMCS_COLOR1)
+            {
                 context->untracked_materials[context->num_untracked_materials] = GL_EMISSION;
                 context->num_untracked_materials++;
             }
-            if(stateblock->renderState[WINED3DRS_SPECULARMATERIALSOURCE] == WINED3DMCS_COLOR1) {
+            if (state->render_states[WINED3DRS_SPECULARMATERIALSOURCE] == WINED3DMCS_COLOR1)
+            {
                 context->untracked_materials[context->num_untracked_materials] = GL_SPECULAR;
                 context->num_untracked_materials++;
             }
-        } else if (stateblock->renderState[WINED3DRS_AMBIENTMATERIALSOURCE] == WINED3DMCS_COLOR1) {
+        }
+        else if (state->render_states[WINED3DRS_AMBIENTMATERIALSOURCE] == WINED3DMCS_COLOR1)
+        {
             Parm = GL_AMBIENT;
-            if(stateblock->renderState[WINED3DRS_EMISSIVEMATERIALSOURCE] == WINED3DMCS_COLOR1) {
+            if (state->render_states[WINED3DRS_EMISSIVEMATERIALSOURCE] == WINED3DMCS_COLOR1)
+            {
                 context->untracked_materials[context->num_untracked_materials] = GL_EMISSION;
                 context->num_untracked_materials++;
             }
-            if(stateblock->renderState[WINED3DRS_SPECULARMATERIALSOURCE] == WINED3DMCS_COLOR1) {
+            if (state->render_states[WINED3DRS_SPECULARMATERIALSOURCE] == WINED3DMCS_COLOR1)
+            {
                 context->untracked_materials[context->num_untracked_materials] = GL_SPECULAR;
                 context->num_untracked_materials++;
             }
-        } else if (stateblock->renderState[WINED3DRS_EMISSIVEMATERIALSOURCE] == WINED3DMCS_COLOR1) {
+        }
+        else if (state->render_states[WINED3DRS_EMISSIVEMATERIALSOURCE] == WINED3DMCS_COLOR1)
+        {
             Parm = GL_EMISSION;
-            if(stateblock->renderState[WINED3DRS_SPECULARMATERIALSOURCE] == WINED3DMCS_COLOR1) {
+            if (state->render_states[WINED3DRS_SPECULARMATERIALSOURCE] == WINED3DMCS_COLOR1)
+            {
                 context->untracked_materials[context->num_untracked_materials] = GL_SPECULAR;
                 context->num_untracked_materials++;
             }
-        } else if (stateblock->renderState[WINED3DRS_SPECULARMATERIALSOURCE] == WINED3DMCS_COLOR1) {
+        }
+        else if (state->render_states[WINED3DRS_SPECULARMATERIALSOURCE] == WINED3DMCS_COLOR1)
+        {
             Parm = GL_SPECULAR;
         }
     }
@@ -1263,30 +1326,31 @@ static void state_colormat(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
      * tracking with glColorMaterial, so apply those here. */
     switch (context->tracking_parm) {
         case GL_AMBIENT_AND_DIFFUSE:
-            glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, (float*)&device->updateStateBlock->material.Ambient);
-            glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, (float*)&device->updateStateBlock->material.Diffuse);
+            glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, (float *)&state->material.Ambient);
+            glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, (float *)&state->material.Diffuse);
             checkGLcall("glMaterialfv");
             break;
 
         case GL_DIFFUSE:
-            glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, (float*)&device->updateStateBlock->material.Diffuse);
+            glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, (float *)&state->material.Diffuse);
             checkGLcall("glMaterialfv");
             break;
 
         case GL_AMBIENT:
-            glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, (float*)&device->updateStateBlock->material.Ambient);
+            glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, (float *)&state->material.Ambient);
             checkGLcall("glMaterialfv");
             break;
 
         case GL_EMISSION:
-            glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, (float*)&device->updateStateBlock->material.Emissive);
+            glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, (float *)&state->material.Emissive);
             checkGLcall("glMaterialfv");
             break;
 
         case GL_SPECULAR:
             /* Only change material color if specular is enabled, otherwise it is set to black */
-            if (device->stateBlock->renderState[WINED3DRS_SPECULARENABLE]) {
-                glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, (float*)&device->updateStateBlock->material.Specular);
+            if (state->render_states[WINED3DRS_SPECULARENABLE])
+            {
+                glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, (float *)&state->material.Specular);
                 checkGLcall("glMaterialfv");
             } else {
                 static const GLfloat black[] = {0.0f, 0.0f, 0.0f, 0.0f};
@@ -1305,7 +1369,7 @@ static void state_linepattern(DWORD state, IWineD3DStateBlockImpl *stateblock, s
         DWORD                 d;
         WINED3DLINEPATTERN    lp;
     } tmppattern;
-    tmppattern.d = stateblock->renderState[WINED3DRS_LINEPATTERN];
+    tmppattern.d = stateblock->state.render_states[WINED3DRS_LINEPATTERN];
 
     TRACE("Line pattern: repeat %d bits %x\n", tmppattern.lp.wRepeatFactor, tmppattern.lp.wLinePattern);
 
@@ -1327,8 +1391,9 @@ static void state_zbias(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         float f;
     } tmpvalue;
 
-    if (stateblock->renderState[WINED3DRS_ZBIAS]) {
-        tmpvalue.d = stateblock->renderState[WINED3DRS_ZBIAS];
+    if (stateblock->state.render_states[WINED3DRS_ZBIAS])
+    {
+        tmpvalue.d = stateblock->state.render_states[WINED3DRS_ZBIAS];
         TRACE("ZBias value %f\n", tmpvalue.f);
         glPolygonOffset(0, -tmpvalue.f);
         checkGLcall("glPolygonOffset(0, -Value)");
@@ -1358,7 +1423,7 @@ static void state_normalize(DWORD state, IWineD3DStateBlockImpl *stateblock, str
      * from the opengl lighting equation, as d3d does. Normalization of 0/0/0 can lead to a division
      * by zero and is not properly defined in opengl, so avoid it
      */
-    if (stateblock->renderState[WINED3DRS_NORMALIZENORMALS]
+    if (stateblock->state.render_states[WINED3DRS_NORMALIZENORMALS]
             && (stateblock->device->strided_streams.use_map & (1 << WINED3D_FFP_NORMAL)))
     {
         glEnable(GL_NORMALIZE);
@@ -1376,12 +1441,12 @@ static void state_psizemin_w(DWORD state, IWineD3DStateBlockImpl *stateblock, st
         float f;
     } tmpvalue;
 
-    tmpvalue.d = stateblock->renderState[WINED3DRS_POINTSIZE_MIN];
+    tmpvalue.d = stateblock->state.render_states[WINED3DRS_POINTSIZE_MIN];
     if (tmpvalue.f != 1.0f)
     {
         FIXME("WINED3DRS_POINTSIZE_MIN not supported on this opengl, value is %f\n", tmpvalue.f);
     }
-    tmpvalue.d = stateblock->renderState[WINED3DRS_POINTSIZE_MAX];
+    tmpvalue.d = stateblock->state.render_states[WINED3DRS_POINTSIZE_MAX];
     if (tmpvalue.f != 64.0f)
     {
         FIXME("WINED3DRS_POINTSIZE_MAX not supported on this opengl, value is %f\n", tmpvalue.f);
@@ -1398,8 +1463,8 @@ static void state_psizemin_ext(DWORD state, IWineD3DStateBlockImpl *stateblock,
         float f;
     } min, max;
 
-    min.d = stateblock->renderState[WINED3DRS_POINTSIZE_MIN];
-    max.d = stateblock->renderState[WINED3DRS_POINTSIZE_MAX];
+    min.d = stateblock->state.render_states[WINED3DRS_POINTSIZE_MIN];
+    max.d = stateblock->state.render_states[WINED3DRS_POINTSIZE_MAX];
 
     /* Max point size trumps min point size */
     if(min.f > max.f) {
@@ -1421,8 +1486,8 @@ static void state_psizemin_arb(DWORD state, IWineD3DStateBlockImpl *stateblock,
         float f;
     } min, max;
 
-    min.d = stateblock->renderState[WINED3DRS_POINTSIZE_MIN];
-    max.d = stateblock->renderState[WINED3DRS_POINTSIZE_MAX];
+    min.d = stateblock->state.render_states[WINED3DRS_POINTSIZE_MIN];
+    max.d = stateblock->state.render_states[WINED3DRS_POINTSIZE_MAX];
 
     /* Max point size trumps min point size */
     if(min.f > max.f) {
@@ -1452,14 +1517,15 @@ static void state_pscale(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         float f;
     } pointSize, A, B, C;
 
-    pointSize.d = stateblock->renderState[WINED3DRS_POINTSIZE];
-    A.d = stateblock->renderState[WINED3DRS_POINTSCALE_A];
-    B.d = stateblock->renderState[WINED3DRS_POINTSCALE_B];
-    C.d = stateblock->renderState[WINED3DRS_POINTSCALE_C];
+    pointSize.d = stateblock->state.render_states[WINED3DRS_POINTSIZE];
+    A.d = stateblock->state.render_states[WINED3DRS_POINTSCALE_A];
+    B.d = stateblock->state.render_states[WINED3DRS_POINTSCALE_B];
+    C.d = stateblock->state.render_states[WINED3DRS_POINTSCALE_C];
 
-    if(stateblock->renderState[WINED3DRS_POINTSCALEENABLE]) {
+    if (stateblock->state.render_states[WINED3DRS_POINTSCALEENABLE])
+    {
         GLfloat scaleFactor;
-        float h = stateblock->viewport.Height;
+        DWORD h = stateblock->state.viewport.Height;
 
         if (pointSize.f < gl_info->limits.pointsize_min)
         {
@@ -1487,7 +1553,7 @@ static void state_pscale(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         } else {
             scaleFactor = 1.0f;
         }
-        scaleFactor = pow(h * scaleFactor, 2);
+        scaleFactor = powf(h * scaleFactor, 2);
 
         att[0] = A.f / scaleFactor;
         att[1] = B.f / scaleFactor;
@@ -1503,7 +1569,9 @@ static void state_pscale(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
     {
         GL_EXTCALL(glPointParameterfvEXT)(GL_DISTANCE_ATTENUATION_EXT, att);
         checkGLcall("glPointParameterfvEXT(GL_DISTANCE_ATTENUATION_EXT, ...)");
-    } else if(stateblock->renderState[WINED3DRS_POINTSCALEENABLE]) {
+    }
+    else if(stateblock->state.render_states[WINED3DRS_POINTSCALEENABLE])
+    {
         WARN("POINT_PARAMETERS not supported in this version of opengl\n");
     }
 
@@ -1513,15 +1581,15 @@ static void state_pscale(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
 
 static void state_debug_monitor(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    WARN("token: %#x\n", stateblock->renderState[WINED3DRS_DEBUGMONITORTOKEN]);
+    WARN("token: %#x\n", stateblock->state.render_states[WINED3DRS_DEBUGMONITORTOKEN]);
 }
 
 static void state_colorwrite(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD mask0 = stateblock->renderState[WINED3DRS_COLORWRITEENABLE];
-    DWORD mask1 = stateblock->renderState[WINED3DRS_COLORWRITEENABLE1];
-    DWORD mask2 = stateblock->renderState[WINED3DRS_COLORWRITEENABLE2];
-    DWORD mask3 = stateblock->renderState[WINED3DRS_COLORWRITEENABLE3];
+    DWORD mask0 = stateblock->state.render_states[WINED3DRS_COLORWRITEENABLE];
+    DWORD mask1 = stateblock->state.render_states[WINED3DRS_COLORWRITEENABLE1];
+    DWORD mask2 = stateblock->state.render_states[WINED3DRS_COLORWRITEENABLE2];
+    DWORD mask3 = stateblock->state.render_states[WINED3DRS_COLORWRITEENABLE3];
 
     TRACE("Color mask: r(%d) g(%d) b(%d) a(%d)\n",
             mask0 & WINED3DCOLORWRITEENABLE_RED ? 1 : 0,
@@ -1554,27 +1622,28 @@ static void set_color_mask(const struct wined3d_gl_info *gl_info, UINT index, DW
 
 static void state_colorwrite0(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    set_color_mask(context->gl_info, 0, stateblock->renderState[WINED3DRS_COLORWRITEENABLE]);
+    set_color_mask(context->gl_info, 0, stateblock->state.render_states[WINED3DRS_COLORWRITEENABLE]);
 }
 
 static void state_colorwrite1(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    set_color_mask(context->gl_info, 1, stateblock->renderState[WINED3DRS_COLORWRITEENABLE1]);
+    set_color_mask(context->gl_info, 1, stateblock->state.render_states[WINED3DRS_COLORWRITEENABLE1]);
 }
 
 static void state_colorwrite2(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    set_color_mask(context->gl_info, 2, stateblock->renderState[WINED3DRS_COLORWRITEENABLE2]);
+    set_color_mask(context->gl_info, 2, stateblock->state.render_states[WINED3DRS_COLORWRITEENABLE2]);
 }
 
 static void state_colorwrite3(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    set_color_mask(context->gl_info, 3, stateblock->renderState[WINED3DRS_COLORWRITEENABLE3]);
+    set_color_mask(context->gl_info, 3, stateblock->state.render_states[WINED3DRS_COLORWRITEENABLE3]);
 }
 
 static void state_localviewer(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_LOCALVIEWER]) {
+    if (stateblock->state.render_states[WINED3DRS_LOCALVIEWER])
+    {
         glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 1);
         checkGLcall("glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 1)");
     } else {
@@ -1585,7 +1654,8 @@ static void state_localviewer(DWORD state, IWineD3DStateBlockImpl *stateblock, s
 
 static void state_lastpixel(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_LASTPIXEL]) {
+    if (stateblock->state.render_states[WINED3DRS_LASTPIXEL])
+    {
         TRACE("Last Pixel Drawing Enabled\n");
     } else {
         static BOOL warned;
@@ -1603,24 +1673,26 @@ static void state_pointsprite_w(DWORD state, IWineD3DStateBlockImpl *stateblock,
     static BOOL warned;
 
     /* TODO: NV_POINT_SPRITE */
-    if (!warned && stateblock->renderState[WINED3DRS_POINTSPRITEENABLE]) {
+    if (!warned && stateblock->state.render_states[WINED3DRS_POINTSPRITEENABLE])
+    {
         /* A FIXME, not a WARN because point sprites should be software emulated if not supported by HW */
         FIXME("Point sprites not supported\n");
         warned = TRUE;
     }
 }
 
-static void state_pointsprite(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void state_pointsprite(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
 
-    if (stateblock->renderState[WINED3DRS_POINTSPRITEENABLE])
+    if (state->render_states[WINED3DRS_POINTSPRITEENABLE])
     {
         static BOOL warned;
 
         if (gl_info->limits.point_sprite_units < gl_info->limits.textures && !warned)
         {
-            if (use_ps(stateblock) || stateblock->lowest_disabled_stage > gl_info->limits.point_sprite_units)
+            if (use_ps(state) || state->lowest_disabled_stage > gl_info->limits.point_sprite_units)
             {
                 FIXME("The app uses point sprite texture coordinates on more units than supported by the driver\n");
                 warned = TRUE;
@@ -1645,37 +1717,37 @@ static void state_wrap(DWORD state, IWineD3DStateBlockImpl *stateblock, struct w
 
      so far as I can tell, wrapping and texture-coordinate generate go hand in hand,
      */
-    TRACE("Stub\n");
-    if(stateblock->renderState[WINED3DRS_WRAP0] ||
-       stateblock->renderState[WINED3DRS_WRAP1] ||
-       stateblock->renderState[WINED3DRS_WRAP2] ||
-       stateblock->renderState[WINED3DRS_WRAP3] ||
-       stateblock->renderState[WINED3DRS_WRAP4] ||
-       stateblock->renderState[WINED3DRS_WRAP5] ||
-       stateblock->renderState[WINED3DRS_WRAP6] ||
-       stateblock->renderState[WINED3DRS_WRAP7] ||
-       stateblock->renderState[WINED3DRS_WRAP8] ||
-       stateblock->renderState[WINED3DRS_WRAP9] ||
-       stateblock->renderState[WINED3DRS_WRAP10] ||
-       stateblock->renderState[WINED3DRS_WRAP11] ||
-       stateblock->renderState[WINED3DRS_WRAP12] ||
-       stateblock->renderState[WINED3DRS_WRAP13] ||
-       stateblock->renderState[WINED3DRS_WRAP14] ||
-       stateblock->renderState[WINED3DRS_WRAP15] ) {
-        FIXME("(WINED3DRS_WRAP0) Texture wrapping not yet supported\n");
+    if (stateblock->state.render_states[WINED3DRS_WRAP0]
+            || stateblock->state.render_states[WINED3DRS_WRAP1]
+            || stateblock->state.render_states[WINED3DRS_WRAP2]
+            || stateblock->state.render_states[WINED3DRS_WRAP3]
+            || stateblock->state.render_states[WINED3DRS_WRAP4]
+            || stateblock->state.render_states[WINED3DRS_WRAP5]
+            || stateblock->state.render_states[WINED3DRS_WRAP6]
+            || stateblock->state.render_states[WINED3DRS_WRAP7]
+            || stateblock->state.render_states[WINED3DRS_WRAP8]
+            || stateblock->state.render_states[WINED3DRS_WRAP9]
+            || stateblock->state.render_states[WINED3DRS_WRAP10]
+            || stateblock->state.render_states[WINED3DRS_WRAP11]
+            || stateblock->state.render_states[WINED3DRS_WRAP12]
+            || stateblock->state.render_states[WINED3DRS_WRAP13]
+            || stateblock->state.render_states[WINED3DRS_WRAP14]
+            || stateblock->state.render_states[WINED3DRS_WRAP15])
+    {
+        FIXME("(WINED3DRS_WRAP0) Texture wrapping not yet supported.\n");
     }
 }
 
 static void state_msaa_w(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_MULTISAMPLEANTIALIAS]) {
+    if (stateblock->state.render_states[WINED3DRS_MULTISAMPLEANTIALIAS])
         WARN("Multisample antialiasing not supported by gl\n");
-    }
 }
 
 static void state_msaa(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_MULTISAMPLEANTIALIAS]) {
+    if (stateblock->state.render_states[WINED3DRS_MULTISAMPLEANTIALIAS])
+    {
         glEnable(GL_MULTISAMPLE_ARB);
         checkGLcall("glEnable(GL_MULTISAMPLE_ARB)");
     } else {
@@ -1686,7 +1758,8 @@ static void state_msaa(DWORD state, IWineD3DStateBlockImpl *stateblock, struct w
 
 static void state_scissor(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_SCISSORTESTENABLE]) {
+    if (stateblock->state.render_states[WINED3DRS_SCISSORTESTENABLE])
+    {
         glEnable(GL_SCISSOR_TEST);
         checkGLcall("glEnable(GL_SCISSOR_TEST)");
     } else {
@@ -1706,8 +1779,8 @@ static void state_scissor(DWORD state, IWineD3DStateBlockImpl *stateblock, struc
  * need to be scaled. */
 static void state_depthbias(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if (stateblock->renderState[WINED3DRS_SLOPESCALEDEPTHBIAS]
-            || stateblock->renderState[WINED3DRS_DEPTHBIAS])
+    if (stateblock->state.render_states[WINED3DRS_SLOPESCALEDEPTHBIAS]
+            || stateblock->state.render_states[WINED3DRS_DEPTHBIAS])
     {
         union
         {
@@ -1715,8 +1788,8 @@ static void state_depthbias(DWORD state, IWineD3DStateBlockImpl *stateblock, str
             float f;
         } scale_bias, const_bias;
 
-        scale_bias.d = stateblock->renderState[WINED3DRS_SLOPESCALEDEPTHBIAS];
-        const_bias.d = stateblock->renderState[WINED3DRS_DEPTHBIAS];
+        scale_bias.d = stateblock->state.render_states[WINED3DRS_SLOPESCALEDEPTHBIAS];
+        const_bias.d = stateblock->state.render_states[WINED3DRS_DEPTHBIAS];
 
         glEnable(GL_POLYGON_OFFSET_FILL);
         checkGLcall("glEnable(GL_POLYGON_OFFSET_FILL)");
@@ -1731,13 +1804,14 @@ static void state_depthbias(DWORD state, IWineD3DStateBlockImpl *stateblock, str
 
 static void state_zvisible(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if (stateblock->renderState[WINED3DRS_ZVISIBLE])
+    if (stateblock->state.render_states[WINED3DRS_ZVISIBLE])
         FIXME("WINED3DRS_ZVISIBLE not implemented.\n");
 }
 
 static void state_perspective(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if (stateblock->renderState[WINED3DRS_TEXTUREPERSPECTIVE]) {
+    if (stateblock->state.render_states[WINED3DRS_TEXTUREPERSPECTIVE])
+    {
         glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
         checkGLcall("glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST)");
     } else {
@@ -1748,30 +1822,28 @@ static void state_perspective(DWORD state, IWineD3DStateBlockImpl *stateblock, s
 
 static void state_stippledalpha(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    TRACE("Stub\n");
-    if (stateblock->renderState[WINED3DRS_STIPPLEDALPHA])
+    if (stateblock->state.render_states[WINED3DRS_STIPPLEDALPHA])
         FIXME(" Stippled Alpha not supported yet.\n");
 }
 
 static void state_antialias(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    TRACE("Stub\n");
-    if (stateblock->renderState[WINED3DRS_ANTIALIAS])
-        FIXME(" Antialias not supported yet.\n");
+    if (stateblock->state.render_states[WINED3DRS_ANTIALIAS])
+        FIXME("Antialias not supported yet.\n");
 }
 
 static void state_multisampmask(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    TRACE("Stub\n");
-    if (stateblock->renderState[WINED3DRS_MULTISAMPLEMASK] != 0xFFFFFFFF)
-        FIXME("(WINED3DRS_MULTISAMPLEMASK,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_MULTISAMPLEMASK]);
+    if (stateblock->state.render_states[WINED3DRS_MULTISAMPLEMASK] != 0xffffffff)
+        FIXME("WINED3DRS_MULTISAMPLEMASK %#x not yet implemented.\n",
+                stateblock->state.render_states[WINED3DRS_MULTISAMPLEMASK]);
 }
 
 static void state_patchedgestyle(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    TRACE("Stub\n");
-    if (stateblock->renderState[WINED3DRS_PATCHEDGESTYLE] != WINED3DPATCHEDGE_DISCRETE)
-        FIXME("(WINED3DRS_PATCHEDGESTYLE,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_PATCHEDGESTYLE]);
+    if (stateblock->state.render_states[WINED3DRS_PATCHEDGESTYLE] != WINED3DPATCHEDGE_DISCRETE)
+        FIXME("WINED3DRS_PATCHEDGESTYLE %#x not yet implemented.\n",
+                stateblock->state.render_states[WINED3DRS_PATCHEDGESTYLE]);
 }
 
 static void state_patchsegments(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
@@ -1782,12 +1854,11 @@ static void state_patchsegments(DWORD state, IWineD3DStateBlockImpl *stateblock,
     } tmpvalue;
     tmpvalue.f = 1.0f;
 
-    TRACE("Stub\n");
-    if (stateblock->renderState[WINED3DRS_PATCHSEGMENTS] != tmpvalue.d)
+    if (stateblock->state.render_states[WINED3DRS_PATCHSEGMENTS] != tmpvalue.d)
     {
         static BOOL displayed = FALSE;
 
-        tmpvalue.d = stateblock->renderState[WINED3DRS_PATCHSEGMENTS];
+        tmpvalue.d = stateblock->state.render_states[WINED3DRS_PATCHSEGMENTS];
         if(!displayed)
             FIXME("(WINED3DRS_PATCHSEGMENTS,%f) not yet implemented\n", tmpvalue.f);
 
@@ -1797,129 +1868,149 @@ static void state_patchsegments(DWORD state, IWineD3DStateBlockImpl *stateblock,
 
 static void state_positiondegree(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    TRACE("Stub\n");
-    if (stateblock->renderState[WINED3DRS_POSITIONDEGREE] != WINED3DDEGREE_CUBIC)
-        FIXME("(WINED3DRS_POSITIONDEGREE,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_POSITIONDEGREE]);
+    if (stateblock->state.render_states[WINED3DRS_POSITIONDEGREE] != WINED3DDEGREE_CUBIC)
+        FIXME("WINED3DRS_POSITIONDEGREE %#x not yet implemented.\n",
+                stateblock->state.render_states[WINED3DRS_POSITIONDEGREE]);
 }
 
 static void state_normaldegree(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    TRACE("Stub\n");
-    if (stateblock->renderState[WINED3DRS_NORMALDEGREE] != WINED3DDEGREE_LINEAR)
-        FIXME("(WINED3DRS_NORMALDEGREE,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_NORMALDEGREE]);
+    if (stateblock->state.render_states[WINED3DRS_NORMALDEGREE] != WINED3DDEGREE_LINEAR)
+        FIXME("WINED3DRS_NORMALDEGREE %#x not yet implemented.\n",
+                stateblock->state.render_states[WINED3DRS_NORMALDEGREE]);
 }
 
 static void state_tessellation(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    TRACE("Stub\n");
-    if(stateblock->renderState[WINED3DRS_ENABLEADAPTIVETESSELLATION])
-        FIXME("(WINED3DRS_ENABLEADAPTIVETESSELLATION,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_ENABLEADAPTIVETESSELLATION]);
+    if (stateblock->state.render_states[WINED3DRS_ENABLEADAPTIVETESSELLATION])
+        FIXME("WINED3DRS_ENABLEADAPTIVETESSELLATION %#x not yet implemented.\n",
+                stateblock->state.render_states[WINED3DRS_ENABLEADAPTIVETESSELLATION]);
 }
 
-static void state_wrapu(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void state_nvdb(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_WRAPU]) {
-        FIXME("Render state WINED3DRS_WRAPU not implemented yet\n");
+    union {
+        DWORD d;
+        float f;
+    } zmin, zmax;
+
+    const struct wined3d_gl_info *gl_info = context->gl_info;
+
+    if (stateblock->state.render_states[WINED3DRS_ADAPTIVETESS_X] == WINED3DFMT_NVDB)
+    {
+        zmin.d = stateblock->state.render_states[WINED3DRS_ADAPTIVETESS_Z];
+        zmax.d = stateblock->state.render_states[WINED3DRS_ADAPTIVETESS_W];
+
+        /* If zmin is larger than zmax INVALID_VALUE error is generated.
+         * In d3d9 test is not performed in this case*/
+        if (zmin.f <= zmax.f)
+        {
+            glEnable(GL_DEPTH_BOUNDS_TEST_EXT);
+            checkGLcall("glEnable(GL_DEPTH_BOUNDS_TEST_EXT)");
+            GL_EXTCALL(glDepthBoundsEXT(zmin.f, zmax.f));
+            checkGLcall("glDepthBoundsEXT(...)");
+        }
+        else {
+            glDisable(GL_DEPTH_BOUNDS_TEST_EXT);
+            checkGLcall("glDisable(GL_DEPTH_BOUNDS_TEST_EXT)");
+        }
     }
+    else {
+        glDisable(GL_DEPTH_BOUNDS_TEST_EXT);
+        checkGLcall("glDisable(GL_DEPTH_BOUNDS_TEST_EXT)");
+    }
+
+    state_tessellation(state, stateblock, context);
+}
+
+static void state_wrapu(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+{
+    if (stateblock->state.render_states[WINED3DRS_WRAPU])
+        FIXME("Render state WINED3DRS_WRAPU not implemented yet.\n");
 }
 
 static void state_wrapv(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_WRAPV]) {
-        FIXME("Render state WINED3DRS_WRAPV not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_WRAPV])
+        FIXME("Render state WINED3DRS_WRAPV not implemented yet.\n");
 }
 
 static void state_monoenable(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_MONOENABLE]) {
-        FIXME("Render state WINED3DRS_MONOENABLE not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_MONOENABLE])
+        FIXME("Render state WINED3DRS_MONOENABLE not implemented yet.\n");
 }
 
 static void state_rop2(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_ROP2]) {
-        FIXME("Render state WINED3DRS_ROP2 not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_ROP2])
+        FIXME("Render state WINED3DRS_ROP2 not implemented yet.\n");
 }
 
 static void state_planemask(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_PLANEMASK]) {
-        FIXME("Render state WINED3DRS_PLANEMASK not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_PLANEMASK])
+        FIXME("Render state WINED3DRS_PLANEMASK not implemented yet.\n");
 }
 
 static void state_subpixel(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_SUBPIXEL]) {
-        FIXME("Render state WINED3DRS_SUBPIXEL not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_SUBPIXEL])
+        FIXME("Render state WINED3DRS_SUBPIXEL not implemented yet.\n");
 }
 
 static void state_subpixelx(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_SUBPIXELX]) {
-        FIXME("Render state WINED3DRS_SUBPIXELX not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_SUBPIXELX])
+        FIXME("Render state WINED3DRS_SUBPIXELX not implemented yet.\n");
 }
 
 static void state_stippleenable(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_STIPPLEENABLE]) {
-        FIXME("Render state WINED3DRS_STIPPLEENABLE not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_STIPPLEENABLE])
+        FIXME("Render state WINED3DRS_STIPPLEENABLE not implemented yet.\n");
 }
 
 static void state_mipmaplodbias(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_MIPMAPLODBIAS]) {
-        FIXME("Render state WINED3DRS_MIPMAPLODBIAS not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_MIPMAPLODBIAS])
+        FIXME("Render state WINED3DRS_MIPMAPLODBIAS not implemented yet.\n");
 }
 
 static void state_anisotropy(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_ANISOTROPY]) {
-        FIXME("Render state WINED3DRS_ANISOTROPY not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_ANISOTROPY])
+        FIXME("Render state WINED3DRS_ANISOTROPY not implemented yet.\n");
 }
 
 static void state_flushbatch(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_FLUSHBATCH]) {
-        FIXME("Render state WINED3DRS_FLUSHBATCH not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_FLUSHBATCH])
+        FIXME("Render state WINED3DRS_FLUSHBATCH not implemented yet.\n");
 }
 
 static void state_translucentsi(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_TRANSLUCENTSORTINDEPENDENT]) {
-        FIXME("Render state WINED3DRS_TRANSLUCENTSORTINDEPENDENT not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_TRANSLUCENTSORTINDEPENDENT])
+        FIXME("Render state WINED3DRS_TRANSLUCENTSORTINDEPENDENT not implemented yet.\n");
 }
 
 static void state_extents(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_EXTENTS]) {
-        FIXME("Render state WINED3DRS_EXTENTS not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_EXTENTS])
+        FIXME("Render state WINED3DRS_EXTENTS not implemented yet.\n");
 }
 
 static void state_ckeyblend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if(stateblock->renderState[WINED3DRS_COLORKEYBLENDENABLE]) {
-        FIXME("Render state WINED3DRS_COLORKEYBLENDENABLE not implemented yet\n");
-    }
+    if (stateblock->state.render_states[WINED3DRS_COLORKEYBLENDENABLE])
+        FIXME("Render state WINED3DRS_COLORKEYBLENDENABLE not implemented yet.\n");
 }
 
 static void state_swvp(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    if (stateblock->renderState[WINED3DRS_SOFTWAREVERTEXPROCESSING])
-    {
+    if (stateblock->state.render_states[WINED3DRS_SOFTWAREVERTEXPROCESSING])
         FIXME("Software vertex processing not implemented.\n");
-    }
 }
 
 /* Set texture operations up - The following avoids lots of ifdefs in this routine!*/
@@ -1970,10 +2061,9 @@ static void get_src_and_opr(DWORD arg, BOOL is_alpha, GLenum* source, GLenum* op
 }
 
 /* Setup the texture operations texture stage states */
-static void set_tex_op(const struct wined3d_context *context, IWineD3DDevice *iface,
+static void set_tex_op(const struct wined3d_gl_info *gl_info, const struct wined3d_state *state,
         BOOL isAlpha, int Stage, WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3)
 {
-    const struct wined3d_gl_info *gl_info = context->gl_info;
     GLenum src1, src2, src3;
     GLenum opr1, opr2, opr3;
     GLenum comb_target;
@@ -1982,7 +2072,6 @@ static void set_tex_op(const struct wined3d_context *context, IWineD3DDevice *if
     GLenum scal_target;
     GLenum opr=0, invopr, src3_target, opr3_target;
     BOOL Handled = FALSE;
-    IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
 
     TRACE("Alpha?(%d), Stage:%d Op(%s), a1(%d), a2(%d), a3(%d)\n", isAlpha, Stage, debug_d3dtop(op), arg1, arg2, arg3);
 
@@ -2022,12 +2111,14 @@ static void set_tex_op(const struct wined3d_context *context, IWineD3DDevice *if
 
         /* If a texture stage references an invalid texture unit the stage just
         * passes through the result from the previous stage */
-    if (is_invalid_op(This, Stage, op, arg1, arg2, arg3)) {
+    if (is_invalid_op(state, Stage, op, arg1, arg2, arg3))
+    {
         arg1 = WINED3DTA_CURRENT;
         op = WINED3DTOP_SELECTARG1;
     }
 
-    if (isAlpha && This->stateBlock->textures[Stage] == NULL && arg1 == WINED3DTA_TEXTURE) {
+    if (isAlpha && !state->textures[Stage] && arg1 == WINED3DTA_TEXTURE)
+    {
         get_src_and_opr(WINED3DTA_DIFFUSE, isAlpha, &src1, &opr1);
     } else {
         get_src_and_opr(arg1, isAlpha, &src1, &opr1);
@@ -2968,11 +3059,10 @@ static void set_tex_op(const struct wined3d_context *context, IWineD3DDevice *if
         {
             DWORD op2;
 
-            if (isAlpha) {
-                op2 = This->stateBlock->textureState[Stage][WINED3DTSS_COLOROP];
-            } else {
-                op2 = This->stateBlock->textureState[Stage][WINED3DTSS_ALPHAOP];
-            }
+            if (isAlpha)
+                op2 = state->texture_states[Stage][WINED3DTSS_COLOROP];
+            else
+                op2 = state->texture_states[Stage][WINED3DTSS_ALPHAOP];
 
             /* Note: If COMBINE4 in effect can't go back to combine! */
             switch (op2) {
@@ -3010,17 +3100,18 @@ static void set_tex_op(const struct wined3d_context *context, IWineD3DDevice *if
 }
 
 
-static void tex_colorop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void tex_colorop(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
+    DWORD stage = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
     BOOL tex_used = stateblock->device->fixed_function_usage_map & (1 << stage);
     DWORD mapped_stage = stateblock->device->texUnitMap[stage];
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
 
     TRACE("Setting color op for stage %d\n", stage);
 
     /* Using a pixel shader? Don't care for anything here, the shader applying does it */
-    if (use_ps(stateblock)) return;
+    if (use_ps(state)) return;
 
     if (stage != mapped_stage) WARN("Using non 1:1 mapping: %d -> %d!\n", stage, mapped_stage);
 
@@ -3035,7 +3126,8 @@ static void tex_colorop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         checkGLcall("glActiveTextureARB");
     }
 
-    if(stage >= stateblock->lowest_disabled_stage) {
+    if (stage >= state->lowest_disabled_stage)
+    {
         TRACE("Stage disabled\n");
         if (mapped_stage != WINED3D_UNMAPPED_STAGE)
         {
@@ -3059,18 +3151,16 @@ static void tex_colorop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
         return;
     }
 
-    /* The sampler will also activate the correct texture dimensions, so no need to do it here
-     * if the sampler for this stage is dirty
-     */
-    if(!isStateDirty(context, STATE_SAMPLER(stage))) {
-        if (tex_used) texture_activate_dimensions(stage, stateblock, context);
-    }
+    /* The sampler will also activate the correct texture dimensions, so no
+     * need to do it here if the sampler for this stage is dirty. */
+    if (!isStateDirty(context, STATE_SAMPLER(stage)) && tex_used)
+        texture_activate_dimensions(state->textures[stage], gl_info);
 
-    set_tex_op(context, (IWineD3DDevice *)stateblock->device, FALSE, stage,
-                stateblock->textureState[stage][WINED3DTSS_COLOROP],
-                stateblock->textureState[stage][WINED3DTSS_COLORARG1],
-                stateblock->textureState[stage][WINED3DTSS_COLORARG2],
-                stateblock->textureState[stage][WINED3DTSS_COLORARG0]);
+    set_tex_op(gl_info, state, FALSE, stage,
+            state->texture_states[stage][WINED3DTSS_COLOROP],
+            state->texture_states[stage][WINED3DTSS_COLORARG1],
+            state->texture_states[stage][WINED3DTSS_COLORARG2],
+            state->texture_states[stage][WINED3DTSS_COLORARG0]);
 }
 
 void tex_alphaop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
@@ -3094,21 +3184,21 @@ void tex_alphaop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d
         checkGLcall("glActiveTextureARB");
     }
 
-    op = stateblock->textureState[stage][WINED3DTSS_ALPHAOP];
-    arg1 = stateblock->textureState[stage][WINED3DTSS_ALPHAARG1];
-    arg2 = stateblock->textureState[stage][WINED3DTSS_ALPHAARG2];
-    arg0 = stateblock->textureState[stage][WINED3DTSS_ALPHAARG0];
+    op = stateblock->state.texture_states[stage][WINED3DTSS_ALPHAOP];
+    arg1 = stateblock->state.texture_states[stage][WINED3DTSS_ALPHAARG1];
+    arg2 = stateblock->state.texture_states[stage][WINED3DTSS_ALPHAARG2];
+    arg0 = stateblock->state.texture_states[stage][WINED3DTSS_ALPHAARG0];
 
-    if (stateblock->renderState[WINED3DRS_COLORKEYENABLE] && stage == 0 && stateblock->textures[0])
+    if (stateblock->state.render_states[WINED3DRS_COLORKEYENABLE] && !stage && stateblock->state.textures[0])
     {
-        UINT texture_dimensions = IWineD3DBaseTexture_GetTextureDimensions(stateblock->textures[0]);
+        IWineD3DBaseTextureImpl *texture = stateblock->state.textures[0];
+        GLenum texture_dimensions = texture->baseTexture.target;
 
         if (texture_dimensions == GL_TEXTURE_2D || texture_dimensions == GL_TEXTURE_RECTANGLE_ARB)
         {
-            IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)stateblock->textures[0];
             IWineD3DSurfaceImpl *surf = (IWineD3DSurfaceImpl *)texture->baseTexture.sub_resources[0];
 
-            if (surf->CKeyFlags & WINEDDSD_CKSRCBLT && !surf->resource.format_desc->alpha_mask)
+            if (surf->CKeyFlags & WINEDDSD_CKSRCBLT && !surf->resource.format->alpha_mask)
             {
                 /* Color keying needs to pass alpha values from the texture through to have the alpha test work
                  * properly. On the other hand applications can still use texture combiners apparently. This code
@@ -3139,7 +3229,7 @@ void tex_alphaop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d
                 }
                 else if(op == WINED3DTOP_SELECTARG1 && arg1 != WINED3DTA_TEXTURE)
                 {
-                    if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE])
+                    if (stateblock->state.render_states[WINED3DRS_ALPHABLENDENABLE])
                     {
                         arg2 = WINED3DTA_TEXTURE;
                         op = WINED3DTOP_MODULATE;
@@ -3148,7 +3238,7 @@ void tex_alphaop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d
                 }
                 else if(op == WINED3DTOP_SELECTARG2 && arg2 != WINED3DTA_TEXTURE)
                 {
-                    if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE])
+                    if (stateblock->state.render_states[WINED3DRS_ALPHABLENDENABLE])
                     {
                         arg1 = WINED3DTA_TEXTURE;
                         op = WINED3DTOP_MODULATE;
@@ -3165,25 +3255,26 @@ void tex_alphaop(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d
     TRACE("Setting alpha op for stage %d\n", stage);
     if (gl_info->supported[NV_REGISTER_COMBINERS])
     {
-        set_tex_op_nvrc((IWineD3DDevice *)stateblock->device, TRUE, stage, op, arg1, arg2, arg0,
-                mapped_stage, stateblock->textureState[stage][WINED3DTSS_RESULTARG]);
+        set_tex_op_nvrc(gl_info, &stateblock->state, TRUE, stage, op, arg1, arg2, arg0,
+                mapped_stage, stateblock->state.texture_states[stage][WINED3DTSS_RESULTARG]);
     }
     else
     {
-        set_tex_op(context, (IWineD3DDevice *)stateblock->device, TRUE, stage, op, arg1, arg2, arg0);
+        set_tex_op(gl_info, &stateblock->state, TRUE, stage, op, arg1, arg2, arg0);
     }
 }
 
-static void transform_texture(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void transform_texture(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD texUnit = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
+    DWORD texUnit = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
     DWORD mapped_stage = stateblock->device->texUnitMap[texUnit];
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
     BOOL generated;
     int coordIdx;
 
     /* Ignore this when a vertex shader is used, or if the streams aren't sorted out yet */
-    if (use_vs(stateblock) || isStateDirty(context, STATE_VDECL))
+    if (use_vs(state) || isStateDirty(context, STATE_VDECL))
     {
         TRACE("Using a vertex shader, or stream sources not sorted out yet, skipping\n");
         return;
@@ -3194,27 +3285,29 @@ static void transform_texture(DWORD state, IWineD3DStateBlockImpl *stateblock, s
 
     GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
     checkGLcall("glActiveTextureARB");
-    generated = (stateblock->textureState[texUnit][WINED3DTSS_TEXCOORDINDEX] & 0xFFFF0000) != WINED3DTSS_TCI_PASSTHRU;
-    coordIdx = min(stateblock->textureState[texUnit][WINED3DTSS_TEXCOORDINDEX & 0x0000FFFF], MAX_TEXTURES - 1);
+    generated = (state->texture_states[texUnit][WINED3DTSS_TEXCOORDINDEX] & 0xffff0000) != WINED3DTSS_TCI_PASSTHRU;
+    coordIdx = min(state->texture_states[texUnit][WINED3DTSS_TEXCOORDINDEX & 0x0000ffff], MAX_TEXTURES - 1);
 
-    set_texture_matrix(&stateblock->transforms[WINED3DTS_TEXTURE0 + texUnit].u.m[0][0],
-            stateblock->textureState[texUnit][WINED3DTSS_TEXTURETRANSFORMFLAGS], generated, context->last_was_rhw,
+    set_texture_matrix(&state->transforms[WINED3DTS_TEXTURE0 + texUnit].u.m[0][0],
+            state->texture_states[texUnit][WINED3DTSS_TEXTURETRANSFORMFLAGS],
+            generated, context->last_was_rhw,
             stateblock->device->strided_streams.use_map & (1 << (WINED3D_FFP_TEXCOORD0 + coordIdx))
-            ? stateblock->device->strided_streams.elements[WINED3D_FFP_TEXCOORD0 + coordIdx].format_desc->format
+            ? stateblock->device->strided_streams.elements[WINED3D_FFP_TEXCOORD0 + coordIdx].format->id
             : WINED3DFMT_UNKNOWN,
             stateblock->device->frag_pipe->ffp_proj_control);
 
     /* The sampler applying function calls us if this changes */
-    if ((context->lastWasPow2Texture & (1 << texUnit)) && stateblock->textures[texUnit])
+    if ((context->lastWasPow2Texture & (1 << texUnit)) && state->textures[texUnit])
     {
         if(generated) {
             FIXME("Non-power2 texture being used with generated texture coords\n");
         }
         /* NP2 texcoord fixup is implemented for pixelshaders so only enable the
            fixed-function-pipeline fixup via pow2Matrix when no PS is used. */
-        if (!use_ps(stateblock)) {
+        if (!use_ps(state))
+        {
             TRACE("Non power two matrix multiply fixup\n");
-            glMultMatrixf(((IWineD3DTextureImpl *) stateblock->textures[texUnit])->baseTexture.pow2Matrix);
+            glMultMatrixf(state->textures[texUnit]->baseTexture.pow2Matrix);
         }
     }
 }
@@ -3233,13 +3326,12 @@ static void unloadTexCoords(const struct wined3d_gl_info *gl_info)
 static void loadTexCoords(const struct wined3d_gl_info *gl_info, IWineD3DStateBlockImpl *stateblock,
         const struct wined3d_stream_info *si, GLuint *curVBO)
 {
-    const UINT *offset = stateblock->streamOffset;
     unsigned int mapped_stage = 0;
     unsigned int textureNo = 0;
 
     for (textureNo = 0; textureNo < gl_info->limits.texture_stages; ++textureNo)
     {
-        int coordIdx = stateblock->textureState[textureNo][WINED3DTSS_TEXCOORDINDEX];
+        int coordIdx = stateblock->state.texture_states[textureNo][WINED3DTSS_TEXCOORDINDEX];
 
         mapped_stage = stateblock->device->texUnitMap[textureNo];
         if (mapped_stage == WINED3D_UNMAPPED_STAGE) continue;
@@ -3247,6 +3339,7 @@ static void loadTexCoords(const struct wined3d_gl_info *gl_info, IWineD3DStateBl
         if (coordIdx < MAX_TEXTURES && (si->use_map & (1 << (WINED3D_FFP_TEXCOORD0 + coordIdx))))
         {
             const struct wined3d_stream_info_element *e = &si->elements[WINED3D_FFP_TEXCOORD0 + coordIdx];
+            const struct wined3d_stream_state *stream = &stateblock->state.streams[e->stream_idx];
 
             TRACE("Setting up texture %u, idx %d, cordindx %u, data %p\n",
                     textureNo, mapped_stage, coordIdx, e->data);
@@ -3262,8 +3355,8 @@ static void loadTexCoords(const struct wined3d_gl_info *gl_info, IWineD3DStateBl
             checkGLcall("glClientActiveTextureARB");
 
             /* The coords to supply depend completely on the fvf / vertex shader */
-            glTexCoordPointer(e->format_desc->gl_vtx_format, e->format_desc->gl_vtx_type, e->stride,
-                    e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
+            glTexCoordPointer(e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
+                    e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
             glEnableClientState(GL_TEXTURE_COORD_ARRAY);
         } else {
             GL_EXTCALL(glMultiTexCoord4fARB(GL_TEXTURE0_ARB + mapped_stage, 0, 0, 0, 1));
@@ -3314,7 +3407,7 @@ static void tex_coordindex(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
      * state. We do not (yet) support the WINED3DRENDERSTATE_WRAPx values, nor tie them up
      * to the TEXCOORDINDEX value
      */
-    switch (stateblock->textureState[stage][WINED3DTSS_TEXCOORDINDEX] & 0xffff0000)
+    switch (stateblock->state.texture_states[stage][WINED3DTSS_TEXCOORDINDEX] & 0xffff0000)
     {
         case WINED3DTSS_TCI_PASSTHRU:
             /* Use the specified texture coordinates contained within the
@@ -3428,8 +3521,8 @@ static void tex_coordindex(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
             break;
 
         default:
-            FIXME("Unhandled WINED3DTSS_TEXCOORDINDEX %#x\n",
-                    stateblock->textureState[stage][WINED3DTSS_TEXCOORDINDEX]);
+            FIXME("Unhandled WINED3DTSS_TEXCOORDINDEX %#x.\n",
+                    stateblock->state.texture_states[stage][WINED3DTSS_TEXCOORDINDEX]);
             glDisable(GL_TEXTURE_GEN_S);
             glDisable(GL_TEXTURE_GEN_T);
             glDisable(GL_TEXTURE_GEN_R);
@@ -3457,8 +3550,9 @@ static void tex_coordindex(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
     }
 }
 
-static void shaderconstant(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void shaderconstant(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
+    const struct wined3d_state *state = &stateblock->state;
     IWineD3DDeviceImpl *device = stateblock->device;
 
     /* Vertex and pixel shader states will call a shader upload, don't do anything as long one of them
@@ -3469,15 +3563,15 @@ static void shaderconstant(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
        return;
     }
 
-    device->shader_backend->shader_load_constants(context, use_ps(stateblock), use_vs(stateblock));
+    device->shader_backend->shader_load_constants(context, use_ps(state), use_vs(state));
 }
 
 static void tex_bumpenvlscale(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
+    IWineD3DPixelShaderImpl *ps = stateblock->state.pixel_shader;
 
-    if (stateblock->pixelShader && stage != 0
-            && (((IWineD3DPixelShaderImpl *)stateblock->pixelShader)->baseShader.reg_maps.luminanceparams & (1 << stage)))
+    if (ps && stage && (ps->baseShader.reg_maps.luminanceparams & (1 << stage)))
     {
         /* The pixel shader has to know the luminance scale. Do a constants update if it
          * isn't scheduled anyway
@@ -3492,7 +3586,7 @@ static void tex_bumpenvlscale(DWORD state, IWineD3DStateBlockImpl *stateblock, s
 static void sampler_texmatrix(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     const DWORD sampler = state - STATE_SAMPLER(0);
-    IWineD3DBaseTexture *texture = stateblock->textures[sampler];
+    IWineD3DBaseTextureImpl *texture = stateblock->state.textures[sampler];
 
     TRACE("state %#x, stateblock %p, context %p\n", state, stateblock, context);
 
@@ -3505,7 +3599,7 @@ static void sampler_texmatrix(DWORD state, IWineD3DStateBlockImpl *stateblock, s
      * misc pipeline
      */
     if(sampler < MAX_TEXTURES) {
-        const BOOL texIsPow2 = !((IWineD3DBaseTextureImpl *)texture)->baseTexture.pow2Matrix_identity;
+        const BOOL texIsPow2 = !texture->baseTexture.pow2Matrix_identity;
 
         if (texIsPow2 || (context->lastWasPow2Texture & (1 << sampler)))
         {
@@ -3517,11 +3611,12 @@ static void sampler_texmatrix(DWORD state, IWineD3DStateBlockImpl *stateblock, s
     }
 }
 
-static void sampler(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void sampler(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    DWORD sampler = state - STATE_SAMPLER(0);
+    DWORD sampler = state_id - STATE_SAMPLER(0);
     DWORD mapped_stage = stateblock->device->texUnitMap[sampler];
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
     union {
         float f;
         DWORD d;
@@ -3545,25 +3640,29 @@ static void sampler(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wine
     GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
     checkGLcall("glActiveTextureARB");
 
-    if(stateblock->textures[sampler]) {
-        BOOL srgb = stateblock->samplerState[sampler][WINED3DSAMP_SRGBTEXTURE];
-        IWineD3DBaseTextureImpl *tex_impl = (IWineD3DBaseTextureImpl *) stateblock->textures[sampler];
-        IWineD3DBaseTexture_BindTexture(stateblock->textures[sampler], srgb);
-        basetexture_apply_state_changes(stateblock->textures[sampler],
-                stateblock->textureState[sampler], stateblock->samplerState[sampler], gl_info);
+    if (state->textures[sampler])
+    {
+        IWineD3DBaseTexture *texture = (IWineD3DBaseTexture *)state->textures[sampler];
+        BOOL srgb = state->sampler_states[sampler][WINED3DSAMP_SRGBTEXTURE];
+
+        IWineD3DBaseTexture_BindTexture(texture, srgb);
+        basetexture_apply_state_changes(texture,
+                state->texture_states[sampler],
+                state->sampler_states[sampler], gl_info);
 
         if (gl_info->supported[EXT_TEXTURE_LOD_BIAS])
         {
-            tmpvalue.d = stateblock->samplerState[sampler][WINED3DSAMP_MIPMAPLODBIAS];
+            tmpvalue.d = state->sampler_states[sampler][WINED3DSAMP_MIPMAPLODBIAS];
             glTexEnvf(GL_TEXTURE_FILTER_CONTROL_EXT,
                       GL_TEXTURE_LOD_BIAS_EXT,
                       tmpvalue.f);
             checkGLcall("glTexEnvi(GL_TEXTURE_LOD_BIAS_EXT, ...)");
         }
 
-        if (!use_ps(stateblock) && sampler < stateblock->lowest_disabled_stage)
+        if (!use_ps(state) && sampler < state->lowest_disabled_stage)
         {
-            if(stateblock->renderState[WINED3DRS_COLORKEYENABLE] && sampler == 0) {
+            if (state->render_states[WINED3DRS_COLORKEYENABLE] && !sampler)
+            {
                 /* If color keying is enabled update the alpha test, it depends on the existence
                  * of a color key in stage 0
                  */
@@ -3572,18 +3671,20 @@ static void sampler(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wine
         }
 
         /* Trigger shader constant reloading (for NP2 texcoord fixup) */
-        if (!tex_impl->baseTexture.pow2Matrix_identity)
+        if (!state->textures[sampler]->baseTexture.pow2Matrix_identity)
         {
             IWineD3DDeviceImpl *d3ddevice = stateblock->device;
             d3ddevice->shader_backend->shader_load_np2fixup_constants(
-                (IWineD3DDevice*)d3ddevice, use_ps(stateblock), use_vs(stateblock));
+                (IWineD3DDevice*)d3ddevice, use_ps(state), use_vs(state));
         }
     }
     else if (mapped_stage < gl_info->limits.textures)
     {
-        if(sampler < stateblock->lowest_disabled_stage) {
+        if (sampler < state->lowest_disabled_stage)
+        {
             /* TODO: What should I do with pixel shaders here ??? */
-            if(stateblock->renderState[WINED3DRS_COLORKEYENABLE] && sampler == 0) {
+            if (state->render_states[WINED3DRS_COLORKEYENABLE] && !sampler)
+            {
                 /* If color keying is enabled update the alpha test, it depends on the existence
                 * of a color key in stage 0
                 */
@@ -3595,12 +3696,13 @@ static void sampler(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wine
     }
 }
 
-void apply_pixelshader(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+void apply_pixelshader(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
+    const struct wined3d_state *state = &stateblock->state;
     IWineD3DDeviceImpl *device = stateblock->device;
-    BOOL use_pshader = use_ps(stateblock);
-    BOOL use_vshader = use_vs(stateblock);
-    int i;
+    BOOL use_vshader = use_vs(state);
+    BOOL use_pshader = use_ps(state);
+    unsigned int i;
 
     if (use_pshader) {
         if(!context->last_was_pshader) {
@@ -3642,8 +3744,9 @@ void apply_pixelshader(DWORD state, IWineD3DStateBlockImpl *stateblock, struct w
 static void shader_bumpenvmat(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
-    if (stateblock->pixelShader && stage != 0
-            && (((IWineD3DPixelShaderImpl *)stateblock->pixelShader)->baseShader.reg_maps.bumpmat & (1 << stage)))
+    IWineD3DPixelShaderImpl *ps = stateblock->state.pixel_shader;
+
+    if (ps && stage && (ps->baseShader.reg_maps.bumpmat & (1 << stage)))
     {
         /* The pixel shader has to know the bump env matrix. Do a constants update if it isn't scheduled
          * anyway
@@ -3674,22 +3777,23 @@ static void transform_world(DWORD state, IWineD3DStateBlockImpl *stateblock, str
         /* In the general case, the view matrix is the identity matrix */
         if (stateblock->device->view_ident)
         {
-            glLoadMatrixf(&stateblock->transforms[WINED3DTS_WORLDMATRIX(0)].u.m[0][0]);
+            glLoadMatrixf(&stateblock->state.transforms[WINED3DTS_WORLDMATRIX(0)].u.m[0][0]);
             checkGLcall("glLoadMatrixf");
         }
         else
         {
-            glLoadMatrixf(&stateblock->transforms[WINED3DTS_VIEW].u.m[0][0]);
+            glLoadMatrixf(&stateblock->state.transforms[WINED3DTS_VIEW].u.m[0][0]);
             checkGLcall("glLoadMatrixf");
-            glMultMatrixf(&stateblock->transforms[WINED3DTS_WORLDMATRIX(0)].u.m[0][0]);
+            glMultMatrixf(&stateblock->state.transforms[WINED3DTS_WORLDMATRIX(0)].u.m[0][0]);
             checkGLcall("glMultMatrixf");
         }
     }
 }
 
-static void clipplane(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void clipplane(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    UINT index = state - STATE_CLIPPLANE(0);
+    const struct wined3d_state *state = &stateblock->state;
+    UINT index = state_id - STATE_CLIPPLANE(0);
 
     if (isStateDirty(context, STATE_TRANSFORM(WINED3DTS_VIEW)) || index >= context->gl_info->limits.clipplanes)
     {
@@ -3697,11 +3801,14 @@ static void clipplane(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wi
     }
 
     /* Clip Plane settings are affected by the model view in OpenGL, the View transform in direct3d */
-    if(!use_vs(stateblock)) {
+    if (!use_vs(state))
+    {
         glMatrixMode(GL_MODELVIEW);
         glPushMatrix();
-        glLoadMatrixf(&stateblock->transforms[WINED3DTS_VIEW].u.m[0][0]);
-    } else {
+        glLoadMatrixf(&state->transforms[WINED3DTS_VIEW].u.m[0][0]);
+    }
+    else
+    {
         /* with vertex shaders, clip planes are not transformed in direct3d,
          * in OpenGL they are still transformed by the model view.
          * Use this to swap the y coordinate if necessary
@@ -3712,12 +3819,12 @@ static void clipplane(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wi
         if (context->render_offscreen) glScalef(1.0f, -1.0f, 1.0f);
     }
 
-    TRACE("Clipplane [%f,%f,%f,%f]\n",
-          stateblock->clipplane[index][0],
-          stateblock->clipplane[index][1],
-          stateblock->clipplane[index][2],
-          stateblock->clipplane[index][3]);
-    glClipPlane(GL_CLIP_PLANE0 + index, stateblock->clipplane[index]);
+    TRACE("Clipplane [%.8e, %.8e, %.8e, %.8e]\n",
+            state->clip_planes[index][0],
+            state->clip_planes[index][1],
+            state->clip_planes[index][2],
+            state->clip_planes[index][3]);
+    glClipPlane(GL_CLIP_PLANE0 + index, state->clip_planes[index]);
     checkGLcall("glClipPlane");
 
     glPopMatrix();
@@ -3755,21 +3862,21 @@ static void transform_worldex(DWORD state, IWineD3DStateBlockImpl *stateblock, s
      */
     if (stateblock->device->view_ident)
     {
-        glLoadMatrixf(&stateblock->transforms[WINED3DTS_WORLDMATRIX(matrix)].u.m[0][0]);
+        glLoadMatrixf(&stateblock->state.transforms[WINED3DTS_WORLDMATRIX(matrix)].u.m[0][0]);
         checkGLcall("glLoadMatrixf");
     }
     else
     {
-        glLoadMatrixf(&stateblock->transforms[WINED3DTS_VIEW].u.m[0][0]);
+        glLoadMatrixf(&stateblock->state.transforms[WINED3DTS_VIEW].u.m[0][0]);
         checkGLcall("glLoadMatrixf");
-        glMultMatrixf(&stateblock->transforms[WINED3DTS_WORLDMATRIX(matrix)].u.m[0][0]);
+        glMultMatrixf(&stateblock->state.transforms[WINED3DTS_WORLDMATRIX(matrix)].u.m[0][0]);
         checkGLcall("glMultMatrixf");
     }
 }
 
 static void state_vertexblend_w(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    WINED3DVERTEXBLENDFLAGS f = stateblock->renderState[WINED3DRS_VERTEXBLEND];
+    WINED3DVERTEXBLENDFLAGS f = stateblock->state.render_states[WINED3DRS_VERTEXBLEND];
     static unsigned int once;
 
     if (f == WINED3DVBF_DISABLE) return;
@@ -3780,7 +3887,7 @@ static void state_vertexblend_w(DWORD state, IWineD3DStateBlockImpl *stateblock,
 
 static void state_vertexblend(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    WINED3DVERTEXBLENDFLAGS val = stateblock->renderState[WINED3DRS_VERTEXBLEND];
+    WINED3DVERTEXBLENDFLAGS val = stateblock->state.render_states[WINED3DRS_VERTEXBLEND];
     const struct wined3d_gl_info *gl_info = context->gl_info;
     static unsigned int once;
 
@@ -3794,7 +3901,7 @@ static void state_vertexblend(DWORD state, IWineD3DStateBlockImpl *stateblock, s
             /* D3D adds one more matrix which has weight (1 - sum(weights)). This is enabled at context
              * creation with enabling GL_WEIGHT_SUM_UNITY_ARB.
              */
-            GL_EXTCALL(glVertexBlendARB(stateblock->renderState[WINED3DRS_VERTEXBLEND] + 1));
+            GL_EXTCALL(glVertexBlendARB(stateblock->state.render_states[WINED3DRS_VERTEXBLEND] + 1));
 
             if (!stateblock->device->vertexBlendUsed)
             {
@@ -3836,13 +3943,13 @@ static void transform_view(DWORD state, IWineD3DStateBlockImpl *stateblock, stru
 
     glMatrixMode(GL_MODELVIEW);
     checkGLcall("glMatrixMode(GL_MODELVIEW)");
-    glLoadMatrixf(&stateblock->transforms[WINED3DTS_VIEW].u.m[0][0]);
+    glLoadMatrixf(&stateblock->state.transforms[WINED3DTS_VIEW].u.m[0][0]);
     checkGLcall("glLoadMatrixf(...)");
 
     /* Reset lights. TODO: Call light apply func */
     for (k = 0; k < stateblock->device->maxConcurrentLights; ++k)
     {
-        light = stateblock->activeLights[k];
+        light = stateblock->state.lights[k];
         if(!light) continue;
         glLightfv(GL_LIGHT0 + light->glIndex, GL_POSITION, light->lightPosn);
         checkGLcall("glLightfv posn");
@@ -3893,10 +4000,10 @@ static void transform_projection(DWORD state, IWineD3DStateBlockImpl *stateblock
 
     if (context->last_was_rhw)
     {
-        double x = stateblock->viewport.X;
-        double y = stateblock->viewport.Y;
-        double w = stateblock->viewport.Width;
-        double h = stateblock->viewport.Height;
+        double x = stateblock->state.viewport.X;
+        double y = stateblock->state.viewport.Y;
+        double w = stateblock->state.viewport.Width;
+        double h = stateblock->state.viewport.Height;
 
         TRACE("Calling glOrtho with x %.8e, y %.8e, w %.8e, h %.8e.\n", x, y, w, h);
         if (context->render_offscreen)
@@ -3905,10 +4012,6 @@ static void transform_projection(DWORD state, IWineD3DStateBlockImpl *stateblock
             glOrtho(x, x + w, y + h, y, 0.0, -1.0);
         checkGLcall("glOrtho");
 
-        /* Window Coord 0 is the middle of the first pixel, so translate by 1/2 pixels */
-        glTranslatef(63.0f / 128.0f, 63.0f / 128.0f, 0.0f);
-        checkGLcall("glTranslatef(63.0f / 128.0f, 63.0f / 128.0f, 0.0f)");
-
         /* D3D texture coordinates are flipped compared to OpenGL ones, so
          * render everything upside down when rendering offscreen. */
         if (context->render_offscreen)
@@ -3916,7 +4019,13 @@ static void transform_projection(DWORD state, IWineD3DStateBlockImpl *stateblock
             glScalef(1.0f, -1.0f, 1.0f);
             checkGLcall("glScalef");
         }
-    } else {
+
+        /* Window Coord 0 is the middle of the first pixel, so translate by 1/2 pixels */
+        glTranslatef(63.0f / 128.0f, 63.0f / 128.0f, 0.0f);
+        checkGLcall("glTranslatef(63.0f / 128.0f, 63.0f / 128.0f, 0.0f)");
+    }
+    else
+    {
         /* The rule is that the window coordinate 0 does not correspond to the
             beginning of the first pixel, but the center of the first pixel.
             As a consequence if you want to correctly draw one line exactly from
@@ -3958,8 +4067,8 @@ static void transform_projection(DWORD state, IWineD3DStateBlockImpl *stateblock
          * filling convention. We want the difference to be large enough that
          * it doesn't get lost due to rounding inside the driver, but small
          * enough to prevent it from interfering with any anti-aliasing. */
-        GLfloat xoffset = (63.0f / 64.0f) / stateblock->viewport.Width;
-        GLfloat yoffset = -(63.0f / 64.0f) / stateblock->viewport.Height;
+        GLfloat xoffset = (63.0f / 64.0f) / stateblock->state.viewport.Width;
+        GLfloat yoffset = -(63.0f / 64.0f) / stateblock->state.viewport.Height;
 
         if (context->render_offscreen)
         {
@@ -3975,7 +4084,7 @@ static void transform_projection(DWORD state, IWineD3DStateBlockImpl *stateblock
         }
         checkGLcall("glScalef");
 
-        glMultMatrixf(&stateblock->transforms[WINED3DTS_PROJECTION].u.m[0][0]);
+        glMultMatrixf(&stateblock->state.transforms[WINED3DTS_PROJECTION].u.m[0][0]);
         checkGLcall("glLoadMatrixf");
     }
 }
@@ -4034,22 +4143,26 @@ static inline void loadNumberedArrays(IWineD3DStateBlockImpl *stateblock,
     const struct wined3d_gl_info *gl_info = context->gl_info;
     GLuint curVBO = gl_info->supported[ARB_VERTEX_BUFFER_OBJECT] ? ~0U : 0;
     int i;
-    const UINT *offset = stateblock->streamOffset;
     struct wined3d_buffer *vb;
     DWORD_PTR shift_index;
 
     /* Default to no instancing */
     stateblock->device->instancedDraw = FALSE;
 
-    for (i = 0; i < MAX_ATTRIBS; i++) {
+    for (i = 0; i < MAX_ATTRIBS; i++)
+    {
+        const struct wined3d_stream_state *stream;
+
         if (!(stream_info->use_map & (1 << i)))
         {
             if (context->numbered_array_mask & (1 << i)) unload_numbered_array(context, i);
             continue;
         }
 
+        stream = &stateblock->state.streams[stream_info->elements[i].stream_idx];
+
         /* Do not load instance data. It will be specified using glTexCoord by drawprim */
-        if (stateblock->streamFlags[stream_info->elements[i].stream_idx] & WINED3DSTREAMSOURCE_INSTANCEDATA)
+        if (stream->flags & WINED3DSTREAMSOURCE_INSTANCEDATA)
         {
             if (context->numbered_array_mask & (1 << i)) unload_numbered_array(context, i);
             stateblock->device->instancedDraw = TRUE;
@@ -4066,11 +4179,11 @@ static inline void loadNumberedArrays(IWineD3DStateBlockImpl *stateblock,
                 checkGLcall("glBindBufferARB");
                 curVBO = stream_info->elements[i].buffer_object;
             }
-            vb = (struct wined3d_buffer *)stateblock->streamSource[stream_info->elements[i].stream_idx];
-            /* Use the VBO to find out if a vertex buffer exists, not the vb pointer. vb can point to a
-             * user pointer data blob. In that case curVBO will be 0. If there is a vertex buffer but no
-             * vbo we won't be load converted attributes anyway
-             */
+            /* Use the VBO to find out if a vertex buffer exists, not the vb
+             * pointer. vb can point to a user pointer data blob. In that case
+             * curVBO will be 0. If there is a vertex buffer but no vbo we
+             * won't be load converted attributes anyway. */
+            vb = stream->buffer;
             if (curVBO && vb->conversion_shift)
             {
                 TRACE("Loading attribute from shifted buffer\n");
@@ -4078,23 +4191,23 @@ static inline void loadNumberedArrays(IWineD3DStateBlockImpl *stateblock,
                         i, stream_info->elements[i].stride, vb->conversion_stride);
                 TRACE("Original offset %p, additional offset 0x%08x\n",
                         stream_info->elements[i].data, vb->conversion_shift[(DWORD_PTR)stream_info->elements[i].data]);
-                TRACE("Opengl type %#x\n", stream_info->elements[i].format_desc->gl_vtx_type);
-                shift_index = ((DWORD_PTR)stream_info->elements[i].data + offset[stream_info->elements[i].stream_idx]);
+                TRACE("Opengl type %#x\n", stream_info->elements[i].format->gl_vtx_type);
+                shift_index = ((DWORD_PTR)stream_info->elements[i].data + stream->offset);
                 shift_index = shift_index % stream_info->elements[i].stride;
-                GL_EXTCALL(glVertexAttribPointerARB(i, stream_info->elements[i].format_desc->gl_vtx_format,
-                        stream_info->elements[i].format_desc->gl_vtx_type,
-                        stream_info->elements[i].format_desc->gl_normalized,
+                GL_EXTCALL(glVertexAttribPointerARB(i, stream_info->elements[i].format->gl_vtx_format,
+                        stream_info->elements[i].format->gl_vtx_type,
+                        stream_info->elements[i].format->gl_normalized,
                         vb->conversion_stride, stream_info->elements[i].data + vb->conversion_shift[shift_index]
-                        + stateblock->loadBaseVertexIndex * stream_info->elements[i].stride
-                        + offset[stream_info->elements[i].stream_idx]));
+                        + stateblock->state.load_base_vertex_index * stream_info->elements[i].stride
+                        + stream->offset));
 
             } else {
-                GL_EXTCALL(glVertexAttribPointerARB(i, stream_info->elements[i].format_desc->gl_vtx_format,
-                        stream_info->elements[i].format_desc->gl_vtx_type,
-                        stream_info->elements[i].format_desc->gl_normalized,
+                GL_EXTCALL(glVertexAttribPointerARB(i, stream_info->elements[i].format->gl_vtx_format,
+                        stream_info->elements[i].format->gl_vtx_type,
+                        stream_info->elements[i].format->gl_normalized,
                         stream_info->elements[i].stride, stream_info->elements[i].data
-                        + stateblock->loadBaseVertexIndex * stream_info->elements[i].stride
-                        + offset[stream_info->elements[i].stream_idx]));
+                        + stateblock->state.load_base_vertex_index * stream_info->elements[i].stride
+                        + stream->offset));
             }
 
             if (!(context->numbered_array_mask & (1 << i)))
@@ -4102,20 +4215,23 @@ static inline void loadNumberedArrays(IWineD3DStateBlockImpl *stateblock,
                 GL_EXTCALL(glEnableVertexAttribArrayARB(i));
                 context->numbered_array_mask |= (1 << i);
             }
-        } else {
-            /* Stride = 0 means always the same values. glVertexAttribPointerARB doesn't do that. Instead disable the pointer and
-             * set up the attribute statically. But we have to figure out the system memory address.
-             */
-            const BYTE *ptr = stream_info->elements[i].data + offset[stream_info->elements[i].stream_idx];
+        }
+        else
+        {
+            /* Stride = 0 means always the same values.
+             * glVertexAttribPointerARB doesn't do that. Instead disable the
+             * pointer and set up the attribute statically. But we have to
+             * figure out the system memory address. */
+            const BYTE *ptr = stream_info->elements[i].data + stream->offset;
             if (stream_info->elements[i].buffer_object)
             {
-                vb = (struct wined3d_buffer *)stateblock->streamSource[stream_info->elements[i].stream_idx];
+                vb = stream->buffer;
                 ptr += (ULONG_PTR)buffer_get_sysmem(vb, gl_info);
             }
 
             if (context->numbered_array_mask & (1 << i)) unload_numbered_array(context, i);
 
-            switch (stream_info->elements[i].format_desc->format)
+            switch (stream_info->elements[i].format->id)
             {
                 case WINED3DFMT_R32_FLOAT:
                     GL_EXTCALL(glVertexAttrib1fvARB(i, (const GLfloat *)ptr));
@@ -4208,9 +4324,9 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
         const struct wined3d_stream_info *si)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
-    const UINT *offset = stateblock->streamOffset;
     GLuint curVBO = gl_info->supported[ARB_VERTEX_BUFFER_OBJECT] ? ~0U : 0;
     const struct wined3d_stream_info_element *e;
+    const struct wined3d_stream_state *stream;
 
     TRACE("Using fast vertex array code\n");
 
@@ -4222,16 +4338,17 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
             || si->use_map & (1 << WINED3D_FFP_BLENDINDICES))
     {
         e = &si->elements[WINED3D_FFP_BLENDWEIGHT];
+        stream = &stateblock->state.streams[e->stream_idx];
 
         if (gl_info->supported[ARB_VERTEX_BLEND])
         {
-            TRACE("Blend %d %p %d\n", e->format_desc->component_count,
-                    e->data + stateblock->loadBaseVertexIndex * e->stride, e->stride + offset[e->stream_idx]);
+            TRACE("Blend %u %p %u\n", e->format->component_count,
+                    e->data + stateblock->state.load_base_vertex_index * e->stride, e->stride + stream->offset);
 
             glEnableClientState(GL_WEIGHT_ARRAY_ARB);
             checkGLcall("glEnableClientState(GL_WEIGHT_ARRAY_ARB)");
 
-            GL_EXTCALL(glVertexBlendARB(e->format_desc->component_count + 1));
+            GL_EXTCALL(glVertexBlendARB(e->format->component_count + 1));
 
             if (curVBO != e->buffer_object)
             {
@@ -4241,12 +4358,12 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
             }
 
             TRACE("glWeightPointerARB(%#x, %#x, %#x, %p);\n",
-                    e->format_desc->gl_vtx_format,
-                    e->format_desc->gl_vtx_type,
+                    e->format->gl_vtx_format,
+                    e->format->gl_vtx_type,
                     e->stride,
-                    e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
-            GL_EXTCALL(glWeightPointerARB(e->format_desc->gl_vtx_format, e->format_desc->gl_vtx_type, e->stride,
-                    e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]));
+                    e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
+            GL_EXTCALL(glWeightPointerARB(e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
+                    e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset));
 
             checkGLcall("glWeightPointerARB");
 
@@ -4288,6 +4405,8 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
     if (si->use_map & (1 << WINED3D_FFP_POSITION))
     {
         e = &si->elements[WINED3D_FFP_POSITION];
+        stream = &stateblock->state.streams[e->stream_idx];
+
         if (curVBO != e->buffer_object)
         {
             GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, e->buffer_object));
@@ -4305,18 +4424,18 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
          */
         if (!e->buffer_object)
         {
-            TRACE("glVertexPointer(3, %#x, %#x, %p);\n", e->format_desc->gl_vtx_type, e->stride,
-                    e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
-            glVertexPointer(3 /* min(e->format_desc->gl_vtx_format, 3) */, e->format_desc->gl_vtx_type, e->stride,
-                    e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
+            TRACE("glVertexPointer(3, %#x, %#x, %p);\n", e->format->gl_vtx_type, e->stride,
+                    e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
+            glVertexPointer(3 /* min(e->format->gl_vtx_format, 3) */, e->format->gl_vtx_type, e->stride,
+                    e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
         }
         else
         {
             TRACE("glVertexPointer(%#x, %#x, %#x, %p);\n",
-                    e->format_desc->gl_vtx_format, e->format_desc->gl_vtx_type, e->stride,
-                    e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
-            glVertexPointer(e->format_desc->gl_vtx_format, e->format_desc->gl_vtx_type, e->stride,
-                    e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
+                    e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
+                    e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
+            glVertexPointer(e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
+                    e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
         }
         checkGLcall("glVertexPointer(...)");
         glEnableClientState(GL_VERTEX_ARRAY);
@@ -4327,6 +4446,8 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
     if (si->use_map & (1 << WINED3D_FFP_NORMAL))
     {
         e = &si->elements[WINED3D_FFP_NORMAL];
+        stream = &stateblock->state.streams[e->stream_idx];
+
         if (curVBO != e->buffer_object)
         {
             GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, e->buffer_object));
@@ -4334,10 +4455,10 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
             curVBO = e->buffer_object;
         }
 
-        TRACE("glNormalPointer(%#x, %#x, %p);\n", e->format_desc->gl_vtx_type, e->stride,
-                e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
-        glNormalPointer(e->format_desc->gl_vtx_type, e->stride,
-                e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
+        TRACE("glNormalPointer(%#x, %#x, %p);\n", e->format->gl_vtx_type, e->stride,
+                e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
+        glNormalPointer(e->format->gl_vtx_type, e->stride,
+                e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
         checkGLcall("glNormalPointer(...)");
         glEnableClientState(GL_NORMAL_ARRAY);
         checkGLcall("glEnableClientState(GL_NORMAL_ARRAY)");
@@ -4359,6 +4480,8 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
     if (si->use_map & (1 << WINED3D_FFP_DIFFUSE))
     {
         e = &si->elements[WINED3D_FFP_DIFFUSE];
+        stream = &stateblock->state.streams[e->stream_idx];
+
         if (curVBO != e->buffer_object)
         {
             GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, e->buffer_object));
@@ -4367,10 +4490,10 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
         }
 
         TRACE("glColorPointer(%#x, %#x %#x, %p);\n",
-                e->format_desc->gl_vtx_format, e->format_desc->gl_vtx_type, e->stride,
-                e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
-        glColorPointer(e->format_desc->gl_vtx_format, e->format_desc->gl_vtx_type, e->stride,
-                e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
+                e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
+                e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
+        glColorPointer(e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
+                e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
         checkGLcall("glColorPointer(4, GL_UNSIGNED_BYTE, ...)");
         glEnableClientState(GL_COLOR_ARRAY);
         checkGLcall("glEnableClientState(GL_COLOR_ARRAY)");
@@ -4386,10 +4509,12 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
         TRACE("setting specular colour\n");
 
         e = &si->elements[WINED3D_FFP_SPECULAR];
+        stream = &stateblock->state.streams[e->stream_idx];
+
         if (gl_info->supported[EXT_SECONDARY_COLOR])
         {
-            GLenum type = e->format_desc->gl_vtx_type;
-            GLint format = e->format_desc->gl_vtx_format;
+            GLenum type = e->format->gl_vtx_type;
+            GLint format = e->format->gl_vtx_format;
 
             if (curVBO != e->buffer_object)
             {
@@ -4406,9 +4531,9 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
                  * 4 component secondary colors use it
                  */
                 TRACE("glSecondaryColorPointer(%#x, %#x, %#x, %p);\n", format, type, e->stride,
-                        e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
+                        e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
                 GL_EXTCALL(glSecondaryColorPointerEXT(format, type, e->stride,
-                        e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]));
+                        e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset));
                 checkGLcall("glSecondaryColorPointerEXT(format, type, ...)");
             }
             else
@@ -4417,9 +4542,9 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
                 {
                     case GL_UNSIGNED_BYTE:
                         TRACE("glSecondaryColorPointer(3, GL_UNSIGNED_BYTE, %#x, %p);\n", e->stride,
-                                e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
+                                e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
                         GL_EXTCALL(glSecondaryColorPointerEXT(3, GL_UNSIGNED_BYTE, e->stride,
-                                e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]));
+                                e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset));
                         checkGLcall("glSecondaryColorPointerEXT(3, GL_UNSIGNED_BYTE, ...)");
                         break;
 
@@ -4427,9 +4552,9 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
                         FIXME("Add 4 component specular color pointers for type %x\n", type);
                         /* Make sure that the right color component is dropped */
                         TRACE("glSecondaryColorPointer(3, %#x, %#x, %p);\n", type, e->stride,
-                                e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]);
+                                e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset);
                         GL_EXTCALL(glSecondaryColorPointerEXT(3, type, e->stride,
-                                e->data + stateblock->loadBaseVertexIndex * e->stride + offset[e->stream_idx]));
+                                e->data + stateblock->state.load_base_vertex_index * e->stride + stream->offset));
                         checkGLcall("glSecondaryColorPointerEXT(3, type, ...)");
                 }
             }
@@ -4461,8 +4586,8 @@ static void loadVertexData(const struct wined3d_context *context, IWineD3DStateB
 static void streamsrc(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     IWineD3DDeviceImpl *device = stateblock->device;
-    BOOL load_numbered = use_vs(stateblock) && !device->useDrawStridedSlow;
-    BOOL load_named = !use_vs(stateblock) && !device->useDrawStridedSlow;
+    BOOL load_numbered = use_vs(&stateblock->state) && !device->useDrawStridedSlow;
+    BOOL load_named = !use_vs(&stateblock->state) && !device->useDrawStridedSlow;
 
     if (context->numberedArraysLoaded && !load_numbered)
     {
@@ -4490,12 +4615,13 @@ static void streamsrc(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wi
     }
 }
 
-static void vertexdeclaration(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+static void vertexdeclaration(DWORD state_id, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
+    const struct wined3d_state *state = &stateblock->state;
+    BOOL useVertexShaderFunction = use_vs(state);
+    BOOL usePixelShaderFunction = use_ps(state);
     BOOL updateFog = FALSE;
-    BOOL useVertexShaderFunction = use_vs(stateblock);
-    BOOL usePixelShaderFunction = use_ps(stateblock);
     IWineD3DDeviceImpl *device = stateblock->device;
     BOOL transformed;
     BOOL wasrhw = context->last_was_rhw;
@@ -4529,7 +4655,7 @@ static void vertexdeclaration(DWORD state, IWineD3DStateBlockImpl *stateblock, s
          */
         if (useVertexShaderFunction)
         {
-            GLfloat yoffset = -(63.0f / 64.0f) / stateblock->viewport.Height;
+            GLfloat yoffset = -(63.0f / 64.0f) / stateblock->state.viewport.Height;
             device->posFixup[1] = context->render_offscreen ? -1.0f : 1.0f;
             device->posFixup[3] = device->posFixup[1] * yoffset;
         }
@@ -4594,7 +4720,8 @@ static void vertexdeclaration(DWORD state, IWineD3DStateBlockImpl *stateblock, s
                     checkGLcall("glDisable(GL_CLIP_PLANE0 + i)");
                 }
 
-                if(!warned && stateblock->renderState[WINED3DRS_CLIPPLANEENABLE]) {
+                if (!warned && stateblock->state.render_states[WINED3DRS_CLIPPLANEENABLE])
+                {
                     FIXME("Clipping not supported with vertex shaders\n");
                     warned = TRUE;
                 }
@@ -4654,7 +4781,7 @@ static void viewport_miscpart(DWORD state, IWineD3DStateBlockImpl *stateblock, s
 {
     IWineD3DSurfaceImpl *target = stateblock->device->render_targets[0];
     UINT width, height;
-    WINED3DVIEWPORT vp = stateblock->viewport;
+    WINED3DVIEWPORT vp = stateblock->state.viewport;
 
     if(vp.Width > target->currentDesc.Width) vp.Width = target->currentDesc.Width;
     if(vp.Height > target->currentDesc.Height) vp.Height = target->currentDesc.Height;
@@ -4679,9 +4806,9 @@ static void viewport_miscpart(DWORD state, IWineD3DStateBlockImpl *stateblock, s
 
 static void viewport_vertexpart(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
-    GLfloat yoffset = -(63.0f / 64.0f) / stateblock->viewport.Height;
+    GLfloat yoffset = -(63.0f / 64.0f) / stateblock->state.viewport.Height;
 
-    stateblock->device->posFixup[2] = (63.0f / 64.0f) / stateblock->viewport.Width;
+    stateblock->device->posFixup[2] = (63.0f / 64.0f) / stateblock->state.viewport.Width;
     stateblock->device->posFixup[3] = stateblock->device->posFixup[1] * yoffset;
 
     if(!isStateDirty(context, STATE_TRANSFORM(WINED3DTS_PROJECTION))) {
@@ -4697,7 +4824,7 @@ static void viewport_vertexpart(DWORD state, IWineD3DStateBlockImpl *stateblock,
 static void light(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     UINT Index = state - STATE_ACTIVELIGHT(0);
-    const struct wined3d_light_info *lightInfo = stateblock->activeLights[Index];
+    const struct wined3d_light_info *lightInfo = stateblock->state.lights[Index];
 
     if(!lightInfo) {
         glDisable(GL_LIGHT0 + Index);
@@ -4709,7 +4836,7 @@ static void light(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3
         /* Light settings are affected by the model view in OpenGL, the View transform in direct3d*/
         glMatrixMode(GL_MODELVIEW);
         glPushMatrix();
-        glLoadMatrixf(&stateblock->transforms[WINED3DTS_VIEW].u.m[0][0]);
+        glLoadMatrixf(&stateblock->state.transforms[WINED3DTS_VIEW].u.m[0][0]);
 
         /* Diffuse: */
         colRGBA[0] = lightInfo->OriginalParms.Diffuse.r;
@@ -4811,7 +4938,7 @@ static void light(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3
 static void scissorrect(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
 {
     IWineD3DSurfaceImpl *target = stateblock->device->render_targets[0];
-    RECT *pRect = &stateblock->scissorRect;
+    RECT *pRect = &stateblock->state.scissor_rect;
     UINT height;
     UINT width;
 
@@ -4835,10 +4962,13 @@ static void indexbuffer(DWORD state, IWineD3DStateBlockImpl *stateblock, struct
 {
     const struct wined3d_gl_info *gl_info = context->gl_info;
 
-    if(stateblock->streamIsUP || stateblock->pIndexData == NULL ) {
+    if (stateblock->state.user_stream || !stateblock->state.index_buffer)
+    {
         GL_EXTCALL(glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0));
-    } else {
-        struct wined3d_buffer *ib = (struct wined3d_buffer *) stateblock->pIndexData;
+    }
+    else
+    {
+        struct wined3d_buffer *ib = stateblock->state.index_buffer;
         GL_EXTCALL(glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, ib->buffer_object));
     }
 }
@@ -4999,6 +5129,7 @@ const struct StateEntryTemplate misc_state_template[] = {
     { STATE_RENDER(WINED3DRS_ADAPTIVETESS_Y),             { STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), NULL                }, WINED3D_GL_EXT_NONE             },
     { STATE_RENDER(WINED3DRS_ADAPTIVETESS_Z),             { STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), NULL                }, WINED3D_GL_EXT_NONE             },
     { STATE_RENDER(WINED3DRS_ADAPTIVETESS_W),             { STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), NULL                }, WINED3D_GL_EXT_NONE             },
+    { STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), { STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), state_nvdb          }, EXT_DEPTH_BOUNDS_TEST           },
     { STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), { STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), state_tessellation  }, WINED3D_GL_EXT_NONE             },
     { STATE_RENDER(WINED3DRS_MULTISAMPLEANTIALIAS),       { STATE_RENDER(WINED3DRS_MULTISAMPLEANTIALIAS),       state_msaa          }, ARB_MULTISAMPLE                 },
     { STATE_RENDER(WINED3DRS_MULTISAMPLEANTIALIAS),       { STATE_RENDER(WINED3DRS_MULTISAMPLEANTIALIAS),       state_msaa_w        }, WINED3D_GL_EXT_NONE             },
@@ -5416,28 +5547,28 @@ const struct StateEntryTemplate ffp_vertexstate_template[] = {
      * otherwise, register sampler_texmatrix, which takes care of updating the texture matrix
      */
     { STATE_SAMPLER(0),                                   { 0,                                                  NULL                }, ARB_TEXTURE_NON_POWER_OF_TWO    },
-    { STATE_SAMPLER(0),                                   { 0,                                                  NULL                }, WINE_NORMALIZED_TEXRECT         },
+    { STATE_SAMPLER(0),                                   { 0,                                                  NULL                }, WINED3D_GL_NORMALIZED_TEXRECT   },
     { STATE_SAMPLER(0),                                   { STATE_SAMPLER(0),                                   sampler_texmatrix   }, WINED3D_GL_EXT_NONE             },
     { STATE_SAMPLER(1),                                   { 0,                                                  NULL                }, ARB_TEXTURE_NON_POWER_OF_TWO    },
-    { STATE_SAMPLER(1),                                   { 0,                                                  NULL                }, WINE_NORMALIZED_TEXRECT         },
+    { STATE_SAMPLER(1),                                   { 0,                                                  NULL                }, WINED3D_GL_NORMALIZED_TEXRECT   },
     { STATE_SAMPLER(1),                                   { STATE_SAMPLER(1),                                   sampler_texmatrix   }, WINED3D_GL_EXT_NONE             },
     { STATE_SAMPLER(2),                                   { 0,                                                  NULL                }, ARB_TEXTURE_NON_POWER_OF_TWO    },
-    { STATE_SAMPLER(2),                                   { 0,                                                  NULL                }, WINE_NORMALIZED_TEXRECT         },
+    { STATE_SAMPLER(2),                                   { 0,                                                  NULL                }, WINED3D_GL_NORMALIZED_TEXRECT   },
     { STATE_SAMPLER(2),                                   { STATE_SAMPLER(2),                                   sampler_texmatrix   }, WINED3D_GL_EXT_NONE             },
     { STATE_SAMPLER(3),                                   { 0,                                                  NULL                }, ARB_TEXTURE_NON_POWER_OF_TWO    },
-    { STATE_SAMPLER(3),                                   { 0,                                                  NULL                }, WINE_NORMALIZED_TEXRECT         },
+    { STATE_SAMPLER(3),                                   { 0,                                                  NULL                }, WINED3D_GL_NORMALIZED_TEXRECT   },
     { STATE_SAMPLER(3),                                   { STATE_SAMPLER(3),                                   sampler_texmatrix   }, WINED3D_GL_EXT_NONE             },
     { STATE_SAMPLER(4),                                   { 0,                                                  NULL                }, ARB_TEXTURE_NON_POWER_OF_TWO    },
-    { STATE_SAMPLER(4),                                   { 0,                                                  NULL                }, WINE_NORMALIZED_TEXRECT         },
+    { STATE_SAMPLER(4),                                   { 0,                                                  NULL                }, WINED3D_GL_NORMALIZED_TEXRECT   },
     { STATE_SAMPLER(4),                                   { STATE_SAMPLER(4),                                   sampler_texmatrix   }, WINED3D_GL_EXT_NONE             },
     { STATE_SAMPLER(5),                                   { 0,                                                  NULL                }, ARB_TEXTURE_NON_POWER_OF_TWO    },
-    { STATE_SAMPLER(5),                                   { 0,                                                  NULL                }, WINE_NORMALIZED_TEXRECT         },
+    { STATE_SAMPLER(5),                                   { 0,                                                  NULL                }, WINED3D_GL_NORMALIZED_TEXRECT   },
     { STATE_SAMPLER(5),                                   { STATE_SAMPLER(5),                                   sampler_texmatrix   }, WINED3D_GL_EXT_NONE             },
     { STATE_SAMPLER(6),                                   { 0,                                                  NULL                }, ARB_TEXTURE_NON_POWER_OF_TWO    },
-    { STATE_SAMPLER(6),                                   { 0,                                                  NULL                }, WINE_NORMALIZED_TEXRECT         },
+    { STATE_SAMPLER(6),                                   { 0,                                                  NULL                }, WINED3D_GL_NORMALIZED_TEXRECT   },
     { STATE_SAMPLER(6),                                   { STATE_SAMPLER(6),                                   sampler_texmatrix   }, WINED3D_GL_EXT_NONE             },
     { STATE_SAMPLER(7),                                   { 0,                                                  NULL                }, ARB_TEXTURE_NON_POWER_OF_TWO    },
-    { STATE_SAMPLER(7),                                   { 0,                                                  NULL                }, WINE_NORMALIZED_TEXRECT         },
+    { STATE_SAMPLER(7),                                   { 0,                                                  NULL                }, WINED3D_GL_NORMALIZED_TEXRECT   },
     { STATE_SAMPLER(7),                                   { STATE_SAMPLER(7),                                   sampler_texmatrix   }, WINED3D_GL_EXT_NONE             },
     {0 /* Terminate */,                                   { 0,                                                  0                   }, WINED3D_GL_EXT_NONE             },
 };
index 1696646..de8ee8e 100644 (file)
@@ -196,17 +196,17 @@ static HRESULT stateblock_allocate_shader_constants(IWineD3DStateBlockImpl *obje
     IWineD3DDeviceImpl *device = object->device;
 
     /* Allocate space for floating point constants */
-    object->pixelShaderConstantF = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
+    object->state.ps_consts_f = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
             sizeof(float) * device->d3d_pshader_constantF * 4);
-    if (!object->pixelShaderConstantF) goto fail;
+    if (!object->state.ps_consts_f) goto fail;
 
     object->changed.pixelShaderConstantsF = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
             sizeof(BOOL) * device->d3d_pshader_constantF);
     if (!object->changed.pixelShaderConstantsF) goto fail;
 
-    object->vertexShaderConstantF = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
+    object->state.vs_consts_f = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
             sizeof(float) * device->d3d_vshader_constantF * 4);
-    if (!object->vertexShaderConstantF) goto fail;
+    if (!object->state.vs_consts_f) goto fail;
 
     object->changed.vertexShaderConstantsF = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
             sizeof(BOOL) * device->d3d_vshader_constantF);
@@ -224,9 +224,9 @@ static HRESULT stateblock_allocate_shader_constants(IWineD3DStateBlockImpl *obje
 
 fail:
     ERR("Failed to allocate memory\n");
-    HeapFree(GetProcessHeap(), 0, object->pixelShaderConstantF);
+    HeapFree(GetProcessHeap(), 0, object->state.ps_consts_f);
     HeapFree(GetProcessHeap(), 0, object->changed.pixelShaderConstantsF);
-    HeapFree(GetProcessHeap(), 0, object->vertexShaderConstantF);
+    HeapFree(GetProcessHeap(), 0, object->state.vs_consts_f);
     HeapFree(GetProcessHeap(), 0, object->changed.vertexShaderConstantsF);
     HeapFree(GetProcessHeap(), 0, object->contained_vs_consts_f);
     HeapFree(GetProcessHeap(), 0, object->contained_ps_consts_f);
@@ -262,7 +262,7 @@ static void stateblock_savedstates_set_all(SAVEDSTATES *states, DWORD vs_consts,
     stateblock_set_bits(states->transform, HIGHEST_TRANSFORMSTATE + 1);
     stateblock_set_bits(states->renderState, WINEHIGHEST_RENDER_STATE + 1);
     for (i = 0; i < MAX_TEXTURES; ++i) states->textureState[i] = 0x3ffff;
-    for (i = 0; i < MAX_COMBINED_SAMPLERS; ++i) states->samplerState[i] = 0x3fff;
+    for (i = 0; i < MAX_COMBINED_SAMPLERS; ++i) states->samplerState[i] = 0x3ffe;
     states->clipplane = 0xffffffff;
     states->pixelShaderConstantsB = 0xffff;
     states->pixelShaderConstantsI = 0xffff;
@@ -452,7 +452,7 @@ static void stateblock_init_lights(IWineD3DStateBlockImpl *stateblock, struct li
             struct wined3d_light_info *dst_light = HeapAlloc(GetProcessHeap(), 0, sizeof(*dst_light));
 
             *dst_light = *src_light;
-            list_add_tail(&stateblock->lightMap[i], &dst_light->entry);
+            list_add_tail(&stateblock->state.light_map[i], &dst_light->entry);
         }
     }
 }
@@ -492,28 +492,33 @@ static ULONG  WINAPI IWineD3DStateBlockImpl_Release(IWineD3DStateBlock *iface) {
     if (!refCount) {
         int counter;
 
-        if (This->vertexDecl) IWineD3DVertexDeclaration_Release(This->vertexDecl);
+        if (This->state.vertex_declaration)
+            IWineD3DVertexDeclaration_Release((IWineD3DVertexDeclaration *)This->state.vertex_declaration);
 
         for (counter = 0; counter < MAX_COMBINED_SAMPLERS; counter++)
         {
-            if (This->textures[counter]) IWineD3DBaseTexture_Release(This->textures[counter]);
+            if (This->state.textures[counter])
+                IWineD3DBaseTexture_Release((IWineD3DBaseTexture *)This->state.textures[counter]);
         }
 
-        for (counter = 0; counter < MAX_STREAMS; counter++) {
-            if(This->streamSource[counter]) {
-                if (IWineD3DBuffer_Release(This->streamSource[counter]))
+        for (counter = 0; counter < MAX_STREAMS; ++counter)
+        {
+            struct wined3d_buffer *buffer = This->state.streams[counter].buffer;
+            if (buffer)
+            {
+                if (IWineD3DBuffer_Release((IWineD3DBuffer *)buffer))
                 {
-                    TRACE("Vertex buffer still referenced by stateblock, applications has leaked Stream %u, buffer %p\n", counter, This->streamSource[counter]);
+                    WARN("Buffer %p still referenced by stateblock, stream %u.\n", buffer, counter);
                 }
             }
         }
-        if(This->pIndexData) IWineD3DBuffer_Release(This->pIndexData);
-        if(This->vertexShader) IWineD3DVertexShader_Release(This->vertexShader);
-        if(This->pixelShader) IWineD3DPixelShader_Release(This->pixelShader);
+        if (This->state.index_buffer) IWineD3DBuffer_Release((IWineD3DBuffer *)This->state.index_buffer);
+        if (This->state.vertex_shader) IWineD3DVertexShader_Release((IWineD3DVertexShader *)This->state.vertex_shader);
+        if (This->state.pixel_shader) IWineD3DPixelShader_Release((IWineD3DPixelShader *)This->state.pixel_shader);
 
         for(counter = 0; counter < LIGHTMAP_SIZE; counter++) {
             struct list *e1, *e2;
-            LIST_FOR_EACH_SAFE(e1, e2, &This->lightMap[counter])
+            LIST_FOR_EACH_SAFE(e1, e2, &This->state.light_map[counter])
             {
                 struct wined3d_light_info *light = LIST_ENTRY(e1, struct wined3d_light_info, entry);
                 list_remove(&light->entry);
@@ -521,9 +526,9 @@ static ULONG  WINAPI IWineD3DStateBlockImpl_Release(IWineD3DStateBlock *iface) {
             }
         }
 
-        HeapFree(GetProcessHeap(), 0, This->vertexShaderConstantF);
+        HeapFree(GetProcessHeap(), 0, This->state.vs_consts_f);
         HeapFree(GetProcessHeap(), 0, This->changed.vertexShaderConstantsF);
-        HeapFree(GetProcessHeap(), 0, This->pixelShaderConstantF);
+        HeapFree(GetProcessHeap(), 0, This->state.ps_consts_f);
         HeapFree(GetProcessHeap(), 0, This->changed.pixelShaderConstantsF);
         HeapFree(GetProcessHeap(), 0, This->contained_vs_consts_f);
         HeapFree(GetProcessHeap(), 0, This->contained_ps_consts_f);
@@ -532,24 +537,24 @@ static ULONG  WINAPI IWineD3DStateBlockImpl_Release(IWineD3DStateBlock *iface) {
     return refCount;
 }
 
-/**********************************************************
- * IWineD3DStateBlockImpl parts follows
- **********************************************************/
-static void record_lights(IWineD3DStateBlockImpl *This, const IWineD3DStateBlockImpl *targetStateBlock)
+static void wined3d_state_record_lights(struct wined3d_state *dst_state, const struct wined3d_state *src_state)
 {
     UINT i;
 
-    /* Lights... For a recorded state block, we just had a chain of actions to perform,
-     * so we need to walk that chain and update any actions which differ
-     */
-    for(i = 0; i < LIGHTMAP_SIZE; i++) {
+    /* Lights... For a recorded state block, we just had a chain of actions
+     * to perform, so we need to walk that chain and update any actions which
+     * differ. */
+    for (i = 0; i < LIGHTMAP_SIZE; ++i)
+    {
         struct list *e, *f;
-        LIST_FOR_EACH(e, &This->lightMap[i]) {
+        LIST_FOR_EACH(e, &dst_state->light_map[i])
+        {
             BOOL updated = FALSE;
             struct wined3d_light_info *src = LIST_ENTRY(e, struct wined3d_light_info, entry), *realLight;
 
             /* Look up the light in the destination */
-            LIST_FOR_EACH(f, &targetStateBlock->lightMap[i]) {
+            LIST_FOR_EACH(f, &src_state->light_map[i])
+            {
                 realLight = LIST_ENTRY(f, struct wined3d_light_info, entry);
                 if (realLight->OriginalIndex == src->OriginalIndex)
                 {
@@ -558,12 +563,12 @@ static void record_lights(IWineD3DStateBlockImpl *This, const IWineD3DStateBlock
                     if (realLight->glIndex == -1 && src->glIndex != -1)
                     {
                         /* Light disabled */
-                        This->activeLights[src->glIndex] = NULL;
+                        dst_state->lights[src->glIndex] = NULL;
                     }
                     else if (realLight->glIndex != -1 && src->glIndex == -1)
                     {
                         /* Light enabled */
-                        This->activeLights[realLight->glIndex] = src;
+                        dst_state->lights[realLight->glIndex] = src;
                     }
                     src->glIndex = realLight->glIndex;
                     updated = TRUE;
@@ -575,13 +580,13 @@ static void record_lights(IWineD3DStateBlockImpl *This, const IWineD3DStateBlock
             {
                 /* This can happen if the light was originally created as a
                  * default light for SetLightEnable() while recording. */
-                WARN("Light %u in stateblock %p does not exist in device stateblock %p.\n",
-                        src->OriginalIndex, This, targetStateBlock);
+                WARN("Light %u in dst_state %p does not exist in src_state %p.\n",
+                        src->OriginalIndex, dst_state, src_state);
 
                 src->OriginalParms = WINED3D_default_light;
                 if (src->glIndex != -1)
                 {
-                    This->activeLights[src->glIndex] = NULL;
+                    dst_state->lights[src->glIndex] = NULL;
                     src->glIndex = -1;
                 }
             }
@@ -592,19 +597,24 @@ static void record_lights(IWineD3DStateBlockImpl *This, const IWineD3DStateBlock
 static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
 {
     IWineD3DStateBlockImpl *This = (IWineD3DStateBlockImpl *)iface;
-    IWineD3DStateBlockImpl *targetStateBlock = This->device->stateBlock;
+    const struct wined3d_state *src_state = &This->device->stateBlock->state;
     unsigned int i;
     DWORD map;
 
-    TRACE("(%p) : Updating state block %p ------------------v\n", targetStateBlock, This);
+    TRACE("iface %p.\n", iface);
+
+    TRACE("Capturing state %p.\n", src_state);
 
-    if (This->changed.vertexShader && This->vertexShader != targetStateBlock->vertexShader)
+    if (This->changed.vertexShader && This->state.vertex_shader != src_state->vertex_shader)
     {
-        TRACE("Updating vertex shader from %p to %p\n", This->vertexShader, targetStateBlock->vertexShader);
+        TRACE("Updating vertex shader from %p to %p\n",
+                This->state.vertex_shader, src_state->vertex_shader);
 
-        if (targetStateBlock->vertexShader) IWineD3DVertexShader_AddRef(targetStateBlock->vertexShader);
-        if (This->vertexShader) IWineD3DVertexShader_Release(This->vertexShader);
-        This->vertexShader = targetStateBlock->vertexShader;
+        if (src_state->vertex_shader)
+            IWineD3DVertexShader_AddRef((IWineD3DVertexShader *)src_state->vertex_shader);
+        if (This->state.vertex_shader)
+            IWineD3DVertexShader_Release((IWineD3DVertexShader *)This->state.vertex_shader);
+        This->state.vertex_shader = src_state->vertex_shader;
     }
 
     /* Vertex Shader Float Constants */
@@ -612,17 +622,16 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
     {
         unsigned int idx = This->contained_vs_consts_f[i];
 
-        TRACE("Setting %p from %p %u to {%.8e, %.8e, %.8e, %.8e}.\n",
-                This, targetStateBlock, idx,
-                targetStateBlock->vertexShaderConstantF[idx * 4 + 0],
-                targetStateBlock->vertexShaderConstantF[idx * 4 + 1],
-                targetStateBlock->vertexShaderConstantF[idx * 4 + 2],
-                targetStateBlock->vertexShaderConstantF[idx * 4 + 3]);
+        TRACE("Setting vs_consts_f[%u] to {%.8e, %.8e, %.8e, %.8e}.\n", idx,
+                src_state->vs_consts_f[idx * 4 + 0],
+                src_state->vs_consts_f[idx * 4 + 1],
+                src_state->vs_consts_f[idx * 4 + 2],
+                src_state->vs_consts_f[idx * 4 + 3]);
 
-        This->vertexShaderConstantF[idx * 4 + 0] = targetStateBlock->vertexShaderConstantF[idx * 4 + 0];
-        This->vertexShaderConstantF[idx * 4 + 1] = targetStateBlock->vertexShaderConstantF[idx * 4 + 1];
-        This->vertexShaderConstantF[idx * 4 + 2] = targetStateBlock->vertexShaderConstantF[idx * 4 + 2];
-        This->vertexShaderConstantF[idx * 4 + 3] = targetStateBlock->vertexShaderConstantF[idx * 4 + 3];
+        This->state.vs_consts_f[idx * 4 + 0] = src_state->vs_consts_f[idx * 4 + 0];
+        This->state.vs_consts_f[idx * 4 + 1] = src_state->vs_consts_f[idx * 4 + 1];
+        This->state.vs_consts_f[idx * 4 + 2] = src_state->vs_consts_f[idx * 4 + 2];
+        This->state.vs_consts_f[idx * 4 + 3] = src_state->vs_consts_f[idx * 4 + 3];
     }
 
     /* Vertex Shader Integer Constants */
@@ -630,17 +639,16 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
     {
         unsigned int idx = This->contained_vs_consts_i[i];
 
-        TRACE("Setting %p from %p %u to {%d, %d, %d, %d}.\n",
-                This, targetStateBlock, idx,
-                targetStateBlock->vertexShaderConstantI[idx * 4 + 0],
-                targetStateBlock->vertexShaderConstantI[idx * 4 + 1],
-                targetStateBlock->vertexShaderConstantI[idx * 4 + 2],
-                targetStateBlock->vertexShaderConstantI[idx * 4 + 3]);
+        TRACE("Setting vs_consts[%u] to {%d, %d, %d, %d}.\n", idx,
+                src_state->vs_consts_i[idx * 4 + 0],
+                src_state->vs_consts_i[idx * 4 + 1],
+                src_state->vs_consts_i[idx * 4 + 2],
+                src_state->vs_consts_i[idx * 4 + 3]);
 
-        This->vertexShaderConstantI[idx * 4 + 0] = targetStateBlock->vertexShaderConstantI[idx * 4 + 0];
-        This->vertexShaderConstantI[idx * 4 + 1] = targetStateBlock->vertexShaderConstantI[idx * 4 + 1];
-        This->vertexShaderConstantI[idx * 4 + 2] = targetStateBlock->vertexShaderConstantI[idx * 4 + 2];
-        This->vertexShaderConstantI[idx * 4 + 3] = targetStateBlock->vertexShaderConstantI[idx * 4 + 3];
+        This->state.vs_consts_i[idx * 4 + 0] = src_state->vs_consts_i[idx * 4 + 0];
+        This->state.vs_consts_i[idx * 4 + 1] = src_state->vs_consts_i[idx * 4 + 1];
+        This->state.vs_consts_i[idx * 4 + 2] = src_state->vs_consts_i[idx * 4 + 2];
+        This->state.vs_consts_i[idx * 4 + 3] = src_state->vs_consts_i[idx * 4 + 3];
     }
 
     /* Vertex Shader Boolean Constants */
@@ -648,11 +656,10 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
     {
         unsigned int idx = This->contained_vs_consts_b[i];
 
-        TRACE("Setting %p from %p %u to %s.\n",
-                This, targetStateBlock, idx,
-                targetStateBlock->vertexShaderConstantB[idx] ? "TRUE" : "FALSE");
+        TRACE("Setting vs_consts_b[%u] to %s.\n",
+                idx, src_state->vs_consts_b[idx] ? "TRUE" : "FALSE");
 
-        This->vertexShaderConstantB[idx] = targetStateBlock->vertexShaderConstantB[idx];
+        This->state.vs_consts_b[idx] = src_state->vs_consts_b[idx];
     }
 
     /* Pixel Shader Float Constants */
@@ -660,44 +667,42 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
     {
         unsigned int idx = This->contained_ps_consts_f[i];
 
-        TRACE("Setting %p from %p %u to {%.8e, %.8e, %.8e, %.8e}.\n",
-                This, targetStateBlock, idx,
-                targetStateBlock->pixelShaderConstantF[idx * 4 + 0],
-                targetStateBlock->pixelShaderConstantF[idx * 4 + 1],
-                targetStateBlock->pixelShaderConstantF[idx * 4 + 2],
-                targetStateBlock->pixelShaderConstantF[idx * 4 + 3]);
+        TRACE("Setting ps_consts_f[%u] to {%.8e, %.8e, %.8e, %.8e}.\n", idx,
+                src_state->ps_consts_f[idx * 4 + 0],
+                src_state->ps_consts_f[idx * 4 + 1],
+                src_state->ps_consts_f[idx * 4 + 2],
+                src_state->ps_consts_f[idx * 4 + 3]);
 
-        This->pixelShaderConstantF[idx * 4 + 0] = targetStateBlock->pixelShaderConstantF[idx * 4 + 0];
-        This->pixelShaderConstantF[idx * 4 + 1] = targetStateBlock->pixelShaderConstantF[idx * 4 + 1];
-        This->pixelShaderConstantF[idx * 4 + 2] = targetStateBlock->pixelShaderConstantF[idx * 4 + 2];
-        This->pixelShaderConstantF[idx * 4 + 3] = targetStateBlock->pixelShaderConstantF[idx * 4 + 3];
+        This->state.ps_consts_f[idx * 4 + 0] = src_state->ps_consts_f[idx * 4 + 0];
+        This->state.ps_consts_f[idx * 4 + 1] = src_state->ps_consts_f[idx * 4 + 1];
+        This->state.ps_consts_f[idx * 4 + 2] = src_state->ps_consts_f[idx * 4 + 2];
+        This->state.ps_consts_f[idx * 4 + 3] = src_state->ps_consts_f[idx * 4 + 3];
     }
 
     /* Pixel Shader Integer Constants */
     for (i = 0; i < This->num_contained_ps_consts_i; ++i)
     {
         unsigned int idx = This->contained_ps_consts_i[i];
-        TRACE("Setting %p from %p %u to {%d, %d, %d, %d}.\n",
-                This, targetStateBlock, idx,
-                targetStateBlock->pixelShaderConstantI[idx * 4 + 0],
-                targetStateBlock->pixelShaderConstantI[idx * 4 + 1],
-                targetStateBlock->pixelShaderConstantI[idx * 4 + 2],
-                targetStateBlock->pixelShaderConstantI[idx * 4 + 3]);
+        TRACE("Setting ps_consts_i[%u] to {%d, %d, %d, %d}.\n", idx,
+                src_state->ps_consts_i[idx * 4 + 0],
+                src_state->ps_consts_i[idx * 4 + 1],
+                src_state->ps_consts_i[idx * 4 + 2],
+                src_state->ps_consts_i[idx * 4 + 3]);
 
-        This->pixelShaderConstantI[idx * 4 + 0] = targetStateBlock->pixelShaderConstantI[idx * 4 + 0];
-        This->pixelShaderConstantI[idx * 4 + 1] = targetStateBlock->pixelShaderConstantI[idx * 4 + 1];
-        This->pixelShaderConstantI[idx * 4 + 2] = targetStateBlock->pixelShaderConstantI[idx * 4 + 2];
-        This->pixelShaderConstantI[idx * 4 + 3] = targetStateBlock->pixelShaderConstantI[idx * 4 + 3];
+        This->state.ps_consts_i[idx * 4 + 0] = src_state->ps_consts_i[idx * 4 + 0];
+        This->state.ps_consts_i[idx * 4 + 1] = src_state->ps_consts_i[idx * 4 + 1];
+        This->state.ps_consts_i[idx * 4 + 2] = src_state->ps_consts_i[idx * 4 + 2];
+        This->state.ps_consts_i[idx * 4 + 3] = src_state->ps_consts_i[idx * 4 + 3];
     }
 
     /* Pixel Shader Boolean Constants */
     for (i = 0; i < This->num_contained_ps_consts_b; ++i)
     {
         unsigned int idx = This->contained_ps_consts_b[i];
-        TRACE("Setting %p from %p %u to %s.\n", This, targetStateBlock, idx,
-                targetStateBlock->pixelShaderConstantB[idx] ? "TRUE" : "FALSE");
+        TRACE("Setting ps_consts_b[%u] to %s.\n",
+                idx, src_state->ps_consts_b[idx] ? "TRUE" : "FALSE");
 
-        This->pixelShaderConstantB[idx] = targetStateBlock->pixelShaderConstantB[idx];
+        This->state.ps_consts_b[idx] = src_state->ps_consts_b[idx];
     }
 
     /* Others + Render & Texture */
@@ -707,57 +712,61 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
 
         TRACE("Updating transform %#x.\n", transform);
 
-        This->transforms[transform] = targetStateBlock->transforms[transform];
+        This->state.transforms[transform] = src_state->transforms[transform];
     }
 
-    if (This->changed.primitive_type) This->gl_primitive_type = targetStateBlock->gl_primitive_type;
+    if (This->changed.primitive_type)
+        This->state.gl_primitive_type = src_state->gl_primitive_type;
 
     if (This->changed.indices
-            && ((This->pIndexData != targetStateBlock->pIndexData)
-                || (This->baseVertexIndex != targetStateBlock->baseVertexIndex)
-                || (This->IndexFmt != targetStateBlock->IndexFmt)))
+            && ((This->state.index_buffer != src_state->index_buffer)
+                || (This->state.base_vertex_index != src_state->base_vertex_index)
+                || (This->state.index_format != src_state->index_format)))
     {
-        TRACE("Updating pIndexData to %p, baseVertexIndex to %d.\n",
-                targetStateBlock->pIndexData, targetStateBlock->baseVertexIndex);
+        TRACE("Updating index buffer to %p, base vertex index to %d.\n",
+                src_state->index_buffer, src_state->base_vertex_index);
 
-        if (targetStateBlock->pIndexData) IWineD3DBuffer_AddRef(targetStateBlock->pIndexData);
-        if (This->pIndexData) IWineD3DBuffer_Release(This->pIndexData);
-        This->pIndexData = targetStateBlock->pIndexData;
-        This->baseVertexIndex = targetStateBlock->baseVertexIndex;
-        This->IndexFmt = targetStateBlock->IndexFmt;
+        if (src_state->index_buffer)
+            IWineD3DBuffer_AddRef((IWineD3DBuffer *)src_state->index_buffer);
+        if (This->state.index_buffer)
+            IWineD3DBuffer_Release((IWineD3DBuffer *)This->state.index_buffer);
+        This->state.index_buffer = src_state->index_buffer;
+        This->state.base_vertex_index = src_state->base_vertex_index;
+        This->state.index_format = src_state->index_format;
     }
 
-    if (This->changed.vertexDecl && This->vertexDecl != targetStateBlock->vertexDecl)
+    if (This->changed.vertexDecl && This->state.vertex_declaration != src_state->vertex_declaration)
     {
-        TRACE("Updating vertex declaration from %p to %p.\n", This->vertexDecl, targetStateBlock->vertexDecl);
+        TRACE("Updating vertex declaration from %p to %p.\n",
+                This->state.vertex_declaration, src_state->vertex_declaration);
 
-        if (targetStateBlock->vertexDecl) IWineD3DVertexDeclaration_AddRef(targetStateBlock->vertexDecl);
-        if (This->vertexDecl) IWineD3DVertexDeclaration_Release(This->vertexDecl);
-        This->vertexDecl = targetStateBlock->vertexDecl;
+        if (src_state->vertex_declaration)
+                IWineD3DVertexDeclaration_AddRef((IWineD3DVertexDeclaration *)src_state->vertex_declaration);
+        if (This->state.vertex_declaration)
+                IWineD3DVertexDeclaration_Release((IWineD3DVertexDeclaration *)This->state.vertex_declaration);
+        This->state.vertex_declaration = src_state->vertex_declaration;
     }
 
-    if (This->changed.material
-            && memcmp(&targetStateBlock->material, &This->material, sizeof(This->material)))
+    if (This->changed.material && memcmp(&src_state->material, &This->state.material, sizeof(This->state.material)))
     {
         TRACE("Updating material.\n");
 
-        This->material = targetStateBlock->material;
+        This->state.material = src_state->material;
     }
 
-    if (This->changed.viewport
-            && memcmp(&targetStateBlock->viewport, &This->viewport, sizeof(This->viewport)))
+    if (This->changed.viewport && memcmp(&src_state->viewport, &This->state.viewport, sizeof(This->state.viewport)))
     {
         TRACE("Updating viewport.\n");
 
-        This->viewport = targetStateBlock->viewport;
+        This->state.viewport = src_state->viewport;
     }
 
-    if(This->changed.scissorRect
-            && memcmp(&targetStateBlock->scissorRect, &This->scissorRect, sizeof(This->scissorRect)))
+    if (This->changed.scissorRect && memcmp(&src_state->scissor_rect,
+            &This->state.scissor_rect, sizeof(This->state.scissor_rect)))
     {
         TRACE("Updating scissor rect.\n");
 
-        This->scissorRect = targetStateBlock->scissorRect;
+        This->state.scissor_rect = src_state->scissor_rect;
     }
 
     map = This->changed.streamSource;
@@ -765,16 +774,19 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
     {
         if (!(map & 1)) continue;
 
-        if (This->streamStride[i] != targetStateBlock->streamStride[i]
-                || This->streamSource[i] != targetStateBlock->streamSource[i])
+        if (This->state.streams[i].stride != src_state->streams[i].stride
+                || This->state.streams[i].buffer != src_state->streams[i].buffer)
         {
             TRACE("Updating stream source %u to %p, stride to %u.\n",
-                    i, targetStateBlock->streamSource[i], targetStateBlock->streamStride[i]);
-
-            This->streamStride[i] = targetStateBlock->streamStride[i];
-            if (targetStateBlock->streamSource[i]) IWineD3DBuffer_AddRef(targetStateBlock->streamSource[i]);
-            if (This->streamSource[i]) IWineD3DBuffer_Release(This->streamSource[i]);
-            This->streamSource[i] = targetStateBlock->streamSource[i];
+                    i, src_state->streams[i].buffer,
+                    src_state->streams[i].stride);
+
+            This->state.streams[i].stride = src_state->streams[i].stride;
+            if (src_state->streams[i].buffer)
+                    IWineD3DBuffer_AddRef((IWineD3DBuffer *)src_state->streams[i].buffer);
+            if (This->state.streams[i].buffer)
+                    IWineD3DBuffer_Release((IWineD3DBuffer *)This->state.streams[i].buffer);
+            This->state.streams[i].buffer = src_state->streams[i].buffer;
         }
     }
 
@@ -783,14 +795,14 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
     {
         if (!(map & 1)) continue;
 
-        if (This->streamFreq[i] != targetStateBlock->streamFreq[i]
-                || This->streamFlags[i] != targetStateBlock->streamFlags[i])
+        if (This->state.streams[i].frequency != src_state->streams[i].frequency
+                || This->state.streams[i].flags != src_state->streams[i].flags)
         {
             TRACE("Updating stream frequency %u to %u flags to %#x.\n",
-                    i, targetStateBlock->streamFreq[i], targetStateBlock->streamFlags[i]);
+                    i, src_state->streams[i].frequency, src_state->streams[i].flags);
 
-            This->streamFreq[i] = targetStateBlock->streamFreq[i];
-            This->streamFlags[i] = targetStateBlock->streamFlags[i];
+            This->state.streams[i].frequency = src_state->streams[i].frequency;
+            This->state.streams[i].flags = src_state->streams[i].flags;
         }
     }
 
@@ -799,10 +811,10 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
     {
         if (!(map & 1)) continue;
 
-        if (memcmp(targetStateBlock->clipplane[i], This->clipplane[i], sizeof(*This->clipplane)))
+        if (memcmp(src_state->clip_planes[i], This->state.clip_planes[i], sizeof(*This->state.clip_planes)))
         {
             TRACE("Updating clipplane %u.\n", i);
-            memcpy(This->clipplane[i], targetStateBlock->clipplane[i], sizeof(*This->clipplane));
+            memcpy(This->state.clip_planes[i], src_state->clip_planes[i], sizeof(*This->state.clip_planes));
         }
     }
 
@@ -811,9 +823,9 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
     {
         WINED3DRENDERSTATETYPE rs = This->contained_render_states[i];
 
-        TRACE("Updating renderState %#x to %u.\n", rs, targetStateBlock->renderState[rs]);
+        TRACE("Updating render state %#x to %u.\n", rs, src_state->render_states[rs]);
 
-        This->renderState[rs] = targetStateBlock->renderState[rs];
+        This->state.render_states[rs] = src_state->render_states[rs];
     }
 
     /* Texture states */
@@ -822,10 +834,10 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
         DWORD stage = This->contained_tss_states[i].stage;
         DWORD state = This->contained_tss_states[i].state;
 
-        TRACE("Updating texturestage state %u, %u to %u (was %u).\n", stage, state,
-                targetStateBlock->textureState[stage][state], This->textureState[stage][state]);
+        TRACE("Updating texturestage state %u, %u to %#x (was %#x).\n", stage, state,
+                src_state->texture_states[stage][state], This->state.texture_states[stage][state]);
 
-        This->textureState[stage][state] = targetStateBlock->textureState[stage][state];
+        This->state.texture_states[stage][state] = src_state->texture_states[stage][state];
     }
 
     /* Samplers */
@@ -834,11 +846,14 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
     {
         if (!(map & 1)) continue;
 
-        TRACE("Updating texture %u to %p (was %p).\n", i, targetStateBlock->textures[i], This->textures[i]);
+        TRACE("Updating texture %u to %p (was %p).\n",
+                i, src_state->textures[i], This->state.textures[i]);
 
-        if (targetStateBlock->textures[i]) IWineD3DBaseTexture_AddRef(targetStateBlock->textures[i]);
-        if (This->textures[i]) IWineD3DBaseTexture_Release(This->textures[i]);
-        This->textures[i] = targetStateBlock->textures[i];
+        if (src_state->textures[i])
+            IWineD3DBaseTexture_AddRef((IWineD3DBaseTexture *)src_state->textures[i]);
+        if (This->state.textures[i])
+            IWineD3DBaseTexture_Release((IWineD3DBaseTexture *)This->state.textures[i]);
+        This->state.textures[i] = src_state->textures[i];
     }
 
     for (i = 0; i < This->num_contained_sampler_states; ++i)
@@ -846,33 +861,37 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
         DWORD stage = This->contained_sampler_states[i].stage;
         DWORD state = This->contained_sampler_states[i].state;
 
-        TRACE("Updating sampler state %u, %u to %u (was %u).\n", stage, state,
-                targetStateBlock->samplerState[stage][state], This->samplerState[stage][state]);
+        TRACE("Updating sampler state %u, %u to %#x (was %#x).\n", stage, state,
+                src_state->sampler_states[stage][state], This->state.sampler_states[stage][state]);
 
-        This->samplerState[stage][state] = targetStateBlock->samplerState[stage][state];
+        This->state.sampler_states[stage][state] = src_state->sampler_states[stage][state];
     }
 
-    if (This->changed.pixelShader && This->pixelShader != targetStateBlock->pixelShader)
+    if (This->changed.pixelShader && This->state.pixel_shader != src_state->pixel_shader)
     {
-        if (targetStateBlock->pixelShader) IWineD3DPixelShader_AddRef(targetStateBlock->pixelShader);
-        if (This->pixelShader) IWineD3DPixelShader_Release(This->pixelShader);
-        This->pixelShader = targetStateBlock->pixelShader;
+        if (src_state->pixel_shader)
+            IWineD3DPixelShader_AddRef((IWineD3DPixelShader *)src_state->pixel_shader);
+        if (This->state.pixel_shader)
+            IWineD3DPixelShader_Release((IWineD3DPixelShader *)This->state.pixel_shader);
+        This->state.pixel_shader = src_state->pixel_shader;
     }
 
-    record_lights(This, targetStateBlock);
+    wined3d_state_record_lights(&This->state, src_state);
 
-    TRACE("(%p) : Updated state block %p ------------------^\n", targetStateBlock, This);
+    TRACE("Captue done.\n");
 
     return WINED3D_OK;
 }
 
-static void apply_lights(IWineD3DDevice *device, const IWineD3DStateBlockImpl *This)
+static void apply_lights(IWineD3DDevice *device, const struct wined3d_state *state)
 {
     UINT i;
-    for(i = 0; i < LIGHTMAP_SIZE; i++) {
+
+    for (i = 0; i < LIGHTMAP_SIZE; ++i)
+    {
         struct list *e;
 
-        LIST_FOR_EACH(e, &This->lightMap[i])
+        LIST_FOR_EACH(e, &state->light_map[i])
         {
             const struct wined3d_light_info *light = LIST_ENTRY(e, struct wined3d_light_info, entry);
 
@@ -893,51 +912,53 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
 
     TRACE("Blocktype: %d\n", This->blockType);
 
-    if (This->changed.vertexShader) IWineD3DDevice_SetVertexShader(device, This->vertexShader);
+    if (This->changed.vertexShader)
+        IWineD3DDevice_SetVertexShader(device, (IWineD3DVertexShader *)This->state.vertex_shader);
 
     /* Vertex Shader Constants */
     for (i = 0; i < This->num_contained_vs_consts_f; ++i)
     {
         IWineD3DDevice_SetVertexShaderConstantF(device, This->contained_vs_consts_f[i],
-                This->vertexShaderConstantF + This->contained_vs_consts_f[i] * 4, 1);
+                This->state.vs_consts_f + This->contained_vs_consts_f[i] * 4, 1);
     }
     for (i = 0; i < This->num_contained_vs_consts_i; ++i)
     {
         IWineD3DDevice_SetVertexShaderConstantI(device, This->contained_vs_consts_i[i],
-                This->vertexShaderConstantI + This->contained_vs_consts_i[i] * 4, 1);
+                This->state.vs_consts_i + This->contained_vs_consts_i[i] * 4, 1);
     }
     for (i = 0; i < This->num_contained_vs_consts_b; ++i)
     {
         IWineD3DDevice_SetVertexShaderConstantB(device, This->contained_vs_consts_b[i],
-                This->vertexShaderConstantB + This->contained_vs_consts_b[i], 1);
+                This->state.vs_consts_b + This->contained_vs_consts_b[i], 1);
     }
 
-    apply_lights(device, This);
+    apply_lights(device, &This->state);
 
-    if (This->changed.pixelShader) IWineD3DDevice_SetPixelShader(device, This->pixelShader);
+    if (This->changed.pixelShader)
+        IWineD3DDevice_SetPixelShader(device, (IWineD3DPixelShader *)This->state.pixel_shader);
 
     /* Pixel Shader Constants */
     for (i = 0; i < This->num_contained_ps_consts_f; ++i)
     {
         IWineD3DDevice_SetPixelShaderConstantF(device, This->contained_ps_consts_f[i],
-                This->pixelShaderConstantF + This->contained_ps_consts_f[i] * 4, 1);
+                This->state.ps_consts_f + This->contained_ps_consts_f[i] * 4, 1);
     }
     for (i = 0; i < This->num_contained_ps_consts_i; ++i)
     {
         IWineD3DDevice_SetPixelShaderConstantI(device, This->contained_ps_consts_i[i],
-                This->pixelShaderConstantI + This->contained_ps_consts_i[i] * 4, 1);
+                This->state.ps_consts_i + This->contained_ps_consts_i[i] * 4, 1);
     }
     for (i = 0; i < This->num_contained_ps_consts_b; ++i)
     {
         IWineD3DDevice_SetPixelShaderConstantB(device, This->contained_ps_consts_b[i],
-                This->pixelShaderConstantB + This->contained_ps_consts_b[i], 1);
+                This->state.ps_consts_b + This->contained_ps_consts_b[i], 1);
     }
 
     /* Render */
     for (i = 0; i < This->num_contained_render_states; ++i)
     {
         IWineD3DDevice_SetRenderState(device, This->contained_render_states[i],
-                This->renderState[This->contained_render_states[i]]);
+                This->state.render_states[This->contained_render_states[i]]);
     }
 
     /* Texture states */
@@ -946,7 +967,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
         DWORD stage = This->contained_tss_states[i].stage;
         DWORD state = This->contained_tss_states[i].state;
 
-        IWineD3DDevice_SetTextureStageState(device, stage, state, This->textureState[stage][state]);
+        IWineD3DDevice_SetTextureStageState(device, stage, state, This->state.texture_states[stage][state]);
     }
 
     /* Sampler states */
@@ -954,7 +975,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
     {
         DWORD stage = This->contained_sampler_states[i].stage;
         DWORD state = This->contained_sampler_states[i].state;
-        DWORD value = This->samplerState[stage][state];
+        DWORD value = This->state.sampler_states[stage][state];
 
         if (stage >= MAX_FRAGMENT_SAMPLERS) stage += WINED3DVERTEXTEXTURESAMPLER0 - MAX_FRAGMENT_SAMPLERS;
         IWineD3DDevice_SetSamplerState(device, stage, state, value);
@@ -963,51 +984,56 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
     for (i = 0; i < This->num_contained_transform_states; ++i)
     {
         IWineD3DDevice_SetTransform(device, This->contained_transform_states[i],
-                &This->transforms[This->contained_transform_states[i]]);
+                &This->state.transforms[This->contained_transform_states[i]]);
     }
 
     if (This->changed.primitive_type)
     {
         This->device->updateStateBlock->changed.primitive_type = TRUE;
-        This->device->updateStateBlock->gl_primitive_type = This->gl_primitive_type;
+        This->device->updateStateBlock->state.gl_primitive_type = This->state.gl_primitive_type;
     }
 
     if (This->changed.indices)
     {
-        IWineD3DDevice_SetIndexBuffer(device, This->pIndexData, This->IndexFmt);
-        IWineD3DDevice_SetBaseVertexIndex(device, This->baseVertexIndex);
+        IWineD3DDevice_SetIndexBuffer(device, (IWineD3DBuffer *)This->state.index_buffer, This->state.index_format);
+        IWineD3DDevice_SetBaseVertexIndex(device, This->state.base_vertex_index);
     }
 
-    if (This->changed.vertexDecl && This->vertexDecl)
+    if (This->changed.vertexDecl && This->state.vertex_declaration)
     {
-        IWineD3DDevice_SetVertexDeclaration(device, This->vertexDecl);
+        IWineD3DDevice_SetVertexDeclaration(device, (IWineD3DVertexDeclaration *)This->state.vertex_declaration);
     }
 
     if (This->changed.material)
     {
-        IWineD3DDevice_SetMaterial(device, &This->material);
+        IWineD3DDevice_SetMaterial(device, &This->state.material);
     }
 
     if (This->changed.viewport)
     {
-        IWineD3DDevice_SetViewport(device, &This->viewport);
+        IWineD3DDevice_SetViewport(device, &This->state.viewport);
     }
 
     if (This->changed.scissorRect)
     {
-        IWineD3DDevice_SetScissorRect(device, &This->scissorRect);
+        IWineD3DDevice_SetScissorRect(device, &This->state.scissor_rect);
     }
 
     map = This->changed.streamSource;
     for (i = 0; map; map >>= 1, ++i)
     {
-        if (map & 1) IWineD3DDevice_SetStreamSource(device, i, This->streamSource[i], 0, This->streamStride[i]);
+        if (map & 1)
+            IWineD3DDevice_SetStreamSource(device, i,
+                    (IWineD3DBuffer *)This->state.streams[i].buffer,
+                    0, This->state.streams[i].stride);
     }
 
     map = This->changed.streamFreq;
     for (i = 0; map; map >>= 1, ++i)
     {
-        if (map & 1) IWineD3DDevice_SetStreamSourceFreq(device, i, This->streamFreq[i] | This->streamFlags[i]);
+        if (map & 1)
+            IWineD3DDevice_SetStreamSourceFreq(device, i,
+                    This->state.streams[i].frequency | This->state.streams[i].flags);
     }
 
     map = This->changed.textures;
@@ -1018,7 +1044,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
         if (!(map & 1)) continue;
 
         stage = i < MAX_FRAGMENT_SAMPLERS ? i : WINED3DVERTEXTEXTURESAMPLER0 + i - MAX_FRAGMENT_SAMPLERS;
-        IWineD3DDevice_SetTexture(device, stage, This->textures[i]);
+        IWineD3DDevice_SetTexture(device, stage, (IWineD3DBaseTexture *)This->state.textures[i]);
     }
 
     map = This->changed.clipplane;
@@ -1028,19 +1054,19 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
 
         if (!(map & 1)) continue;
 
-        clip[0] = This->clipplane[i][0];
-        clip[1] = This->clipplane[i][1];
-        clip[2] = This->clipplane[i][2];
-        clip[3] = This->clipplane[i][3];
+        clip[0] = This->state.clip_planes[i][0];
+        clip[1] = This->state.clip_planes[i][1];
+        clip[2] = This->state.clip_planes[i][2];
+        clip[3] = This->state.clip_planes[i][3];
         IWineD3DDevice_SetClipPlane(device, i, clip);
     }
 
-    This->device->stateBlock->lowest_disabled_stage = MAX_TEXTURES - 1;
+    This->device->stateBlock->state.lowest_disabled_stage = MAX_TEXTURES - 1;
     for (i = 0; i < MAX_TEXTURES - 1; ++i)
     {
-        if (This->device->stateBlock->textureState[i][WINED3DTSS_COLOROP] == WINED3DTOP_DISABLE)
+        if (This->device->stateBlock->state.texture_states[i][WINED3DTSS_COLOROP] == WINED3DTOP_DISABLE)
         {
-            This->device->stateBlock->lowest_disabled_stage = i;
+            This->device->stateBlock->state.lowest_disabled_stage = i;
             break;
         }
     }
@@ -1049,11 +1075,11 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
     return WINED3D_OK;
 }
 
-static HRESULT  WINAPI IWineD3DStateBlockImpl_InitStartupStateBlock(IWineD3DStateBlock* iface) {
-    IWineD3DStateBlockImpl *This = (IWineD3DStateBlockImpl *)iface;
-    IWineD3DDevice *device = (IWineD3DDevice *)This->device;
-    IWineD3DDeviceImpl *device_impl = (IWineD3DDeviceImpl *)device;
-    const struct wined3d_gl_info *gl_info = &device_impl->adapter->gl_info;
+void stateblock_init_default_state(IWineD3DStateBlockImpl *stateblock)
+{
+    IWineD3DDeviceImpl *device = stateblock->device;
+    const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
+    struct wined3d_state *state = &stateblock->state;
     union {
         WINED3DLINEPATTERN lp;
         DWORD d;
@@ -1067,243 +1093,237 @@ static HRESULT  WINAPI IWineD3DStateBlockImpl_InitStartupStateBlock(IWineD3DStat
     IWineD3DSurface *backbuffer;
     HRESULT hr;
 
-    /* Note this may have a large overhead but it should only be executed
-       once, in order to initialize the complete state of the device and
-       all opengl equivalents                                            */
-    TRACE("(%p) -----------------------> Setting up device defaults... %p\n", This, device);
-    /* TODO: make a special stateblock type for the primary stateblock (it never gets applied so it doesn't need a real type) */
-    This->blockType = WINED3DSBT_INIT;
+    TRACE("stateblock %p.\n", stateblock);
+
+    stateblock->blockType = WINED3DSBT_INIT;
 
     /* Set some of the defaults for lights, transforms etc */
-    memcpy(&This->transforms[WINED3DTS_PROJECTION], identity, sizeof(identity));
-    memcpy(&This->transforms[WINED3DTS_VIEW], identity, sizeof(identity));
-    for (i = 0; i < 256; ++i) {
-      memcpy(&This->transforms[WINED3DTS_WORLDMATRIX(i)], identity, sizeof(identity));
+    memcpy(&state->transforms[WINED3DTS_PROJECTION], identity, sizeof(identity));
+    memcpy(&state->transforms[WINED3DTS_VIEW], identity, sizeof(identity));
+    for (i = 0; i < 256; ++i)
+    {
+        memcpy(&state->transforms[WINED3DTS_WORLDMATRIX(i)], identity, sizeof(identity));
     }
 
     TRACE("Render states\n");
     /* Render states: */
-    if (device_impl->auto_depth_stencil)
-       IWineD3DDevice_SetRenderState(device, WINED3DRS_ZENABLE,       WINED3DZB_TRUE);
+    if (device->auto_depth_stencil)
+       state->render_states[WINED3DRS_ZENABLE] = WINED3DZB_TRUE;
     else
-       IWineD3DDevice_SetRenderState(device, WINED3DRS_ZENABLE,       WINED3DZB_FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_FILLMODE,         WINED3DFILL_SOLID);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SHADEMODE,        WINED3DSHADE_GOURAUD);
+       state->render_states[WINED3DRS_ZENABLE] = WINED3DZB_FALSE;
+    state->render_states[WINED3DRS_FILLMODE] = WINED3DFILL_SOLID;
+    state->render_states[WINED3DRS_SHADEMODE] = WINED3DSHADE_GOURAUD;
     lp.lp.wRepeatFactor = 0;
-    lp.lp.wLinePattern  = 0;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_LINEPATTERN,      lp.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ZWRITEENABLE,     TRUE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ALPHATESTENABLE,  FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_LASTPIXEL,        TRUE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SRCBLEND,         WINED3DBLEND_ONE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_DESTBLEND,        WINED3DBLEND_ZERO);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_CULLMODE,         WINED3DCULL_CCW);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ZFUNC,            WINED3DCMP_LESSEQUAL);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ALPHAFUNC,        WINED3DCMP_ALWAYS);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ALPHAREF,         0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_DITHERENABLE,     FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ALPHABLENDENABLE, FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_FOGENABLE,        FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SPECULARENABLE,   FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ZVISIBLE,         0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_FOGCOLOR,         0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_FOGTABLEMODE,     WINED3DFOG_NONE);
+    lp.lp.wLinePattern = 0;
+    state->render_states[WINED3DRS_LINEPATTERN] = lp.d;
+    state->render_states[WINED3DRS_ZWRITEENABLE] = TRUE;
+    state->render_states[WINED3DRS_ALPHATESTENABLE] = FALSE;
+    state->render_states[WINED3DRS_LASTPIXEL] = TRUE;
+    state->render_states[WINED3DRS_SRCBLEND] = WINED3DBLEND_ONE;
+    state->render_states[WINED3DRS_DESTBLEND] = WINED3DBLEND_ZERO;
+    state->render_states[WINED3DRS_CULLMODE] = WINED3DCULL_CCW;
+    state->render_states[WINED3DRS_ZFUNC] = WINED3DCMP_LESSEQUAL;
+    state->render_states[WINED3DRS_ALPHAFUNC] = WINED3DCMP_ALWAYS;
+    state->render_states[WINED3DRS_ALPHAREF] = 0;
+    state->render_states[WINED3DRS_DITHERENABLE] = FALSE;
+    state->render_states[WINED3DRS_ALPHABLENDENABLE] = FALSE;
+    state->render_states[WINED3DRS_FOGENABLE] = FALSE;
+    state->render_states[WINED3DRS_SPECULARENABLE] = FALSE;
+    state->render_states[WINED3DRS_ZVISIBLE] = 0;
+    state->render_states[WINED3DRS_FOGCOLOR] = 0;
+    state->render_states[WINED3DRS_FOGTABLEMODE] = WINED3DFOG_NONE;
     tmpfloat.f = 0.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_FOGSTART,         tmpfloat.d);
+    state->render_states[WINED3DRS_FOGSTART] = tmpfloat.d;
     tmpfloat.f = 1.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_FOGEND,           tmpfloat.d);
+    state->render_states[WINED3DRS_FOGEND] = tmpfloat.d;
     tmpfloat.f = 1.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_FOGDENSITY,       tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_EDGEANTIALIAS,    FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ZBIAS,            0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_RANGEFOGENABLE,   FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_STENCILENABLE,    FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_STENCILFAIL,      WINED3DSTENCILOP_KEEP);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_STENCILZFAIL,     WINED3DSTENCILOP_KEEP);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_STENCILPASS,      WINED3DSTENCILOP_KEEP);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_STENCILREF,       0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_STENCILMASK,      0xFFFFFFFF);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_STENCILFUNC,      WINED3DCMP_ALWAYS);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_STENCILWRITEMASK, 0xFFFFFFFF);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_TEXTUREFACTOR,    0xFFFFFFFF);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP0, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP1, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP2, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP3, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP4, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP5, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP6, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP7, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_CLIPPING,                 TRUE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_LIGHTING,                 TRUE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_AMBIENT,                  0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_FOGVERTEXMODE,            WINED3DFOG_NONE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_COLORVERTEX,              TRUE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_LOCALVIEWER,              TRUE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_NORMALIZENORMALS,         FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_DIFFUSEMATERIALSOURCE,    WINED3DMCS_COLOR1);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SPECULARMATERIALSOURCE,   WINED3DMCS_COLOR2);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_AMBIENTMATERIALSOURCE,    WINED3DMCS_MATERIAL);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_EMISSIVEMATERIALSOURCE,   WINED3DMCS_MATERIAL);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_VERTEXBLEND,              WINED3DVBF_DISABLE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_CLIPPLANEENABLE,          0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SOFTWAREVERTEXPROCESSING, FALSE);
+    state->render_states[WINED3DRS_FOGDENSITY] = tmpfloat.d;
+    state->render_states[WINED3DRS_EDGEANTIALIAS] = FALSE;
+    state->render_states[WINED3DRS_ZBIAS] = 0;
+    state->render_states[WINED3DRS_RANGEFOGENABLE] = FALSE;
+    state->render_states[WINED3DRS_STENCILENABLE] = FALSE;
+    state->render_states[WINED3DRS_STENCILFAIL] = WINED3DSTENCILOP_KEEP;
+    state->render_states[WINED3DRS_STENCILZFAIL] = WINED3DSTENCILOP_KEEP;
+    state->render_states[WINED3DRS_STENCILPASS] = WINED3DSTENCILOP_KEEP;
+    state->render_states[WINED3DRS_STENCILREF] = 0;
+    state->render_states[WINED3DRS_STENCILMASK] = 0xffffffff;
+    state->render_states[WINED3DRS_STENCILFUNC] = WINED3DCMP_ALWAYS;
+    state->render_states[WINED3DRS_STENCILWRITEMASK] = 0xffffffff;
+    state->render_states[WINED3DRS_TEXTUREFACTOR] = 0xffffffff;
+    state->render_states[WINED3DRS_WRAP0] = 0;
+    state->render_states[WINED3DRS_WRAP1] = 0;
+    state->render_states[WINED3DRS_WRAP2] = 0;
+    state->render_states[WINED3DRS_WRAP3] = 0;
+    state->render_states[WINED3DRS_WRAP4] = 0;
+    state->render_states[WINED3DRS_WRAP5] = 0;
+    state->render_states[WINED3DRS_WRAP6] = 0;
+    state->render_states[WINED3DRS_WRAP7] = 0;
+    state->render_states[WINED3DRS_CLIPPING] = TRUE;
+    state->render_states[WINED3DRS_LIGHTING] = TRUE;
+    state->render_states[WINED3DRS_AMBIENT] = 0;
+    state->render_states[WINED3DRS_FOGVERTEXMODE] = WINED3DFOG_NONE;
+    state->render_states[WINED3DRS_COLORVERTEX] = TRUE;
+    state->render_states[WINED3DRS_LOCALVIEWER] = TRUE;
+    state->render_states[WINED3DRS_NORMALIZENORMALS] = FALSE;
+    state->render_states[WINED3DRS_DIFFUSEMATERIALSOURCE] = WINED3DMCS_COLOR1;
+    state->render_states[WINED3DRS_SPECULARMATERIALSOURCE] = WINED3DMCS_COLOR2;
+    state->render_states[WINED3DRS_AMBIENTMATERIALSOURCE] = WINED3DMCS_MATERIAL;
+    state->render_states[WINED3DRS_EMISSIVEMATERIALSOURCE] = WINED3DMCS_MATERIAL;
+    state->render_states[WINED3DRS_VERTEXBLEND] = WINED3DVBF_DISABLE;
+    state->render_states[WINED3DRS_CLIPPLANEENABLE] = 0;
+    state->render_states[WINED3DRS_SOFTWAREVERTEXPROCESSING] = FALSE;
     tmpfloat.f = 1.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_POINTSIZE,                tmpfloat.d);
+    state->render_states[WINED3DRS_POINTSIZE] = tmpfloat.d;
     tmpfloat.f = 1.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_POINTSIZE_MIN,            tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_POINTSPRITEENABLE,        FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_POINTSCALEENABLE,         FALSE);
+    state->render_states[WINED3DRS_POINTSIZE_MIN] = tmpfloat.d;
+    state->render_states[WINED3DRS_POINTSPRITEENABLE] = FALSE;
+    state->render_states[WINED3DRS_POINTSCALEENABLE] = FALSE;
     tmpfloat.f = 1.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_POINTSCALE_A,             tmpfloat.d);
+    state->render_states[WINED3DRS_POINTSCALE_A] = tmpfloat.d;
     tmpfloat.f = 0.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_POINTSCALE_B,             tmpfloat.d);
+    state->render_states[WINED3DRS_POINTSCALE_B] = tmpfloat.d;
     tmpfloat.f = 0.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_POINTSCALE_C,             tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_MULTISAMPLEANTIALIAS,     TRUE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_MULTISAMPLEMASK,          0xFFFFFFFF);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_PATCHEDGESTYLE,           WINED3DPATCHEDGE_DISCRETE);
+    state->render_states[WINED3DRS_POINTSCALE_C] = tmpfloat.d;
+    state->render_states[WINED3DRS_MULTISAMPLEANTIALIAS] = TRUE;
+    state->render_states[WINED3DRS_MULTISAMPLEMASK] = 0xffffffff;
+    state->render_states[WINED3DRS_PATCHEDGESTYLE] = WINED3DPATCHEDGE_DISCRETE;
     tmpfloat.f = 1.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_PATCHSEGMENTS,            tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_DEBUGMONITORTOKEN,        0xbaadcafe);
+    state->render_states[WINED3DRS_PATCHSEGMENTS] = tmpfloat.d;
+    state->render_states[WINED3DRS_DEBUGMONITORTOKEN] = 0xbaadcafe;
     tmpfloat.f = gl_info->limits.pointsize_max;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_POINTSIZE_MAX,            tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_INDEXEDVERTEXBLENDENABLE, FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_COLORWRITEENABLE,         0x0000000F);
+    state->render_states[WINED3DRS_POINTSIZE_MAX] = tmpfloat.d;
+    state->render_states[WINED3DRS_INDEXEDVERTEXBLENDENABLE] = FALSE;
+    state->render_states[WINED3DRS_COLORWRITEENABLE] = 0x0000000f;
     tmpfloat.f = 0.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_TWEENFACTOR,              tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_BLENDOP,                  WINED3DBLENDOP_ADD);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_POSITIONDEGREE,           WINED3DDEGREE_CUBIC);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_NORMALDEGREE,             WINED3DDEGREE_LINEAR);
+    state->render_states[WINED3DRS_TWEENFACTOR] = tmpfloat.d;
+    state->render_states[WINED3DRS_BLENDOP] = WINED3DBLENDOP_ADD;
+    state->render_states[WINED3DRS_POSITIONDEGREE] = WINED3DDEGREE_CUBIC;
+    state->render_states[WINED3DRS_NORMALDEGREE] = WINED3DDEGREE_LINEAR;
     /* states new in d3d9 */
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SCISSORTESTENABLE,        FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SLOPESCALEDEPTHBIAS,      0);
+    state->render_states[WINED3DRS_SCISSORTESTENABLE] = FALSE;
+    state->render_states[WINED3DRS_SLOPESCALEDEPTHBIAS] = 0;
     tmpfloat.f = 1.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_MINTESSELLATIONLEVEL,     tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_MAXTESSELLATIONLEVEL,     tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ANTIALIASEDLINEENABLE,    FALSE);
+    state->render_states[WINED3DRS_MINTESSELLATIONLEVEL] = tmpfloat.d;
+    state->render_states[WINED3DRS_MAXTESSELLATIONLEVEL] = tmpfloat.d;
+    state->render_states[WINED3DRS_ANTIALIASEDLINEENABLE] = FALSE;
     tmpfloat.f = 0.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ADAPTIVETESS_X,           tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ADAPTIVETESS_Y,           tmpfloat.d);
+    state->render_states[WINED3DRS_ADAPTIVETESS_X] = tmpfloat.d;
+    state->render_states[WINED3DRS_ADAPTIVETESS_Y] = tmpfloat.d;
     tmpfloat.f = 1.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ADAPTIVETESS_Z,           tmpfloat.d);
+    state->render_states[WINED3DRS_ADAPTIVETESS_Z] = tmpfloat.d;
     tmpfloat.f = 0.0f;
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ADAPTIVETESS_W,           tmpfloat.d);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_ENABLEADAPTIVETESSELLATION, FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_TWOSIDEDSTENCILMODE,      FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_CCW_STENCILFAIL,          WINED3DSTENCILOP_KEEP);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_CCW_STENCILZFAIL,         WINED3DSTENCILOP_KEEP);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_CCW_STENCILPASS,          WINED3DSTENCILOP_KEEP);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_CCW_STENCILFUNC,          WINED3DCMP_ALWAYS);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_COLORWRITEENABLE1,        0x0000000F);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_COLORWRITEENABLE2,        0x0000000F);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_COLORWRITEENABLE3,        0x0000000F);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_BLENDFACTOR,              0xFFFFFFFF);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SRGBWRITEENABLE,          0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_DEPTHBIAS,                0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP8,  0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP9,  0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP10, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP11, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP12, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP13, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP14, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_WRAP15, 0);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SEPARATEALPHABLENDENABLE, FALSE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_SRCBLENDALPHA,            WINED3DBLEND_ONE);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_DESTBLENDALPHA,           WINED3DBLEND_ZERO);
-    IWineD3DDevice_SetRenderState(device, WINED3DRS_BLENDOPALPHA,             WINED3DBLENDOP_ADD);
+    state->render_states[WINED3DRS_ADAPTIVETESS_W] = tmpfloat.d;
+    state->render_states[WINED3DRS_ENABLEADAPTIVETESSELLATION] = FALSE;
+    state->render_states[WINED3DRS_TWOSIDEDSTENCILMODE] = FALSE;
+    state->render_states[WINED3DRS_CCW_STENCILFAIL] = WINED3DSTENCILOP_KEEP;
+    state->render_states[WINED3DRS_CCW_STENCILZFAIL] = WINED3DSTENCILOP_KEEP;
+    state->render_states[WINED3DRS_CCW_STENCILPASS] = WINED3DSTENCILOP_KEEP;
+    state->render_states[WINED3DRS_CCW_STENCILFUNC] = WINED3DCMP_ALWAYS;
+    state->render_states[WINED3DRS_COLORWRITEENABLE1] = 0x0000000f;
+    state->render_states[WINED3DRS_COLORWRITEENABLE2] = 0x0000000f;
+    state->render_states[WINED3DRS_COLORWRITEENABLE3] = 0x0000000f;
+    state->render_states[WINED3DRS_BLENDFACTOR] = 0xFFFFFFFF;
+    state->render_states[WINED3DRS_SRGBWRITEENABLE] = 0;
+    state->render_states[WINED3DRS_DEPTHBIAS] = 0;
+    state->render_states[WINED3DRS_WRAP8] = 0;
+    state->render_states[WINED3DRS_WRAP9] = 0;
+    state->render_states[WINED3DRS_WRAP10] = 0;
+    state->render_states[WINED3DRS_WRAP11] = 0;
+    state->render_states[WINED3DRS_WRAP12] = 0;
+    state->render_states[WINED3DRS_WRAP13] = 0;
+    state->render_states[WINED3DRS_WRAP14] = 0;
+    state->render_states[WINED3DRS_WRAP15] = 0;
+    state->render_states[WINED3DRS_SEPARATEALPHABLENDENABLE] = FALSE;
+    state->render_states[WINED3DRS_SRCBLENDALPHA] = WINED3DBLEND_ONE;
+    state->render_states[WINED3DRS_DESTBLENDALPHA] = WINED3DBLEND_ZERO;
+    state->render_states[WINED3DRS_BLENDOPALPHA] = WINED3DBLENDOP_ADD;
 
     /* clipping status */
-    This->clip_status.ClipUnion = 0;
-    This->clip_status.ClipIntersection = 0xFFFFFFFF;
+    state->clip_status.ClipUnion = 0;
+    state->clip_status.ClipIntersection = 0xFFFFFFFF;
 
     /* Texture Stage States - Put directly into state block, we will call function below */
-    for (i = 0; i < MAX_TEXTURES; i++) {
-        TRACE("Setting up default texture states for texture Stage %d\n", i);
-        memcpy(&This->transforms[WINED3DTS_TEXTURE0 + i], identity, sizeof(identity));
-        This->textureState[i][WINED3DTSS_COLOROP               ] = (i==0)? WINED3DTOP_MODULATE :  WINED3DTOP_DISABLE;
-        This->textureState[i][WINED3DTSS_COLORARG1             ] = WINED3DTA_TEXTURE;
-        This->textureState[i][WINED3DTSS_COLORARG2             ] = WINED3DTA_CURRENT;
-        This->textureState[i][WINED3DTSS_ALPHAOP               ] = (i==0)? WINED3DTOP_SELECTARG1 :  WINED3DTOP_DISABLE;
-        This->textureState[i][WINED3DTSS_ALPHAARG1             ] = WINED3DTA_TEXTURE;
-        This->textureState[i][WINED3DTSS_ALPHAARG2             ] = WINED3DTA_CURRENT;
-        This->textureState[i][WINED3DTSS_BUMPENVMAT00          ] = 0;
-        This->textureState[i][WINED3DTSS_BUMPENVMAT01          ] = 0;
-        This->textureState[i][WINED3DTSS_BUMPENVMAT10          ] = 0;
-        This->textureState[i][WINED3DTSS_BUMPENVMAT11          ] = 0;
-        This->textureState[i][WINED3DTSS_TEXCOORDINDEX         ] = i;
-        This->textureState[i][WINED3DTSS_BUMPENVLSCALE         ] = 0;
-        This->textureState[i][WINED3DTSS_BUMPENVLOFFSET        ] = 0;
-        This->textureState[i][WINED3DTSS_TEXTURETRANSFORMFLAGS ] = WINED3DTTFF_DISABLE;
-        This->textureState[i][WINED3DTSS_COLORARG0             ] = WINED3DTA_CURRENT;
-        This->textureState[i][WINED3DTSS_ALPHAARG0             ] = WINED3DTA_CURRENT;
-        This->textureState[i][WINED3DTSS_RESULTARG             ] = WINED3DTA_CURRENT;
-    }
-    This->lowest_disabled_stage = 1;
+    for (i = 0; i < MAX_TEXTURES; ++i)
+    {
+        TRACE("Setting up default texture states for texture Stage %u.\n", i);
+        memcpy(&state->transforms[WINED3DTS_TEXTURE0 + i], identity, sizeof(identity));
+        state->texture_states[i][WINED3DTSS_COLOROP] = i ? WINED3DTOP_DISABLE : WINED3DTOP_MODULATE;
+        state->texture_states[i][WINED3DTSS_COLORARG1] = WINED3DTA_TEXTURE;
+        state->texture_states[i][WINED3DTSS_COLORARG2] = WINED3DTA_CURRENT;
+        state->texture_states[i][WINED3DTSS_ALPHAOP] = i ? WINED3DTOP_DISABLE : WINED3DTOP_SELECTARG1;
+        state->texture_states[i][WINED3DTSS_ALPHAARG1] = WINED3DTA_TEXTURE;
+        state->texture_states[i][WINED3DTSS_ALPHAARG2] = WINED3DTA_CURRENT;
+        state->texture_states[i][WINED3DTSS_BUMPENVMAT00] = 0;
+        state->texture_states[i][WINED3DTSS_BUMPENVMAT01] = 0;
+        state->texture_states[i][WINED3DTSS_BUMPENVMAT10] = 0;
+        state->texture_states[i][WINED3DTSS_BUMPENVMAT11] = 0;
+        state->texture_states[i][WINED3DTSS_TEXCOORDINDEX] = i;
+        state->texture_states[i][WINED3DTSS_BUMPENVLSCALE] = 0;
+        state->texture_states[i][WINED3DTSS_BUMPENVLOFFSET] = 0;
+        state->texture_states[i][WINED3DTSS_TEXTURETRANSFORMFLAGS] = WINED3DTTFF_DISABLE;
+        state->texture_states[i][WINED3DTSS_COLORARG0] = WINED3DTA_CURRENT;
+        state->texture_states[i][WINED3DTSS_ALPHAARG0] = WINED3DTA_CURRENT;
+        state->texture_states[i][WINED3DTSS_RESULTARG] = WINED3DTA_CURRENT;
+    }
+    state->lowest_disabled_stage = 1;
 
         /* Sampler states*/
-    for (i = 0 ; i <  MAX_COMBINED_SAMPLERS; i++) {
-        TRACE("Setting up default samplers states for sampler %d\n", i);
-        This->samplerState[i][WINED3DSAMP_ADDRESSU         ] = WINED3DTADDRESS_WRAP;
-        This->samplerState[i][WINED3DSAMP_ADDRESSV         ] = WINED3DTADDRESS_WRAP;
-        This->samplerState[i][WINED3DSAMP_ADDRESSW         ] = WINED3DTADDRESS_WRAP;
-        This->samplerState[i][WINED3DSAMP_BORDERCOLOR      ] = 0x00;
-        This->samplerState[i][WINED3DSAMP_MAGFILTER        ] = WINED3DTEXF_POINT;
-        This->samplerState[i][WINED3DSAMP_MINFILTER        ] = WINED3DTEXF_POINT;
-        This->samplerState[i][WINED3DSAMP_MIPFILTER        ] = WINED3DTEXF_NONE;
-        This->samplerState[i][WINED3DSAMP_MIPMAPLODBIAS    ] = 0;
-        This->samplerState[i][WINED3DSAMP_MAXMIPLEVEL      ] = 0;
-        This->samplerState[i][WINED3DSAMP_MAXANISOTROPY    ] = 1;
-        This->samplerState[i][WINED3DSAMP_SRGBTEXTURE      ] = 0;
-        This->samplerState[i][WINED3DSAMP_ELEMENTINDEX     ] = 0; /* TODO: Indicates which element of a  multielement texture to use */
-        This->samplerState[i][WINED3DSAMP_DMAPOFFSET       ] = 0; /* TODO: Vertex offset in the presampled displacement map */
+    for (i = 0 ; i <  MAX_COMBINED_SAMPLERS; ++i)
+    {
+        TRACE("Setting up default samplers states for sampler %u.\n", i);
+        state->sampler_states[i][WINED3DSAMP_ADDRESSU] = WINED3DTADDRESS_WRAP;
+        state->sampler_states[i][WINED3DSAMP_ADDRESSV] = WINED3DTADDRESS_WRAP;
+        state->sampler_states[i][WINED3DSAMP_ADDRESSW] = WINED3DTADDRESS_WRAP;
+        state->sampler_states[i][WINED3DSAMP_BORDERCOLOR] = 0;
+        state->sampler_states[i][WINED3DSAMP_MAGFILTER] = WINED3DTEXF_POINT;
+        state->sampler_states[i][WINED3DSAMP_MINFILTER] = WINED3DTEXF_POINT;
+        state->sampler_states[i][WINED3DSAMP_MIPFILTER] = WINED3DTEXF_NONE;
+        state->sampler_states[i][WINED3DSAMP_MIPMAPLODBIAS] = 0;
+        state->sampler_states[i][WINED3DSAMP_MAXMIPLEVEL] = 0;
+        state->sampler_states[i][WINED3DSAMP_MAXANISOTROPY] = 1;
+        state->sampler_states[i][WINED3DSAMP_SRGBTEXTURE] = 0;
+        /* TODO: Indicates which element of a multielement texture to use. */
+        state->sampler_states[i][WINED3DSAMP_ELEMENTINDEX] = 0;
+        /* TODO: Vertex offset in the presampled displacement map. */
+        state->sampler_states[i][WINED3DSAMP_DMAPOFFSET] = 0;
     }
 
     for (i = 0; i < gl_info->limits.textures; ++i)
     {
-        /* Note: This avoids calling SetTexture, so pretend it has been called */
-        This->changed.textures |= 1 << i;
-        This->textures[i]         = NULL;
+        state->textures[i] = NULL;
     }
 
     /* check the return values, because the GetBackBuffer call isn't valid for ddraw */
-    hr = IWineD3DDevice_GetSwapChain(device, 0, &swapchain);
-    if( hr == WINED3D_OK && swapchain != NULL) {
-        WINED3DVIEWPORT vp;
-
+    hr = IWineD3DDevice_GetSwapChain((IWineD3DDevice *)device, 0, &swapchain);
+    if (SUCCEEDED(hr) && swapchain)
+    {
         hr = IWineD3DSwapChain_GetBackBuffer(swapchain, 0, WINED3DBACKBUFFER_TYPE_MONO, &backbuffer);
         if (SUCCEEDED(hr) && backbuffer)
         {
             WINED3DSURFACE_DESC desc;
-            RECT scissorrect;
 
             IWineD3DSurface_GetDesc(backbuffer, &desc);
             IWineD3DSurface_Release(backbuffer);
 
             /* Set the default scissor rect values */
-            scissorrect.left = 0;
-            scissorrect.right = desc.width;
-            scissorrect.top = 0;
-            scissorrect.bottom = desc.height;
-            hr = IWineD3DDevice_SetScissorRect(device, &scissorrect);
-            if (FAILED(hr)) ERR("This should never happen, expect rendering issues!\n");
+            state->scissor_rect.left = 0;
+            state->scissor_rect.right = desc.width;
+            state->scissor_rect.top = 0;
+            state->scissor_rect.bottom = desc.height;
         }
 
         /* Set the default viewport */
-        vp.X      = 0;
-        vp.Y      = 0;
-        vp.Width  = ((IWineD3DSwapChainImpl *)swapchain)->presentParms.BackBufferWidth;
-        vp.Height = ((IWineD3DSwapChainImpl *)swapchain)->presentParms.BackBufferHeight;
-        vp.MinZ   = 0.0f;
-        vp.MaxZ   = 1.0f;
-        IWineD3DDevice_SetViewport(device, &vp);
+        state->viewport.X = 0;
+        state->viewport.Y = 0;
+        state->viewport.Width = ((IWineD3DSwapChainImpl *)swapchain)->presentParms.BackBufferWidth;
+        state->viewport.Height = ((IWineD3DSwapChainImpl *)swapchain)->presentParms.BackBufferHeight;
+        state->viewport.MinZ = 0.0f;
+        state->viewport.MaxZ = 1.0f;
 
         IWineD3DSwapChain_Release(swapchain);
     }
 
-    TRACE("-----------------------> Device defaults now set up...\n");
-    return WINED3D_OK;
+    TRACE("Done.\n");
 }
 
 /**********************************************************
@@ -1319,7 +1339,6 @@ static const IWineD3DStateBlockVtbl IWineD3DStateBlock_Vtbl =
     /* IWineD3DStateBlock */
     IWineD3DStateBlockImpl_Capture,
     IWineD3DStateBlockImpl_Apply,
-    IWineD3DStateBlockImpl_InitStartupStateBlock
 };
 
 HRESULT stateblock_init(IWineD3DStateBlockImpl *stateblock, IWineD3DDeviceImpl *device, WINED3DSTATEBLOCKTYPE type)
@@ -1334,7 +1353,7 @@ HRESULT stateblock_init(IWineD3DStateBlockImpl *stateblock, IWineD3DDeviceImpl *
 
     for (i = 0; i < LIGHTMAP_SIZE; i++)
     {
-        list_init(&stateblock->lightMap[i]);
+        list_init(&stateblock->state.light_map[i]);
     }
 
     hr = stateblock_allocate_shader_constants(stateblock);
@@ -1350,7 +1369,7 @@ HRESULT stateblock_init(IWineD3DStateBlockImpl *stateblock, IWineD3DDeviceImpl *
     switch (type)
     {
         case WINED3DSBT_ALL:
-            stateblock_init_lights(stateblock, device->stateBlock->lightMap);
+            stateblock_init_lights(stateblock, device->stateBlock->state.light_map);
             stateblock_savedstates_set_all(&stateblock->changed, device->d3d_vshader_constantF,
                                            device->d3d_pshader_constantF);
             break;
@@ -1360,7 +1379,7 @@ HRESULT stateblock_init(IWineD3DStateBlockImpl *stateblock, IWineD3DDeviceImpl *
             break;
 
         case WINED3DSBT_VERTEXSTATE:
-            stateblock_init_lights(stateblock, device->stateBlock->lightMap);
+            stateblock_init_lights(stateblock, device->stateBlock->state.light_map);
             stateblock_savedstates_set_vertex(&stateblock->changed, device->d3d_vshader_constantF);
             break;
 
index 0903f6e..442ce75 100644 (file)
@@ -36,44 +36,42 @@ WINE_DECLARE_DEBUG_CHANNEL(d3d);
 
 static void surface_cleanup(IWineD3DSurfaceImpl *This)
 {
-    IWineD3DDeviceImpl *device = This->resource.device;
-    const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    struct wined3d_context *context = NULL;
-    renderbuffer_entry_t *entry, *entry2;
-
     TRACE("(%p) : Cleaning up.\n", This);
 
-    /* Need a context to destroy the texture. Use the currently active render
-     * target, but only if the primary render target exists. Otherwise
-     * lastActiveRenderTarget is garbage. When destroying the primary render
-     * target, Uninit3D() will activate a context before doing anything. */
-    if (device->render_targets && device->render_targets[0])
+    if (This->texture_name || (This->Flags & SFLAG_PBO) || !list_empty(&This->renderbuffers))
     {
-        context = context_acquire(device, NULL);
-    }
+        const struct wined3d_gl_info *gl_info;
+        renderbuffer_entry_t *entry, *entry2;
+        struct wined3d_context *context;
 
-    ENTER_GL();
+        context = context_acquire(This->resource.device, NULL);
+        gl_info = context->gl_info;
 
-    if (This->texture_name)
-    {
-        /* Release the OpenGL texture. */
-        TRACE("Deleting texture %u.\n", This->texture_name);
-        glDeleteTextures(1, &This->texture_name);
-    }
+        ENTER_GL();
 
-    if (This->Flags & SFLAG_PBO)
-    {
-        /* Delete the PBO. */
-        GL_EXTCALL(glDeleteBuffersARB(1, &This->pbo));
-    }
+        if (This->texture_name)
+        {
+            TRACE("Deleting texture %u.\n", This->texture_name);
+            glDeleteTextures(1, &This->texture_name);
+        }
 
-    LIST_FOR_EACH_ENTRY_SAFE(entry, entry2, &This->renderbuffers, renderbuffer_entry_t, entry)
-    {
-        gl_info->fbo_ops.glDeleteRenderbuffers(1, &entry->id);
-        HeapFree(GetProcessHeap(), 0, entry);
-    }
+        if (This->Flags & SFLAG_PBO)
+        {
+            TRACE("Deleting PBO %u.\n", This->pbo);
+            GL_EXTCALL(glDeleteBuffersARB(1, &This->pbo));
+        }
 
-    LEAVE_GL();
+        LIST_FOR_EACH_ENTRY_SAFE(entry, entry2, &This->renderbuffers, renderbuffer_entry_t, entry)
+        {
+            TRACE("Deleting renderbuffer %u.\n", entry->id);
+            gl_info->fbo_ops.glDeleteRenderbuffers(1, &entry->id);
+            HeapFree(GetProcessHeap(), 0, entry);
+        }
+
+        LEAVE_GL();
+
+        context_release(context);
+    }
 
     if (This->Flags & SFLAG_DIBSECTION)
     {
@@ -92,33 +90,39 @@ static void surface_cleanup(IWineD3DSurfaceImpl *This)
     HeapFree(GetProcessHeap(), 0, This->palette9);
 
     resource_cleanup((IWineD3DResource *)This);
-
-    if (context) context_release(context);
 }
 
-UINT surface_calculate_size(const struct wined3d_format_desc *format_desc, UINT alignment, UINT width, UINT height)
+void surface_set_container(IWineD3DSurfaceImpl *surface, enum wined3d_container_type type, IWineD3DBase *container)
 {
-    UINT size;
+    TRACE("surface %p, container %p.\n", surface, container);
 
-    if (format_desc->format == WINED3DFMT_UNKNOWN)
-    {
-        size = 0;
-    }
-    else if (format_desc->Flags & WINED3DFMT_FLAG_COMPRESSED)
+    if (!container && type != WINED3D_CONTAINER_NONE)
+        ERR("Setting NULL container of type %#x.\n", type);
+
+    if (type == WINED3D_CONTAINER_SWAPCHAIN)
     {
-        UINT row_block_count = (width + format_desc->block_width - 1) / format_desc->block_width;
-        UINT row_count = (height + format_desc->block_height - 1) / format_desc->block_height;
-        size = row_count * row_block_count * format_desc->block_byte_count;
+        surface->get_drawable_size = get_drawable_size_swapchain;
     }
     else
     {
-        /* The pitch is a multiple of 4 bytes. */
-        size = height * (((width * format_desc->byte_count) + alignment - 1) & ~(alignment - 1));
-    }
+        switch (wined3d_settings.offscreen_rendering_mode)
+        {
+            case ORM_FBO:
+                surface->get_drawable_size = get_drawable_size_fbo;
+                break;
+
+            case ORM_BACKBUFFER:
+                surface->get_drawable_size = get_drawable_size_backbuffer;
+                break;
 
-    if (format_desc->heightscale != 0.0f) size *= format_desc->heightscale;
+            default:
+                ERR("Unhandled offscreen rendering mode %#x.\n", wined3d_settings.offscreen_rendering_mode);
+                return;
+        }
+    }
 
-    return size;
+    surface->container.type = type;
+    surface->container.u.base = container;
 }
 
 struct blt_info
@@ -287,7 +291,6 @@ static inline void surface_get_rect(IWineD3DSurfaceImpl *This, const RECT *rect_
 /* GL locking and context activation is done by the caller */
 void draw_textured_quad(IWineD3DSurfaceImpl *src_surface, const RECT *src_rect, const RECT *dst_rect, WINED3DTEXTUREFILTERTYPE Filter)
 {
-    IWineD3DBaseTextureImpl *texture;
     struct blt_info info;
 
     surface_get_blt_info(src_surface->texture_target, src_rect, src_surface->pow2Width, src_surface->pow2Height, &info);
@@ -332,22 +335,22 @@ void draw_textured_quad(IWineD3DSurfaceImpl *src_surface, const RECT *src_rect,
 
     /* We changed the filtering settings on the texture. Inform the
      * container about this to get the filters reset properly next draw. */
-    if (SUCCEEDED(IWineD3DSurface_GetContainer((IWineD3DSurface *)src_surface, &IID_IWineD3DBaseTexture, (void **)&texture)))
+    if (src_surface->container.type == WINED3D_CONTAINER_TEXTURE)
     {
+        IWineD3DBaseTextureImpl *texture = src_surface->container.u.texture;
         texture->baseTexture.texture_rgb.states[WINED3DTEXSTA_MAGFILTER] = WINED3DTEXF_POINT;
         texture->baseTexture.texture_rgb.states[WINED3DTEXSTA_MINFILTER] = WINED3DTEXF_POINT;
         texture->baseTexture.texture_rgb.states[WINED3DTEXSTA_MIPFILTER] = WINED3DTEXF_NONE;
-        IWineD3DBaseTexture_Release((IWineD3DBaseTexture *)texture);
     }
 }
 
 HRESULT surface_init(IWineD3DSurfaceImpl *surface, WINED3DSURFTYPE surface_type, UINT alignment,
         UINT width, UINT height, UINT level, BOOL lockable, BOOL discard, WINED3DMULTISAMPLE_TYPE multisample_type,
-        UINT multisample_quality, IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format,
-        WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        UINT multisample_quality, IWineD3DDeviceImpl *device, DWORD usage, enum wined3d_format_id format_id,
+        WINED3DPOOL pool, void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, gl_info);
+    const struct wined3d_format *format = wined3d_get_format(gl_info, format_id);
     void (*cleanup)(IWineD3DSurfaceImpl *This);
     unsigned int resource_size;
     HRESULT hr;
@@ -360,7 +363,7 @@ HRESULT surface_init(IWineD3DSurfaceImpl *surface, WINED3DSURFTYPE surface_type,
 
     /* FIXME: Check that the format is supported by the device. */
 
-    resource_size = surface_calculate_size(format_desc, alignment, width, height);
+    resource_size = wined3d_format_calculate_size(format, alignment, width, height);
 
     /* Look at the implementation and set the correct Vtable. */
     switch (surface_type)
@@ -381,7 +384,7 @@ HRESULT surface_init(IWineD3DSurfaceImpl *surface, WINED3DSURFTYPE surface_type,
     }
 
     hr = resource_init((IWineD3DResource *)surface, WINED3DRTYPE_SURFACE,
-            device, resource_size, usage, format_desc, pool, parent, parent_ops);
+            device, resource_size, usage, format, pool, parent, parent_ops);
     if (FAILED(hr))
     {
         WARN("Failed to initialize resource, returning %#x.\n", hr);
@@ -389,7 +392,7 @@ HRESULT surface_init(IWineD3DSurfaceImpl *surface, WINED3DSURFTYPE surface_type,
     }
 
     /* "Standalone" surface. */
-    IWineD3DSurface_SetContainer((IWineD3DSurface *)surface, NULL);
+    surface_set_container(surface, WINED3D_CONTAINER_NONE, NULL);
 
     surface->currentDesc.Width = width;
     surface->currentDesc.Height = height;
@@ -401,7 +404,7 @@ HRESULT surface_init(IWineD3DSurfaceImpl *surface, WINED3DSURFTYPE surface_type,
     /* Flags */
     surface->Flags = SFLAG_NORMCOORD; /* Default to normalized coords. */
     if (discard) surface->Flags |= SFLAG_DISCARD;
-    if (lockable || format == WINED3DFMT_D16_LOCKABLE) surface->Flags |= SFLAG_LOCKABLE;
+    if (lockable || format_id == WINED3DFMT_D16_LOCKABLE) surface->Flags |= SFLAG_LOCKABLE;
 
     /* Quick lockable sanity check.
      * TODO: remove this after surfaces, usage and lockability have been debugged properly
@@ -489,8 +492,8 @@ void surface_set_texture_name(IWineD3DSurfaceImpl *surface, GLuint new_name, BOO
         /* FIXME: We shouldn't need to remove SFLAG_INTEXTURE if the
          * surface has no texture name yet. See if we can get rid of this. */
         if (surface->Flags & flag)
-            ERR("Surface has SFLAG_INTEXTURE set, but no texture name\n");
-        IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, flag, FALSE);
+            ERR("Surface has %s set, but no texture name.\n", debug_surflocation(flag));
+        surface_modify_location(surface, flag, FALSE);
     }
 
     *name = new_name;
@@ -551,7 +554,7 @@ static BOOL primary_render_target_is_p8(IWineD3DDeviceImpl *device)
     {
         IWineD3DSurfaceImpl *render_target = device->render_targets[0];
         if ((render_target->resource.usage & WINED3DUSAGE_RENDERTARGET)
-                && (render_target->resource.format_desc->format == WINED3DFMT_P8_UINT))
+                && (render_target->resource.format->id == WINED3DFMT_P8_UINT))
             return TRUE;
     }
     return FALSE;
@@ -562,21 +565,21 @@ static BOOL primary_render_target_is_p8(IWineD3DDeviceImpl *device)
 /* Context activation is done by the caller. */
 static void surface_download_data(IWineD3DSurfaceImpl *This, const struct wined3d_gl_info *gl_info)
 {
-    const struct wined3d_format_desc *format_desc = This->resource.format_desc;
+    const struct wined3d_format *format = This->resource.format;
 
     /* Only support read back of converted P8 surfaces */
-    if (This->Flags & SFLAG_CONVERTED && format_desc->format != WINED3DFMT_P8_UINT)
+    if (This->Flags & SFLAG_CONVERTED && format->id != WINED3DFMT_P8_UINT)
     {
-        FIXME("Read back converted textures unsupported, format=%s\n", debug_d3dformat(format_desc->format));
+        FIXME("Readback conversion not supported for format %s.\n", debug_d3dformat(format->id));
         return;
     }
 
     ENTER_GL();
 
-    if (format_desc->Flags & WINED3DFMT_FLAG_COMPRESSED)
+    if (format->Flags & WINED3DFMT_FLAG_COMPRESSED)
     {
         TRACE("(%p) : Calling glGetCompressedTexImageARB level %d, format %#x, type %#x, data %p.\n",
-                This, This->texture_level, format_desc->glFormat, format_desc->glType,
+                This, This->texture_level, format->glFormat, format->glType,
                 This->resource.allocatedMemory);
 
         if (This->Flags & SFLAG_PBO)
@@ -598,21 +601,21 @@ static void surface_download_data(IWineD3DSurfaceImpl *This, const struct wined3
         LEAVE_GL();
     } else {
         void *mem;
-        GLenum format = format_desc->glFormat;
-        GLenum type = format_desc->glType;
+        GLenum gl_format = format->glFormat;
+        GLenum gl_type = format->glType;
         int src_pitch = 0;
         int dst_pitch = 0;
 
         /* In case of P8 the index is stored in the alpha component if the primary render target uses P8 */
-        if (format_desc->format == WINED3DFMT_P8_UINT && primary_render_target_is_p8(This->resource.device))
+        if (format->id == WINED3DFMT_P8_UINT && primary_render_target_is_p8(This->resource.device))
         {
-            format = GL_ALPHA;
-            type = GL_UNSIGNED_BYTE;
+            gl_format = GL_ALPHA;
+            gl_type = GL_UNSIGNED_BYTE;
         }
 
         if (This->Flags & SFLAG_NONPOW2) {
             unsigned char alignment = This->resource.device->surface_alignment;
-            src_pitch = format_desc->byte_count * This->pow2Width;
+            src_pitch = format->byte_count * This->pow2Width;
             dst_pitch = IWineD3DSurface_GetPitch((IWineD3DSurface *) This);
             src_pitch = (src_pitch + alignment - 1) & ~(alignment - 1);
             mem = HeapAlloc(GetProcessHeap(), 0, src_pitch * This->pow2Height);
@@ -621,19 +624,19 @@ static void surface_download_data(IWineD3DSurfaceImpl *This, const struct wined3
         }
 
         TRACE("(%p) : Calling glGetTexImage level %d, format %#x, type %#x, data %p\n",
-                This, This->texture_level, format, type, mem);
+                This, This->texture_level, gl_format, gl_type, mem);
 
         if(This->Flags & SFLAG_PBO) {
             GL_EXTCALL(glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, This->pbo));
             checkGLcall("glBindBufferARB");
 
-            glGetTexImage(This->texture_target, This->texture_level, format, type, NULL);
+            glGetTexImage(This->texture_target, This->texture_level, gl_format, gl_type, NULL);
             checkGLcall("glGetTexImage");
 
             GL_EXTCALL(glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, 0));
             checkGLcall("glBindBufferARB");
         } else {
-            glGetTexImage(This->texture_target, This->texture_level, format, type, mem);
+            glGetTexImage(This->texture_target, This->texture_level, gl_format, gl_type, mem);
             checkGLcall("glGetTexImage");
         }
         LEAVE_GL();
@@ -714,7 +717,7 @@ static void surface_download_data(IWineD3DSurfaceImpl *This, const struct wined3
  * correct texture. */
 /* Context activation is done by the caller. */
 static void surface_upload_data(IWineD3DSurfaceImpl *This, const struct wined3d_gl_info *gl_info,
-        const struct wined3d_format_desc *format_desc, BOOL srgb, const GLvoid *data)
+        const struct wined3d_format *format, BOOL srgb, const GLvoid *data)
 {
     GLsizei width = This->currentDesc.Width;
     GLsizei height = This->currentDesc.Height;
@@ -722,23 +725,23 @@ static void surface_upload_data(IWineD3DSurfaceImpl *This, const struct wined3d_
 
     if (srgb)
     {
-        internal = format_desc->glGammaInternal;
+        internal = format->glGammaInternal;
     }
     else if (This->resource.usage & WINED3DUSAGE_RENDERTARGET && surface_is_offscreen(This))
     {
-        internal = format_desc->rtInternal;
+        internal = format->rtInternal;
     }
     else
     {
-        internal = format_desc->glInternal;
+        internal = format->glInternal;
     }
 
     TRACE("This %p, internal %#x, width %d, height %d, format %#x, type %#x, data %p.\n",
-            This, internal, width, height, format_desc->glFormat, format_desc->glType, data);
+            This, internal, width, height, format->glFormat, format->glType, data);
     TRACE("target %#x, level %u, resource size %u.\n",
             This->texture_target, This->texture_level, This->resource.size);
 
-    if (format_desc->heightscale != 1.0f && format_desc->heightscale != 0.0f) height *= format_desc->heightscale;
+    if (format->heightscale != 1.0f && format->heightscale != 0.0f) height *= format->heightscale;
 
     ENTER_GL();
 
@@ -751,7 +754,7 @@ static void surface_upload_data(IWineD3DSurfaceImpl *This, const struct wined3d_
         data = NULL;
     }
 
-    if (format_desc->Flags & WINED3DFMT_FLAG_COMPRESSED)
+    if (format->Flags & WINED3DFMT_FLAG_COMPRESSED)
     {
         TRACE("Calling glCompressedTexSubImage2DARB.\n");
 
@@ -764,7 +767,7 @@ static void surface_upload_data(IWineD3DSurfaceImpl *This, const struct wined3d_
         TRACE("Calling glTexSubImage2D.\n");
 
         glTexSubImage2D(This->texture_target, This->texture_level,
-                0, 0, width, height, format_desc->glFormat, format_desc->glType, data);
+                0, 0, width, height, format->glFormat, format->glType, data);
         checkGLcall("glTexSubImage2D");
     }
 
@@ -792,7 +795,7 @@ static void surface_upload_data(IWineD3DSurfaceImpl *This, const struct wined3d_
  * the correct texture. */
 /* Context activation is done by the caller. */
 static void surface_allocate_surface(IWineD3DSurfaceImpl *This, const struct wined3d_gl_info *gl_info,
-        const struct wined3d_format_desc *format_desc, BOOL srgb)
+        const struct wined3d_format *format, BOOL srgb)
 {
     BOOL enable_client_storage = FALSE;
     GLsizei width = This->pow2Width;
@@ -802,28 +805,30 @@ static void surface_allocate_surface(IWineD3DSurfaceImpl *This, const struct win
 
     if (srgb)
     {
-        internal = format_desc->glGammaInternal;
+        internal = format->glGammaInternal;
     }
     else if (This->resource.usage & WINED3DUSAGE_RENDERTARGET && surface_is_offscreen(This))
     {
-        internal = format_desc->rtInternal;
+        internal = format->rtInternal;
     }
     else
     {
-        internal = format_desc->glInternal;
+        internal = format->glInternal;
     }
 
-    if (format_desc->heightscale != 1.0f && format_desc->heightscale != 0.0f) height *= format_desc->heightscale;
+    if (format->heightscale != 1.0f && format->heightscale != 0.0f) height *= format->heightscale;
 
     TRACE("(%p) : Creating surface (target %#x)  level %d, d3d format %s, internal format %#x, width %d, height %d, gl format %#x, gl type=%#x\n",
-            This, This->texture_target, This->texture_level, debug_d3dformat(format_desc->format),
-            internal, width, height, format_desc->glFormat, format_desc->glType);
+            This, This->texture_target, This->texture_level, debug_d3dformat(format->id),
+            internal, width, height, format->glFormat, format->glType);
 
     ENTER_GL();
 
     if (gl_info->supported[APPLE_CLIENT_STORAGE])
     {
-        if(This->Flags & (SFLAG_NONPOW2 | SFLAG_DIBSECTION | SFLAG_CONVERTED) || This->resource.allocatedMemory == NULL) {
+        if (This->Flags & (SFLAG_NONPOW2 | SFLAG_DIBSECTION | SFLAG_CONVERTED)
+                || !This->resource.allocatedMemory)
+        {
             /* In some cases we want to disable client storage.
              * SFLAG_NONPOW2 has a bigger opengl texture than the client memory, and different pitches
              * SFLAG_DIBSECTION: Dibsections may have read / write protections on the memory. Avoid issues...
@@ -844,15 +849,16 @@ static void surface_allocate_surface(IWineD3DSurfaceImpl *This, const struct win
         }
     }
 
-    if (format_desc->Flags & WINED3DFMT_FLAG_COMPRESSED && mem)
+    if (format->Flags & WINED3DFMT_FLAG_COMPRESSED && mem)
     {
         GL_EXTCALL(glCompressedTexImage2DARB(This->texture_target, This->texture_level,
                 internal, width, height, 0, This->resource.size, mem));
+        checkGLcall("glCompressedTexImage2DARB");
     }
     else
     {
         glTexImage2D(This->texture_target, This->texture_level,
-                internal, width, height, 0, format_desc->glFormat, format_desc->glType, mem);
+                internal, width, height, 0, format->glFormat, format->glType, mem);
         checkGLcall("glTexImage2D");
     }
 
@@ -904,7 +910,7 @@ void surface_set_compatible_renderbuffer(IWineD3DSurfaceImpl *surface, unsigned
         gl_info->fbo_ops.glGenRenderbuffers(1, &renderbuffer);
         gl_info->fbo_ops.glBindRenderbuffer(GL_RENDERBUFFER, renderbuffer);
         gl_info->fbo_ops.glRenderbufferStorage(GL_RENDERBUFFER,
-                surface->resource.format_desc->glInternal, width, height);
+                surface->resource.format->glInternal, width, height);
 
         entry = HeapAlloc(GetProcessHeap(), 0, sizeof(renderbuffer_entry_t));
         entry->width = width;
@@ -920,11 +926,11 @@ void surface_set_compatible_renderbuffer(IWineD3DSurfaceImpl *surface, unsigned
 
 GLenum surface_get_gl_buffer(IWineD3DSurfaceImpl *surface)
 {
-    IWineD3DSwapChainImpl *swapchain = (IWineD3DSwapChainImpl *)surface->container;
+    IWineD3DSwapChainImpl *swapchain = surface->container.u.swapchain;
 
     TRACE("surface %p.\n", surface);
 
-    if (!(surface->Flags & SFLAG_SWAPCHAIN))
+    if (surface->container.type != WINED3D_CONTAINER_SWAPCHAIN)
     {
         ERR("Surface %p is not on a swapchain.\n", surface);
         return GL_NONE;
@@ -953,15 +959,13 @@ GLenum surface_get_gl_buffer(IWineD3DSurfaceImpl *surface)
 /* Slightly inefficient way to handle multiple dirty rects but it works :) */
 void surface_add_dirty_rect(IWineD3DSurfaceImpl *surface, const RECT *dirty_rect)
 {
-    IWineD3DBaseTexture *baseTexture = NULL;
-
     TRACE("surface %p, dirty_rect %s.\n", surface, wine_dbgstr_rect(dirty_rect));
 
     if (!(surface->Flags & SFLAG_INSYSMEM) && (surface->Flags & SFLAG_INTEXTURE))
         /* No partial locking for textures yet. */
-        IWineD3DSurface_LoadLocation((IWineD3DSurface *)surface, SFLAG_INSYSMEM, NULL);
+        surface_load_location(surface, SFLAG_INSYSMEM, NULL);
 
-    IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INSYSMEM, TRUE);
+    surface_modify_location(surface, SFLAG_INSYSMEM, TRUE);
     if (dirty_rect)
     {
         surface->dirtyRect.left = min(surface->dirtyRect.left, dirty_rect->left);
@@ -978,70 +982,67 @@ void surface_add_dirty_rect(IWineD3DSurfaceImpl *surface, const RECT *dirty_rect
     }
 
     /* if the container is a basetexture then mark it dirty. */
-    if (SUCCEEDED(IWineD3DSurface_GetContainer((IWineD3DSurface *)surface,
-            &IID_IWineD3DBaseTexture, (void **)&baseTexture)))
+    if (surface->container.type == WINED3D_CONTAINER_TEXTURE)
     {
-        TRACE("Passing to container\n");
-        IWineD3DBaseTexture_SetDirty(baseTexture, TRUE);
-        IWineD3DBaseTexture_Release(baseTexture);
+        TRACE("Passing to container.\n");
+        IWineD3DBaseTexture_SetDirty((IWineD3DBaseTexture *)surface->container.u.texture, TRUE);
     }
 }
 
-static BOOL surface_convert_color_to_argb(IWineD3DSurfaceImpl *This, DWORD color, DWORD *argb_color)
+static BOOL surface_convert_color_to_float(IWineD3DSurfaceImpl *surface, DWORD color, WINED3DCOLORVALUE *float_color)
 {
-    IWineD3DDeviceImpl *device = This->resource.device;
+    const struct wined3d_format *format = surface->resource.format;
+    IWineD3DDeviceImpl *device = surface->resource.device;
 
-    switch(This->resource.format_desc->format)
+    switch (format->id)
     {
         case WINED3DFMT_P8_UINT:
+            if (surface->palette)
             {
-                DWORD alpha;
-
-                if (primary_render_target_is_p8(device))
-                    alpha = color << 24;
-                else
-                    alpha = 0xFF000000;
-
-                if (This->palette) {
-                    *argb_color = (alpha |
-                            (This->palette->palents[color].peRed << 16) |
-                            (This->palette->palents[color].peGreen << 8) |
-                            (This->palette->palents[color].peBlue));
-                } else {
-                    *argb_color = alpha;
-                }
+                float_color->r = surface->palette->palents[color].peRed / 255.0f;
+                float_color->g = surface->palette->palents[color].peGreen / 255.0f;
+                float_color->b = surface->palette->palents[color].peBlue / 255.0f;
             }
+            else
+            {
+                float_color->r = 0.0f;
+                float_color->g = 0.0f;
+                float_color->b = 0.0f;
+            }
+            float_color->a = primary_render_target_is_p8(device) ? color / 255.0f : 1.0f;
             break;
 
         case WINED3DFMT_B5G6R5_UNORM:
-            {
-                if (color == 0xFFFF) {
-                    *argb_color = 0xFFFFFFFF;
-                } else {
-                    *argb_color = ((0xFF000000) |
-                            ((color & 0xF800) << 8) |
-                            ((color & 0x07E0) << 5) |
-                            ((color & 0x001F) << 3));
-                }
-            }
+            float_color->r = ((color >> 11) & 0x1f) / 31.0f;
+            float_color->g = ((color >> 5) & 0x3f) / 63.0f;
+            float_color->b = (color & 0x1f) / 31.0f;
+            float_color->a = 1.0f;
             break;
 
         case WINED3DFMT_B8G8R8_UNORM:
         case WINED3DFMT_B8G8R8X8_UNORM:
-            *argb_color = 0xFF000000 | color;
+            float_color->r = D3DCOLOR_R(color);
+            float_color->g = D3DCOLOR_G(color);
+            float_color->b = D3DCOLOR_B(color);
+            float_color->a = 1.0f;
             break;
 
         case WINED3DFMT_B8G8R8A8_UNORM:
-            *argb_color = color;
+            float_color->r = D3DCOLOR_R(color);
+            float_color->g = D3DCOLOR_G(color);
+            float_color->b = D3DCOLOR_B(color);
+            float_color->a = D3DCOLOR_A(color);
             break;
 
         default:
-            ERR("Unhandled conversion from %s to ARGB!\n", debug_d3dformat(This->resource.format_desc->format));
+            ERR("Unhandled conversion from %s to floating point.\n", debug_d3dformat(format->id));
             return FALSE;
     }
+
     return TRUE;
 }
 
+/* Do not call while under the GL lock. */
 static ULONG WINAPI IWineD3DSurfaceImpl_Release(IWineD3DSurface *iface)
 {
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
@@ -1064,37 +1065,38 @@ static ULONG WINAPI IWineD3DSurfaceImpl_Release(IWineD3DSurface *iface)
    IWineD3DSurface IWineD3DResource parts follow
    **************************************************** */
 
+/* Do not call while under the GL lock. */
 void surface_internal_preload(IWineD3DSurfaceImpl *surface, enum WINED3DSRGB srgb)
 {
-    /* TODO: check for locks */
     IWineD3DDeviceImpl *device = surface->resource.device;
-    IWineD3DBaseTexture *baseTexture = NULL;
 
-    TRACE("(%p)Checking to see if the container is a base texture\n", surface);
-    if (SUCCEEDED(IWineD3DSurface_GetContainer((IWineD3DSurface *)surface,
-            &IID_IWineD3DBaseTexture, (void **)&baseTexture)))
+    TRACE("iface %p, srgb %#x.\n", surface, srgb);
+
+    if (surface->container.type == WINED3D_CONTAINER_TEXTURE)
+    {
+        IWineD3DBaseTextureImpl *texture = surface->container.u.texture;
+
+        TRACE("Passing to container.\n");
+        texture->baseTexture.internal_preload((IWineD3DBaseTexture *)texture, srgb);
+    }
+    else
     {
-        IWineD3DBaseTextureImpl *tex_impl = (IWineD3DBaseTextureImpl *)baseTexture;
-        TRACE("Passing to container\n");
-        tex_impl->baseTexture.internal_preload(baseTexture, srgb);
-        IWineD3DBaseTexture_Release(baseTexture);
-    } else {
         struct wined3d_context *context = NULL;
 
         TRACE("(%p) : About to load surface\n", surface);
 
         if (!device->isInDraw) context = context_acquire(device, NULL);
 
-        if (surface->resource.format_desc->format == WINED3DFMT_P8_UINT
-                || surface->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM)
+        if (surface->resource.format->id == WINED3DFMT_P8_UINT
+                || surface->resource.format->id == WINED3DFMT_P8_UINT_A8_UNORM)
         {
             if (palette9_changed(surface))
             {
                 TRACE("Reloading surface because the d3d8/9 palette was changed\n");
                 /* TODO: This is not necessarily needed with hw palettized texture support */
-                IWineD3DSurface_LoadLocation((IWineD3DSurface *)surface, SFLAG_INSYSMEM, NULL);
+                surface_load_location(surface, SFLAG_INSYSMEM, NULL);
                 /* Make sure the texture is reloaded because of the palette change, this kills performance though :( */
-                IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INTEXTURE, FALSE);
+                surface_modify_location(surface, SFLAG_INTEXTURE, FALSE);
             }
         }
 
@@ -1158,12 +1160,14 @@ BOOL surface_init_sysmem(IWineD3DSurfaceImpl *surface)
         memset(surface->resource.allocatedMemory, 0, surface->resource.size);
     }
 
-    IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INSYSMEM, TRUE);
+    surface_modify_location(surface, SFLAG_INSYSMEM, TRUE);
+
     return TRUE;
 }
 
-static void WINAPI IWineD3DSurfaceImpl_UnLoad(IWineD3DSurface *iface) {
-    IWineD3DBaseTexture *texture = NULL;
+/* Do not call while under the GL lock. */
+static void WINAPI IWineD3DSurfaceImpl_UnLoad(IWineD3DSurface *iface)
+{
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
     IWineD3DDeviceImpl *device = This->resource.device;
     const struct wined3d_gl_info *gl_info;
@@ -1188,11 +1192,11 @@ static void WINAPI IWineD3DSurfaceImpl_UnLoad(IWineD3DSurface *iface) {
     else
     {
         /* Load the surface into system memory */
-        IWineD3DSurface_LoadLocation(iface, SFLAG_INSYSMEM, NULL);
-        IWineD3DSurface_ModifyLocation(iface, SFLAG_INDRAWABLE, FALSE);
+        surface_load_location(This, SFLAG_INSYSMEM, NULL);
+        surface_modify_location(This, SFLAG_INDRAWABLE, FALSE);
     }
-    IWineD3DSurface_ModifyLocation(iface, SFLAG_INTEXTURE, FALSE);
-    IWineD3DSurface_ModifyLocation(iface, SFLAG_INSRGBTEX, FALSE);
+    surface_modify_location(This, SFLAG_INTEXTURE, FALSE);
+    surface_modify_location(This, SFLAG_INSRGBTEX, FALSE);
     This->Flags &= ~(SFLAG_ALLOCATED | SFLAG_SRGBALLOCATED);
 
     context = context_acquire(device, NULL);
@@ -1216,22 +1220,21 @@ static void WINAPI IWineD3DSurfaceImpl_UnLoad(IWineD3DSurface *iface) {
     list_init(&This->renderbuffers);
     This->current_renderbuffer = NULL;
 
-    /* If we're in a texture, the texture name belongs to the texture. Otherwise,
-     * destroy it
-     */
-    IWineD3DSurface_GetContainer(iface, &IID_IWineD3DBaseTexture, (void **) &texture);
-    if(!texture) {
+    /* If we're in a texture, the texture name belongs to the texture.
+     * Otherwise, destroy it. */
+    if (This->container.type != WINED3D_CONTAINER_TEXTURE)
+    {
         ENTER_GL();
         glDeleteTextures(1, &This->texture_name);
         This->texture_name = 0;
         glDeleteTextures(1, &This->texture_name_srgb);
         This->texture_name_srgb = 0;
         LEAVE_GL();
-    } else {
-        IWineD3DBaseTexture_Release(texture);
     }
 
     context_release(context);
+
+    resource_unload((IWineD3DResourceImpl *)This);
 }
 
 /* ******************************************************
@@ -1310,7 +1313,7 @@ static void read_from_framebuffer(IWineD3DSurfaceImpl *This, const RECT *rect, v
     }
     /* TODO: Get rid of the extra GetPitch call, LockRect does that too. Cache the pitch */
 
-    switch(This->resource.format_desc->format)
+    switch (This->resource.format->id)
     {
         case WINED3DFMT_P8_UINT:
         {
@@ -1320,7 +1323,7 @@ static void read_from_framebuffer(IWineD3DSurfaceImpl *This, const RECT *rect, v
                 fmt = GL_ALPHA;
                 type = GL_UNSIGNED_BYTE;
                 mem = dest;
-                bpp = This->resource.format_desc->byte_count;
+                bpp = This->resource.format->byte_count;
             } else {
                 /* GL can't return palettized data, so read ARGB pixels into a
                  * separate block of memory and convert them into palettized format
@@ -1340,22 +1343,23 @@ static void read_from_framebuffer(IWineD3DSurfaceImpl *This, const RECT *rect, v
                     LEAVE_GL();
                     return;
                 }
-                bpp = This->resource.format_desc->byte_count * 3;
+                bpp = This->resource.format->byte_count * 3;
             }
         }
         break;
 
         default:
             mem = dest;
-            fmt = This->resource.format_desc->glFormat;
-            type = This->resource.format_desc->glType;
-            bpp = This->resource.format_desc->byte_count;
+            fmt = This->resource.format->glFormat;
+            type = This->resource.format->glType;
+            bpp = This->resource.format->byte_count;
     }
 
     if(This->Flags & SFLAG_PBO) {
         GL_EXTCALL(glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, This->pbo));
         checkGLcall("glBindBufferARB");
-        if(mem != NULL) {
+        if (mem)
+        {
             ERR("mem not null for pbo -- unexpected\n");
             mem = NULL;
         }
@@ -1419,7 +1423,7 @@ static void read_from_framebuffer(IWineD3DSurfaceImpl *This, const RECT *rect, v
         row = HeapAlloc(GetProcessHeap(), 0, len);
         if(!row) {
             ERR("Out of memory\n");
-            if (This->resource.format_desc->format == WINED3DFMT_P8_UINT) HeapFree(GetProcessHeap(), 0, mem);
+            if (This->resource.format->id == WINED3DFMT_P8_UINT) HeapFree(GetProcessHeap(), 0, mem);
             LEAVE_GL();
             return;
         }
@@ -1450,7 +1454,7 @@ static void read_from_framebuffer(IWineD3DSurfaceImpl *This, const RECT *rect, v
      * the same color but we have no choice.
      * In case of P8 render targets, the index is stored in the alpha component so no conversion is needed.
      */
-    if (This->resource.format_desc->format == WINED3DFMT_P8_UINT && !primary_render_target_is_p8(device))
+    if (This->resource.format->id == WINED3DFMT_P8_UINT && !primary_render_target_is_p8(device))
     {
         const PALETTEENTRY *pal = NULL;
         DWORD width = pitch / 3;
@@ -1492,7 +1496,15 @@ static void read_from_framebuffer_texture(IWineD3DSurfaceImpl *This, BOOL srgb)
     IWineD3DDeviceImpl *device = This->resource.device;
     const struct wined3d_gl_info *gl_info;
     struct wined3d_context *context;
-    GLint prevRead;
+
+    if (!surface_is_offscreen(This))
+    {
+        /* We would need to flip onscreen surfaces, but there's no efficient
+         * way to do that here. It makes more sense for the caller to
+         * explicitly go through sysmem. */
+        ERR("Not supported for onscreen targets.\n");
+        return;
+    }
 
     /* Activate the surface to read from. In some situations it isn't the currently active target(e.g. backbuffer
      * locking during offscreen rendering). RESOURCELOAD is ok because glCopyTexSubImage2D isn't affected by any
@@ -1504,55 +1516,20 @@ static void read_from_framebuffer_texture(IWineD3DSurfaceImpl *This, BOOL srgb)
     surface_prepare_texture(This, gl_info, srgb);
     surface_bind_and_dirtify(This, srgb);
 
-    ENTER_GL();
-    glGetIntegerv(GL_READ_BUFFER, &prevRead);
-    LEAVE_GL();
-
-    /* Select the correct read buffer, and give some debug output.
-     * There is no need to keep track of the current read buffer or reset it, every part of the code
-     * that reads sets the read buffer as desired.
-     */
-    if (!surface_is_offscreen(This))
-    {
-        GLenum buffer = surface_get_gl_buffer(This);
-        TRACE("Locking %#x buffer\n", buffer);
-
-        ENTER_GL();
-        glReadBuffer(buffer);
-        checkGLcall("glReadBuffer");
-        LEAVE_GL();
-    }
-    else
-    {
-        /* Locking the primary render target which is not on a swapchain(=offscreen render target).
-         * Read from the back buffer
-         */
-        TRACE("Locking offscreen render target\n");
-        ENTER_GL();
-        glReadBuffer(device->offscreenBuffer);
-        checkGLcall("glReadBuffer");
-        LEAVE_GL();
-    }
+    TRACE("Reading back offscreen render target %p.\n", This);
 
     ENTER_GL();
-    /* If !SrcIsUpsideDown we should flip the surface.
-     * This can be done using glCopyTexSubImage2D but this
-     * is VERY slow, so don't do that. We should prevent
-     * this code from getting called in such cases or perhaps
-     * we can use FBOs */
+
+    glReadBuffer(device->offscreenBuffer);
+    checkGLcall("glReadBuffer");
 
     glCopyTexSubImage2D(This->texture_target, This->texture_level,
             0, 0, 0, 0, This->currentDesc.Width, This->currentDesc.Height);
     checkGLcall("glCopyTexSubImage2D");
 
-    glReadBuffer(prevRead);
-    checkGLcall("glReadBuffer");
-
     LEAVE_GL();
 
     context_release(context);
-
-    TRACE("Updated target %d\n", This->texture_target);
 }
 
 /* Context activation is done by the caller. */
@@ -1561,27 +1538,25 @@ static void surface_prepare_texture_internal(IWineD3DSurfaceImpl *surface,
 {
     DWORD alloc_flag = srgb ? SFLAG_SRGBALLOCATED : SFLAG_ALLOCATED;
     CONVERT_TYPES convert;
-    struct wined3d_format_desc desc;
+    struct wined3d_format format;
 
     if (surface->Flags & alloc_flag) return;
 
-    d3dfmt_get_conv(surface, TRUE, TRUE, &desc, &convert);
-    if(convert != NO_CONVERSION || desc.convert) surface->Flags |= SFLAG_CONVERTED;
+    d3dfmt_get_conv(surface, TRUE, TRUE, &format, &convert);
+    if (convert != NO_CONVERSION || format.convert) surface->Flags |= SFLAG_CONVERTED;
     else surface->Flags &= ~SFLAG_CONVERTED;
 
     surface_bind_and_dirtify(surface, srgb);
-    surface_allocate_surface(surface, gl_info, &desc, srgb);
+    surface_allocate_surface(surface, gl_info, &format, srgb);
     surface->Flags |= alloc_flag;
 }
 
 /* Context activation is done by the caller. */
 void surface_prepare_texture(IWineD3DSurfaceImpl *surface, const struct wined3d_gl_info *gl_info, BOOL srgb)
 {
-    IWineD3DBaseTextureImpl *texture;
-
-    if (SUCCEEDED(IWineD3DSurface_GetContainer((IWineD3DSurface *)surface,
-            &IID_IWineD3DBaseTexture, (void **)&texture)))
+    if (surface->container.type == WINED3D_CONTAINER_TEXTURE)
     {
+        IWineD3DBaseTextureImpl *texture = surface->container.u.texture;
         UINT sub_count = texture->baseTexture.level_count * texture->baseTexture.layer_count;
         UINT i;
 
@@ -1593,7 +1568,7 @@ void surface_prepare_texture(IWineD3DSurfaceImpl *surface, const struct wined3d_
             surface_prepare_texture_internal(s, gl_info, srgb);
         }
 
-        IWineD3DBaseTexture_Release((IWineD3DBaseTexture *)texture);
+        return;
     }
 
     surface_prepare_texture_internal(surface, gl_info, srgb);
@@ -1632,9 +1607,8 @@ static void surface_prepare_system_memory(IWineD3DSurfaceImpl *This)
 
         GL_EXTCALL(glGenBuffersARB(1, &This->pbo));
         error = glGetError();
-        if(This->pbo == 0 || error != GL_NO_ERROR) {
+        if (!This->pbo || error != GL_NO_ERROR)
             ERR("Failed to bind the PBO with error %s (%#x)\n", debug_glerror(error), error);
-        }
 
         TRACE("Attaching pbo=%#x to (%p)\n", This->pbo, This);
 
@@ -1710,9 +1684,9 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LockRect(IWineD3DSurface *iface, WINED
         goto lock_end;
     }
 
-    /* IWineD3DSurface_LoadLocation() does not check if the rectangle specifies
+    /* surface_load_location() does not check if the rectangle specifies
      * the full surface. Most callers don't need that, so do it here. */
-    if (pRect && pRect->top == 0 && pRect->left == 0
+    if (pRect && !pRect->top && !pRect->left
             && pRect->right == This->currentDesc.Width
             && pRect->bottom == This->currentDesc.Height)
     {
@@ -1720,9 +1694,9 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LockRect(IWineD3DSurface *iface, WINED
     }
 
     if (!(wined3d_settings.rendertargetlock_mode == RTL_DISABLE
-            && ((This->Flags & SFLAG_SWAPCHAIN) || This == device->render_targets[0])))
+            && ((This->container.type == WINED3D_CONTAINER_SWAPCHAIN) || This == device->render_targets[0])))
     {
-        IWineD3DSurface_LoadLocation(iface, SFLAG_INSYSMEM, pass_rect);
+        surface_load_location(This, SFLAG_INSYSMEM, pass_rect);
     }
 
 lock_end:
@@ -1756,20 +1730,18 @@ lock_end:
 
     if (Flags & (WINED3DLOCK_NO_DIRTY_UPDATE | WINED3DLOCK_READONLY)) {
         /* Don't dirtify */
-    } else {
-        IWineD3DBaseTexture *pBaseTexture;
-        /**
-         * Dirtify on lock
-         * as seen in msdn docs
-         */
+    }
+    else
+    {
         surface_add_dirty_rect(This, pRect);
 
-        /** Dirtify Container if needed */
-        if (SUCCEEDED(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DBaseTexture, (void **)&pBaseTexture))) {
-            TRACE("Making container dirty\n");
-            IWineD3DBaseTexture_SetDirty(pBaseTexture, TRUE);
-            IWineD3DBaseTexture_Release(pBaseTexture);
-        } else {
+        if (This->container.type == WINED3D_CONTAINER_TEXTURE)
+        {
+            TRACE("Making container dirty.\n");
+            IWineD3DBaseTexture_SetDirty((IWineD3DBaseTexture *)This->container.u.texture, TRUE);
+        }
+        else
+        {
             TRACE("Surface is standalone, no need to dirty the container\n");
         }
     }
@@ -1912,7 +1884,8 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_UnlockRect(IWineD3DSurface *iface) {
         goto unlock_end;
     }
 
-    if ((This->Flags & SFLAG_SWAPCHAIN) || (device->render_targets && This == device->render_targets[0]))
+    if (This->container.type == WINED3D_CONTAINER_SWAPCHAIN
+            || (device->render_targets && This == device->render_targets[0]))
     {
         if(wined3d_settings.rendertargetlock_mode == RTL_DISABLE) {
             static BOOL warned = FALSE;
@@ -1923,10 +1896,10 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_UnlockRect(IWineD3DSurface *iface) {
             goto unlock_end;
         }
 
-        if(This->dirtyRect.left   == 0 &&
-           This->dirtyRect.top    == 0 &&
-           This->dirtyRect.right  == This->currentDesc.Width &&
-           This->dirtyRect.bottom == This->currentDesc.Height) {
+        if (!This->dirtyRect.left && !This->dirtyRect.top
+                && This->dirtyRect.right == This->currentDesc.Width
+                && This->dirtyRect.bottom == This->currentDesc.Height)
+        {
             fullsurface = TRUE;
         } else {
             /* TODO: Proper partial rectangle tracking */
@@ -1936,11 +1909,11 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_UnlockRect(IWineD3DSurface *iface) {
 
         switch(wined3d_settings.rendertargetlock_mode) {
             case RTL_READTEX:
-                IWineD3DSurface_LoadLocation(iface, SFLAG_INTEXTURE, NULL /* partial texture loading not supported yet */);
+                surface_load_location(This, SFLAG_INTEXTURE, NULL /* partial texture loading not supported yet */);
                 /* drop through */
 
             case RTL_READDRAW:
-                IWineD3DSurface_LoadLocation(iface, SFLAG_INDRAWABLE, fullsurface ? NULL : &This->dirtyRect);
+                surface_load_location(This, SFLAG_INDRAWABLE, fullsurface ? NULL : &This->dirtyRect);
                 break;
         }
 
@@ -1965,15 +1938,15 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_UnlockRect(IWineD3DSurface *iface) {
         FIXME("Depth Stencil buffer locking is not implemented\n");
     } else {
         /* The rest should be a normal texture */
-        IWineD3DBaseTextureImpl *impl;
         /* Check if the texture is bound, if yes dirtify the sampler to force a re-upload of the texture
          * Can't load the texture here because PreLoad may destroy and recreate the gl texture, so sampler
          * states need resetting
          */
-        if(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DBaseTexture, (void **)&impl) == WINED3D_OK) {
-            if (impl->baseTexture.bindCount)
-                IWineD3DDeviceImpl_MarkStateDirty(device, STATE_SAMPLER(impl->baseTexture.sampler));
-            IWineD3DBaseTexture_Release((IWineD3DBaseTexture *) impl);
+        if (This->container.type == WINED3D_CONTAINER_TEXTURE)
+        {
+            IWineD3DBaseTextureImpl *texture = This->container.u.texture;
+            if (texture->baseTexture.bindCount)
+                IWineD3DDeviceImpl_MarkStateDirty(device, STATE_SAMPLER(texture->baseTexture.sampler));
         }
     }
 
@@ -2013,8 +1986,8 @@ static void surface_release_client_storage(IWineD3DSurfaceImpl *surface)
     LEAVE_GL();
     context_release(context);
 
-    IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INSRGBTEX, FALSE);
-    IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INTEXTURE, FALSE);
+    surface_modify_location(surface, SFLAG_INSRGBTEX, FALSE);
+    surface_modify_location(surface, SFLAG_INTEXTURE, FALSE);
     surface_force_reload(surface);
 }
 
@@ -2043,9 +2016,11 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_GetDC(IWineD3DSurface *iface, HDC *pHD
     memset(&lock, 0, sizeof(lock)); /* To be sure */
 
     /* Create a DIB section if there isn't a hdc yet */
-    if(!This->hDC) {
-        if(This->Flags & SFLAG_CLIENT) {
-            IWineD3DSurface_LoadLocation(iface, SFLAG_INSYSMEM, NULL);
+    if (!This->hDC)
+    {
+        if (This->Flags & SFLAG_CLIENT)
+        {
+            surface_load_location(This, SFLAG_INSYSMEM, NULL);
             surface_release_client_storage(This);
         }
         hr = IWineD3DBaseSurfaceImpl_CreateDIBSection(iface);
@@ -2073,8 +2048,8 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_GetDC(IWineD3DSurface *iface, HDC *pHD
         return hr;
     }
 
-    if (This->resource.format_desc->format == WINED3DFMT_P8_UINT
-            || This->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM)
+    if (This->resource.format->id == WINED3DFMT_P8_UINT
+            || This->resource.format->id == WINED3DFMT_P8_UINT_A8_UNORM)
     {
         /* GetDC on palettized formats is unsupported in D3D9, and the method is missing in
             D3D8, so this should only be used for DX <=7 surfaces (with non-device palettes) */
@@ -2141,30 +2116,37 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_ReleaseDC(IWineD3DSurface *iface, HDC
    IWineD3DSurface Internal (No mapping to directx api) parts follow
    ****************************************************** */
 
-HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *This, BOOL need_alpha_ck, BOOL use_texturing, struct wined3d_format_desc *desc, CONVERT_TYPES *convert)
+HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *This, BOOL need_alpha_ck,
+        BOOL use_texturing, struct wined3d_format *format, CONVERT_TYPES *convert)
 {
     BOOL colorkey_active = need_alpha_ck && (This->CKeyFlags & WINEDDSD_CKSRCBLT);
     IWineD3DDeviceImpl *device = This->resource.device;
+    const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
     BOOL blit_supported = FALSE;
-    RECT rect = {0, 0, This->pow2Width, This->pow2Height};
 
     /* Copy the default values from the surface. Below we might perform fixups */
     /* TODO: get rid of color keying desc fixups by using e.g. a table. */
-    *desc = *This->resource.format_desc;
+    *format = *This->resource.format;
     *convert = NO_CONVERSION;
 
     /* Ok, now look if we have to do any conversion */
-    switch(This->resource.format_desc->format)
+    switch (This->resource.format->id)
     {
         case WINED3DFMT_P8_UINT:
-            /* ****************
-                Paletted Texture
-                **************** */
-
+            /* Below the call to blit_supported is disabled for Wine 1.2
+             * because the function isn't operating correctly yet. At the
+             * moment 8-bit blits are handled in software and if certain GL
+             * extensions are around, surface conversion is performed at
+             * upload time. The blit_supported call recognizes it as a
+             * destination fixup. This type of upload 'fixup' and 8-bit to
+             * 8-bit blits need to be handled by the blit_shader.
+             * TODO: get rid of this #if 0. */
+#if 0
             blit_supported = device->blitter->blit_supported(&device->adapter->gl_info, BLIT_OP_BLIT,
-                                                             &rect, This->resource.usage, This->resource.pool,
-                                                             This->resource.format_desc, &rect, This->resource.usage,
-                                                             This->resource.pool, This->resource.format_desc);
+                    &rect, This->resource.usage, This->resource.pool, This->resource.format,
+                    &rect, This->resource.usage, This->resource.pool, This->resource.format);
+#endif
+            blit_supported = gl_info->supported[EXT_PALETTED_TEXTURE] || gl_info->supported[ARB_FRAGMENT_PROGRAM];
 
             /* Use conversion when the blit_shader backend supports it. It only supports this in case of
              * texturing. Further also use conversion in case of color keying.
@@ -2175,15 +2157,14 @@ HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *This, BOOL need_alpha_ck, BOOL use_
             if (!((blit_supported && device->render_targets && This == device->render_targets[0]))
                     || colorkey_active || !use_texturing)
             {
-                desc->glFormat = GL_RGBA;
-                desc->glInternal = GL_RGBA;
-                desc->glType = GL_UNSIGNED_BYTE;
-                desc->conv_byte_count = 4;
-                if(colorkey_active) {
+                format->glFormat = GL_RGBA;
+                format->glInternal = GL_RGBA;
+                format->glType = GL_UNSIGNED_BYTE;
+                format->conv_byte_count = 4;
+                if (colorkey_active)
                     *convert = CONVERT_PALETTED_CK;
-                } else {
+                else
                     *convert = CONVERT_PALETTED;
-                }
             }
             break;
 
@@ -2199,42 +2180,46 @@ HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *This, BOOL need_alpha_ck, BOOL use_
             break;
 
         case WINED3DFMT_B5G6R5_UNORM:
-            if (colorkey_active) {
+            if (colorkey_active)
+            {
                 *convert = CONVERT_CK_565;
-                desc->glFormat = GL_RGBA;
-                desc->glInternal = GL_RGB5_A1;
-                desc->glType = GL_UNSIGNED_SHORT_5_5_5_1;
-                desc->conv_byte_count = 2;
+                format->glFormat = GL_RGBA;
+                format->glInternal = GL_RGB5_A1;
+                format->glType = GL_UNSIGNED_SHORT_5_5_5_1;
+                format->conv_byte_count = 2;
             }
             break;
 
         case WINED3DFMT_B5G5R5X1_UNORM:
-            if (colorkey_active) {
+            if (colorkey_active)
+            {
                 *convert = CONVERT_CK_5551;
-                desc->glFormat = GL_BGRA;
-                desc->glInternal = GL_RGB5_A1;
-                desc->glType = GL_UNSIGNED_SHORT_1_5_5_5_REV;
-                desc->conv_byte_count = 2;
+                format->glFormat = GL_BGRA;
+                format->glInternal = GL_RGB5_A1;
+                format->glType = GL_UNSIGNED_SHORT_1_5_5_5_REV;
+                format->conv_byte_count = 2;
             }
             break;
 
         case WINED3DFMT_B8G8R8_UNORM:
-            if (colorkey_active) {
+            if (colorkey_active)
+            {
                 *convert = CONVERT_CK_RGB24;
-                desc->glFormat = GL_RGBA;
-                desc->glInternal = GL_RGBA8;
-                desc->glType = GL_UNSIGNED_INT_8_8_8_8;
-                desc->conv_byte_count = 4;
+                format->glFormat = GL_RGBA;
+                format->glInternal = GL_RGBA8;
+                format->glType = GL_UNSIGNED_INT_8_8_8_8;
+                format->conv_byte_count = 4;
             }
             break;
 
         case WINED3DFMT_B8G8R8X8_UNORM:
-            if (colorkey_active) {
+            if (colorkey_active)
+            {
                 *convert = CONVERT_RGB32_888;
-                desc->glFormat = GL_RGBA;
-                desc->glInternal = GL_RGBA8;
-                desc->glType = GL_UNSIGNED_INT_8_8_8_8;
-                desc->conv_byte_count = 4;
+                format->glFormat = GL_RGBA;
+                format->glInternal = GL_RGBA8;
+                format->glType = GL_UNSIGNED_INT_8_8_8_8;
+                format->conv_byte_count = 4;
             }
             break;
 
@@ -2341,14 +2326,9 @@ static HRESULT d3dfmt_convert_surface(const BYTE *src, BYTE *dst, UINT pitch, UI
         case CONVERT_PALETTED:
         case CONVERT_PALETTED_CK:
         {
-            IWineD3DPaletteImpl* pal = This->palette;
             BYTE table[256][4];
             unsigned int x, y;
 
-            if( pal == NULL) {
-                /* TODO: If we are a sublevel, try to get the palette from level 0 */
-            }
-
             d3dfmt_p8_init_palette(This, table, (convert == CONVERT_PALETTED_CK));
 
             for (y = 0; y < height; y++)
@@ -2483,8 +2463,8 @@ BOOL palette9_changed(IWineD3DSurfaceImpl *This)
 {
     IWineD3DDeviceImpl *device = This->resource.device;
 
-    if (This->palette || (This->resource.format_desc->format != WINED3DFMT_P8_UINT
-            && This->resource.format_desc->format != WINED3DFMT_P8_UINT_A8_UNORM))
+    if (This->palette || (This->resource.format->id != WINED3DFMT_P8_UINT
+            && This->resource.format->id != WINED3DFMT_P8_UINT_A8_UNORM))
     {
         /* If a ddraw-style palette is attached assume no d3d9 palette change.
          * Also the palette isn't interesting if the surface format isn't P8 or A8P8
@@ -2509,6 +2489,8 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadTexture(IWineD3DSurface *iface, BO
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
     DWORD flag = srgb_mode ? SFLAG_INSRGBTEX : SFLAG_INTEXTURE;
 
+    TRACE("iface %p, srgb %#x.\n", iface, srgb_mode);
+
     if (!(This->Flags & flag)) {
         TRACE("Reloading because surface is dirty\n");
     } else if(/* Reload: gl texture has ck, now no ckey is set OR */
@@ -2524,10 +2506,10 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadTexture(IWineD3DSurface *iface, BO
          * the surface. Make sure we have it
          */
 
-        IWineD3DSurface_LoadLocation(iface, SFLAG_INSYSMEM, NULL);
+        surface_load_location(This, SFLAG_INSYSMEM, NULL);
         /* Make sure the texture is reloaded because of the color key change, this kills performance though :( */
         /* TODO: This is not necessarily needed with hw palettized texture support */
-        IWineD3DSurface_ModifyLocation(iface, SFLAG_INSYSMEM, TRUE);
+        surface_modify_location(This, SFLAG_INSYSMEM, TRUE);
     } else {
         TRACE("surface is already in texture\n");
         return WINED3D_OK;
@@ -2544,49 +2526,29 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadTexture(IWineD3DSurface *iface, BO
         return WINED3DERR_INVALIDCALL;
     }
 
-    IWineD3DSurface_LoadLocation(iface, flag, NULL /* no partial locking for textures yet */);
-
-#if 0
-    {
-        static unsigned int gen = 0;
-        char buffer[4096];
-        ++gen;
-        if ((gen % 10) == 0) {
-            snprintf(buffer, sizeof(buffer), "/tmp/surface%p_type%u_level%u_%u.ppm",
-                    This, This->texture_target, This->texture_level, gen);
-            IWineD3DSurfaceImpl_SaveSnapshot(iface, buffer);
-        }
-        /*
-         * debugging crash code
-         if (gen == 250) {
-         void** test = NULL;
-         *test = 0;
-         }
-         */
-    }
-#endif
+    surface_load_location(This, flag, NULL /* no partial locking for textures yet */);
 
     if (!(This->Flags & SFLAG_DONOTFREE)) {
         HeapFree(GetProcessHeap(), 0, This->resource.heapMemory);
         This->resource.allocatedMemory = NULL;
         This->resource.heapMemory = NULL;
-        IWineD3DSurface_ModifyLocation(iface, SFLAG_INSYSMEM, FALSE);
+        surface_modify_location(This, SFLAG_INSYSMEM, FALSE);
     }
 
     return WINED3D_OK;
 }
 
 /* Context activation is done by the caller. */
-static void WINAPI IWineD3DSurfaceImpl_BindTexture(IWineD3DSurface *iface, BOOL srgb) {
-    /* TODO: check for locks */
+static void WINAPI IWineD3DSurfaceImpl_BindTexture(IWineD3DSurface *iface, BOOL srgb)
+{
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-    IWineD3DBaseTexture *baseTexture = NULL;
 
-    TRACE("(%p)Checking to see if the container is a base texture\n", This);
-    if (IWineD3DSurface_GetContainer(iface, &IID_IWineD3DBaseTexture, (void **)&baseTexture) == WINED3D_OK) {
-        TRACE("Passing to container\n");
-        IWineD3DBaseTexture_BindTexture(baseTexture, srgb);
-        IWineD3DBaseTexture_Release(baseTexture);
+    TRACE("iface %p, srgb %#x.\n", iface, srgb);
+
+    if (This->container.type == WINED3D_CONTAINER_TEXTURE)
+    {
+        TRACE("Passing to container.\n");
+        IWineD3DBaseTexture_BindTexture((IWineD3DBaseTexture *)This->container.u.texture, srgb);
     }
     else
     {
@@ -2631,148 +2593,8 @@ static void WINAPI IWineD3DSurfaceImpl_BindTexture(IWineD3DSurface *iface, BOOL
     }
 }
 
-#include <errno.h>
-#include <stdio.h>
-static HRESULT WINAPI IWineD3DSurfaceImpl_SaveSnapshot(IWineD3DSurface *iface, const char* filename)
+static HRESULT WINAPI IWineD3DSurfaceImpl_SetFormat(IWineD3DSurface *iface, enum wined3d_format_id format)
 {
-    FILE* f = NULL;
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-    char *allocatedMemory;
-    const char *textureRow;
-    IWineD3DSwapChain *swapChain = NULL;
-    int width, height, i, y;
-    GLuint tmpTexture = 0;
-    DWORD color;
-    /*FIXME:
-    Textures may not be stored in ->allocatedgMemory and a GlTexture
-    so we should lock the surface before saving a snapshot, or at least check that
-    */
-    /* TODO: Compressed texture images can be obtained from the GL in uncompressed form
-    by calling GetTexImage and in compressed form by calling
-    GetCompressedTexImageARB.  Queried compressed images can be saved and
-    later reused by calling CompressedTexImage[123]DARB.  Pre-compressed
-    texture images do not need to be processed by the GL and should
-    significantly improve texture loading performance relative to uncompressed
-    images. */
-
-/* Setup the width and height to be the internal texture width and height. */
-    width  = This->pow2Width;
-    height = This->pow2Height;
-/* check to see if we're a 'virtual' texture, e.g. we're not a pbuffer of texture, we're a back buffer*/
-    IWineD3DSurface_GetContainer(iface, &IID_IWineD3DSwapChain, (void **)&swapChain);
-
-    if (This->Flags & SFLAG_INDRAWABLE && !(This->Flags & SFLAG_INTEXTURE)) {
-        /* if were not a real texture then read the back buffer into a real texture */
-        /* we don't want to interfere with the back buffer so read the data into a temporary
-         * texture and then save the data out of the temporary texture
-         */
-        GLint prevRead;
-        ENTER_GL();
-        TRACE("(%p) Reading render target into texture\n", This);
-
-        glGenTextures(1, &tmpTexture);
-        glBindTexture(GL_TEXTURE_2D, tmpTexture);
-
-        glTexImage2D(GL_TEXTURE_2D,
-                        0,
-                        GL_RGBA,
-                        width,
-                        height,
-                        0/*border*/,
-                        GL_RGBA,
-                        GL_UNSIGNED_INT_8_8_8_8_REV,
-                        NULL);
-
-        glGetIntegerv(GL_READ_BUFFER, &prevRead);
-        checkGLcall("glGetIntegerv");
-        glReadBuffer(swapChain ? GL_BACK : This->resource.device->offscreenBuffer);
-        checkGLcall("glReadBuffer");
-        glCopyTexImage2D(GL_TEXTURE_2D,
-                            0,
-                            GL_RGBA,
-                            0,
-                            0,
-                            width,
-                            height,
-                            0);
-
-        checkGLcall("glCopyTexImage2D");
-        glReadBuffer(prevRead);
-        LEAVE_GL();
-
-    } else { /* bind the real texture, and make sure it up to date */
-        surface_internal_preload(This, SRGB_RGB);
-        surface_bind_and_dirtify(This, FALSE);
-    }
-    allocatedMemory = HeapAlloc(GetProcessHeap(), 0, width  * height * 4);
-    ENTER_GL();
-    FIXME("Saving texture level %d width %d height %d\n", This->texture_level, width, height);
-    glGetTexImage(GL_TEXTURE_2D, This->texture_level, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8_REV, allocatedMemory);
-    checkGLcall("glGetTexImage");
-    if (tmpTexture) {
-        glBindTexture(GL_TEXTURE_2D, 0);
-        glDeleteTextures(1, &tmpTexture);
-    }
-    LEAVE_GL();
-
-    f = fopen(filename, "w+");
-    if (NULL == f) {
-        ERR("opening of %s failed with: %s\n", filename, strerror(errno));
-        return WINED3DERR_INVALIDCALL;
-    }
-/* Save the data out to a TGA file because 1: it's an easy raw format, 2: it supports an alpha channel */
-    TRACE("(%p) opened %s with format %s\n", This, filename, debug_d3dformat(This->resource.format_desc->format));
-/* TGA header */
-    fputc(0,f);
-    fputc(0,f);
-    fputc(2,f);
-    fputc(0,f);
-    fputc(0,f);
-    fputc(0,f);
-    fputc(0,f);
-    fputc(0,f);
-    fputc(0,f);
-    fputc(0,f);
-    fputc(0,f);
-    fputc(0,f);
-/* short width*/
-    fwrite(&width,2,1,f);
-/* short height */
-    fwrite(&height,2,1,f);
-/* format rgba */
-    fputc(0x20,f);
-    fputc(0x28,f);
-/* raw data */
-    /* if the data is upside down if we've fetched it from a back buffer, so it needs flipping again to make it the correct way up */
-    if(swapChain)
-        textureRow = allocatedMemory + (width * (height - 1) *4);
-    else
-        textureRow = allocatedMemory;
-    for (y = 0 ; y < height; y++) {
-        for (i = 0; i < width;  i++) {
-            color = *((const DWORD*)textureRow);
-            fputc((color >> 16) & 0xFF, f); /* B */
-            fputc((color >>  8) & 0xFF, f); /* G */
-            fputc((color >>  0) & 0xFF, f); /* R */
-            fputc((color >> 24) & 0xFF, f); /* A */
-            textureRow += 4;
-        }
-        /* take two rows of the pointer to the texture memory */
-        if(swapChain)
-            (textureRow-= width << 3);
-
-    }
-    TRACE("Closing file\n");
-    fclose(f);
-
-    if(swapChain) {
-        IWineD3DSwapChain_Release(swapChain);
-    }
-    HeapFree(GetProcessHeap(), 0, allocatedMemory);
-    return WINED3D_OK;
-}
-
-static HRESULT WINAPI IWineD3DSurfaceImpl_SetFormat(IWineD3DSurface *iface, WINED3DFORMAT format) {
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
     HRESULT hr;
 
@@ -2780,8 +2602,8 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_SetFormat(IWineD3DSurface *iface, WINE
     hr = IWineD3DBaseSurfaceImpl_SetFormat(iface, format);
     if(SUCCEEDED(hr)) {
         This->Flags &= ~(SFLAG_ALLOCATED | SFLAG_SRGBALLOCATED);
-        TRACE("(%p) : glFormat %d, glFormatInternal %d, glType %d\n", This, This->resource.format_desc->glFormat,
-                This->resource.format_desc->glInternal, This->resource.format_desc->glType);
+        TRACE("(%p) : glFormat %d, glFormatInternal %d, glType %d\n", This, This->resource.format->glFormat,
+                This->resource.format->glInternal, This->resource.format->glType);
     }
     return hr;
 }
@@ -2819,7 +2641,7 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_SetMem(IWineD3DSurface *iface, void *M
         This->Flags |= SFLAG_USERPTR | SFLAG_INSYSMEM;
 
         /* Now the surface memory is most up do date. Invalidate drawable and texture */
-        IWineD3DSurface_ModifyLocation(iface, SFLAG_INSYSMEM, TRUE);
+        surface_modify_location(This, SFLAG_INSYSMEM, TRUE);
 
         /* For client textures opengl has to be notified */
         if (This->Flags & SFLAG_CLIENT)
@@ -2831,7 +2653,8 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_SetMem(IWineD3DSurface *iface, void *M
         /* LockRect and GetDC will re-create the dib section and allocated memory */
         This->resource.allocatedMemory = NULL;
         /* HeapMemory should be NULL already */
-        if(This->resource.heapMemory != NULL) ERR("User pointer surface has heap memory allocated\n");
+        if (This->resource.heapMemory)
+            ERR("User pointer surface has heap memory allocated.\n");
         This->Flags &= ~SFLAG_USERPTR;
 
         if (This->Flags & SFLAG_CLIENT)
@@ -2920,7 +2743,7 @@ void flip_surface(IWineD3DSurfaceImpl *front, IWineD3DSurfaceImpl *back) {
 static HRESULT WINAPI IWineD3DSurfaceImpl_Flip(IWineD3DSurface *iface, IWineD3DSurface *override, DWORD Flags) {
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
     IWineD3DSwapChainImpl *swapchain = NULL;
-    HRESULT hr;
+
     TRACE("(%p)->(%p,%x)\n", This, override, Flags);
 
     /* Flipping is only supported on RenderTargets and overlays*/
@@ -2948,16 +2771,18 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_Flip(IWineD3DSurface *iface, IWineD3DS
          */
     }
 
-    IWineD3DSurface_GetContainer(iface, &IID_IWineD3DSwapChain, (void **) &swapchain);
-    if(!swapchain) {
+    if (This->container.type != WINED3D_CONTAINER_SWAPCHAIN)
+    {
         ERR("Flipped surface is not on a swapchain\n");
         return WINEDDERR_NOTFLIPPABLE;
     }
+    swapchain = This->container.u.swapchain;
 
     /* Just overwrite the swapchain presentation interval. This is ok because only ddraw apps can call Flip,
      * and only d3d8 and d3d9 apps specify the presentation interval
      */
-    if((Flags & (WINEDDFLIP_NOVSYNC | WINEDDFLIP_INTERVAL2 | WINEDDFLIP_INTERVAL3 | WINEDDFLIP_INTERVAL4)) == 0) {
+    if (!(Flags & (WINEDDFLIP_NOVSYNC | WINEDDFLIP_INTERVAL2 | WINEDDFLIP_INTERVAL3 | WINEDDFLIP_INTERVAL4)))
+    {
         /* Most common case first to avoid wasting time on all the other cases */
         swapchain->presentParms.PresentationInterval = WINED3DPRESENT_INTERVAL_ONE;
     } else if(Flags & WINEDDFLIP_NOVSYNC) {
@@ -2971,10 +2796,8 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_Flip(IWineD3DSurface *iface, IWineD3DS
     }
 
     /* Flipping a OpenGL surface -> Use WineD3DDevice::Present */
-    hr = IWineD3DSwapChain_Present((IWineD3DSwapChain *)swapchain,
+    return IWineD3DSwapChain_Present((IWineD3DSwapChain *)swapchain,
             NULL, NULL, swapchain->win_handle, NULL, 0);
-    IWineD3DSwapChain_Release((IWineD3DSwapChain *) swapchain);
-    return hr;
 }
 
 /* Does a direct frame buffer -> texture copy. Stretching is done
@@ -3086,7 +2909,7 @@ static void fb_copy_to_texture_direct(IWineD3DSurfaceImpl *dst_surface, IWineD3D
     /* The texture is now most up to date - If the surface is a render target and has a drawable, this
      * path is never entered
      */
-    IWineD3DSurface_ModifyLocation((IWineD3DSurface *)dst_surface, SFLAG_INTEXTURE, TRUE);
+    surface_modify_location(dst_surface, SFLAG_INTEXTURE, TRUE);
 }
 
 /* Uses the hardware to stretch and flip the image */
@@ -3194,8 +3017,8 @@ static void fb_copy_to_texture_hwstretch(IWineD3DSurfaceImpl *dst_surface, IWine
             wined3d_gl_min_mip_filter(minMipLookup, Filter, WINED3DTEXF_NONE));
     checkGLcall("glTexParameteri");
 
-    IWineD3DSurface_GetContainer((IWineD3DSurface *)src_surface, &IID_IWineD3DSwapChain, (void **)&src_swapchain);
-    if (src_swapchain) IWineD3DSwapChain_Release((IWineD3DSwapChain *)src_swapchain);
+    if (src_surface->container.type == WINED3D_CONTAINER_SWAPCHAIN)
+        src_swapchain = src_surface->container.u.swapchain;
     if (!src_swapchain || src_surface == src_swapchain->back_buffers[0])
     {
         src = backup ? backup : src_surface->texture_name;
@@ -3368,15 +3191,13 @@ static void fb_copy_to_texture_hwstretch(IWineD3DSurfaceImpl *dst_surface, IWine
     /* The texture is now most up to date - If the surface is a render target and has a drawable, this
      * path is never entered
      */
-    IWineD3DSurface_ModifyLocation((IWineD3DSurface *)dst_surface, SFLAG_INTEXTURE, TRUE);
+    surface_modify_location(dst_surface, SFLAG_INTEXTURE, TRUE);
 }
 
 /* Until the blit_shader is ready, define some prototypes here. */
 static BOOL fbo_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_operation blit_op,
-                               const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool,
-                               const struct wined3d_format_desc *src_format_desc,
-                               const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool,
-                               const struct wined3d_format_desc *dst_format_desc);
+        const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool, const struct wined3d_format *src_format,
+        const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool, const struct wined3d_format *dst_format);
 
 /* Front buffer coordinates are always full screen coordinates, but our GL
  * drawable is limited to the window's client area. The sysmem and texture
@@ -3393,12 +3214,172 @@ void surface_translate_frontbuffer_coords(IWineD3DSurfaceImpl *surface, HWND win
     OffsetRect(rect, offset.x, offset.y);
 }
 
+static BOOL surface_is_full_rect(IWineD3DSurfaceImpl *surface, const RECT *r)
+{
+    if ((r->left && r->right) || abs(r->right - r->left) != surface->currentDesc.Width)
+        return FALSE;
+    if ((r->top && r->bottom) || abs(r->bottom - r->top) != surface->currentDesc.Height)
+        return FALSE;
+    return TRUE;
+}
+
+/* blit between surface locations. onscreen on different swapchains is not supported.
+ * depth / stencil is not supported. */
+static void surface_blt_fbo(IWineD3DDeviceImpl *device, const WINED3DTEXTUREFILTERTYPE filter,
+        IWineD3DSurfaceImpl *src_surface, DWORD src_location, const RECT *src_rect_in,
+        IWineD3DSurfaceImpl *dst_surface, DWORD dst_location, const RECT *dst_rect_in)
+{
+    const struct wined3d_gl_info *gl_info;
+    struct wined3d_context *context;
+    RECT src_rect, dst_rect;
+    GLenum gl_filter;
+
+    TRACE("device %p, filter %s,\n", device, debug_d3dtexturefiltertype(filter));
+    TRACE("src_surface %p, src_location %s, src_rect %s,\n",
+            src_surface, debug_surflocation(src_location), wine_dbgstr_rect(src_rect_in));
+    TRACE("dst_surface %p, dst_location %s, dst_rect %s.\n",
+            dst_surface, debug_surflocation(dst_location), wine_dbgstr_rect(dst_rect_in));
+
+    src_rect = *src_rect_in;
+    dst_rect = *dst_rect_in;
+
+    switch (filter)
+    {
+        case WINED3DTEXF_LINEAR:
+            gl_filter = GL_LINEAR;
+            break;
+
+        default:
+            FIXME("Unsupported filter mode %s (%#x).\n", debug_d3dtexturefiltertype(filter), filter);
+        case WINED3DTEXF_NONE:
+        case WINED3DTEXF_POINT:
+            gl_filter = GL_NEAREST;
+            break;
+    }
+
+    if (src_location == SFLAG_INDRAWABLE && surface_is_offscreen(src_surface))
+        src_location = SFLAG_INTEXTURE;
+    if (dst_location == SFLAG_INDRAWABLE && surface_is_offscreen(dst_surface))
+        dst_location = SFLAG_INTEXTURE;
+
+    /* Make sure the locations are up-to-date. Loading the destination
+     * surface isn't required if the entire surface is overwritten. (And is
+     * in fact harmful if we're being called by surface_load_location() with
+     * the purpose of loading the destination surface.) */
+    surface_load_location(src_surface, src_location, NULL);
+    if (!surface_is_full_rect(dst_surface, &dst_rect))
+        surface_load_location(dst_surface, dst_location, NULL);
+
+    if (src_location == SFLAG_INDRAWABLE) context = context_acquire(device, src_surface);
+    else if (dst_location == SFLAG_INDRAWABLE) context = context_acquire(device, dst_surface);
+    else context = context_acquire(device, NULL);
+
+    if (!context->valid)
+    {
+        context_release(context);
+        WARN("Invalid context, skipping blit.\n");
+        return;
+    }
+
+    gl_info = context->gl_info;
+
+    if (src_location == SFLAG_INDRAWABLE)
+    {
+        GLenum buffer = surface_get_gl_buffer(src_surface);
+
+        TRACE("Source surface %p is onscreen.\n", src_surface);
+
+        if (buffer == GL_FRONT)
+            surface_translate_frontbuffer_coords(src_surface, context->win_handle, &src_rect);
+
+        src_rect.top = src_surface->currentDesc.Height - src_rect.top;
+        src_rect.bottom = src_surface->currentDesc.Height - src_rect.bottom;
+
+        ENTER_GL();
+        context_bind_fbo(context, GL_READ_FRAMEBUFFER, NULL);
+        glReadBuffer(buffer);
+        checkGLcall("glReadBuffer()");
+    }
+    else
+    {
+        TRACE("Source surface %p is offscreen.\n", src_surface);
+        ENTER_GL();
+        context_apply_fbo_state_blit(context, GL_READ_FRAMEBUFFER, src_surface, NULL, src_location);
+        glReadBuffer(GL_COLOR_ATTACHMENT0);
+        checkGLcall("glReadBuffer()");
+    }
+    LEAVE_GL();
+
+    if (dst_location == SFLAG_INDRAWABLE)
+    {
+        GLenum buffer = surface_get_gl_buffer(dst_surface);
+
+        TRACE("Destination surface %p is onscreen.\n", dst_surface);
+
+        if (buffer == GL_FRONT)
+            surface_translate_frontbuffer_coords(dst_surface, context->win_handle, &dst_rect);
+
+        dst_rect.top = dst_surface->currentDesc.Height - dst_rect.top;
+        dst_rect.bottom = dst_surface->currentDesc.Height - dst_rect.bottom;
+
+        ENTER_GL();
+        context_bind_fbo(context, GL_DRAW_FRAMEBUFFER, NULL);
+        context_set_draw_buffer(context, buffer);
+    }
+    else
+    {
+        TRACE("Destination surface %p is offscreen.\n", dst_surface);
+
+        ENTER_GL();
+        context_apply_fbo_state_blit(context, GL_DRAW_FRAMEBUFFER, dst_surface, NULL, dst_location);
+        context_set_draw_buffer(context, GL_COLOR_ATTACHMENT0);
+    }
+
+    glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
+    IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE));
+    IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE1));
+    IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE2));
+    IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE3));
+
+    glDisable(GL_SCISSOR_TEST);
+    IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_SCISSORTESTENABLE));
+
+    gl_info->fbo_ops.glBlitFramebuffer(src_rect.left, src_rect.top, src_rect.right, src_rect.bottom,
+            dst_rect.left, dst_rect.top, dst_rect.right, dst_rect.bottom, GL_COLOR_BUFFER_BIT, gl_filter);
+    checkGLcall("glBlitFramebuffer()");
+
+    LEAVE_GL();
+
+    if (wined3d_settings.strict_draw_ordering) wglFlush(); /* Flush to ensure ordering across contexts. */
+
+    context_release(context);
+}
+
+/* Do not call while under the GL lock. */
+HRESULT surface_color_fill(IWineD3DSurfaceImpl *s, const RECT *rect, const WINED3DCOLORVALUE *color)
+{
+    IWineD3DDeviceImpl *device = s->resource.device;
+    const struct blit_shader *blitter;
+
+    blitter = wined3d_select_blitter(&device->adapter->gl_info, BLIT_OP_COLOR_FILL,
+            NULL, 0, 0, NULL, rect, s->resource.usage, s->resource.pool, s->resource.format);
+    if (!blitter)
+    {
+        FIXME("No blitter is capable of performing the requested color fill operation.\n");
+        return WINED3DERR_INVALIDCALL;
+    }
+
+    return blitter->color_fill(device, s, rect, color);
+}
+
 /* Not called from the VTable */
+/* Do not call while under the GL lock. */
 static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface, const RECT *DestRect,
         IWineD3DSurfaceImpl *src_surface, const RECT *SrcRect, DWORD Flags, const WINEDDBLTFX *DDBltFx,
         WINED3DTEXTUREFILTERTYPE Filter)
 {
     IWineD3DDeviceImpl *device = dst_surface->resource.device;
+    const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
     IWineD3DSwapChainImpl *srcSwapchain = NULL, *dstSwapchain = NULL;
     RECT dst_rect, src_rect;
 
@@ -3412,8 +3393,10 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
         WARN("Destination is in sysmem, rejecting gl blt\n");
         return WINED3DERR_INVALIDCALL;
     }
-    IWineD3DSurface_GetContainer((IWineD3DSurface *)dst_surface, &IID_IWineD3DSwapChain, (void **)&dstSwapchain);
-    if (dstSwapchain) IWineD3DSwapChain_Release((IWineD3DSwapChain *)dstSwapchain);
+
+    if (dst_surface->container.type == WINED3D_CONTAINER_SWAPCHAIN)
+        dstSwapchain = dst_surface->container.u.swapchain;
+
     if (src_surface)
     {
         if (src_surface->resource.pool == WINED3DPOOL_SYSTEMMEM)
@@ -3421,8 +3404,9 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
             WARN("Src is in sysmem, rejecting gl blt\n");
             return WINED3DERR_INVALIDCALL;
         }
-        IWineD3DSurface_GetContainer((IWineD3DSurface *)src_surface, &IID_IWineD3DSwapChain, (void **)&srcSwapchain);
-        if (srcSwapchain) IWineD3DSwapChain_Release((IWineD3DSwapChain *)srcSwapchain);
+
+        if (src_surface->container.type == WINED3D_CONTAINER_SWAPCHAIN)
+            srcSwapchain = src_surface->container.u.swapchain;
     }
 
     /* Early sort out of cases where no render target is used */
@@ -3449,7 +3433,7 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
             && dst_surface == dstSwapchain->front_buffer
             && src_surface == dstSwapchain->back_buffers[0])
     {
-        /* Half-life does a Blt from the back buffer to the front buffer,
+        /* Half-Life does a Blt from the back buffer to the front buffer,
          * Full surface size, no flags... Use present instead
          *
          * This path will only be entered for d3d7 and ddraw apps, because d3d8/9 offer no way to blit TO the front buffer
@@ -3507,7 +3491,8 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
             TRACE("Yes\n");
 
             /* These flags are unimportant for the flag check, remove them */
-            if((Flags & ~(WINEDDBLT_DONOTWAIT | WINEDDBLT_WAIT)) == 0) {
+            if (!(Flags & ~(WINEDDBLT_DONOTWAIT | WINEDDBLT_WAIT)))
+            {
                 WINED3DSWAPEFFECT orig_swap = dstSwapchain->presentParms.SwapEffect;
 
                 /* The idea behind this is that a glReadPixels and a glDrawPixels call
@@ -3566,8 +3551,8 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
         BOOL stretchx;
 
         /* P8 read back is not implemented */
-        if (src_surface->resource.format_desc->format == WINED3DFMT_P8_UINT
-                || dst_surface->resource.format_desc->format == WINED3DFMT_P8_UINT)
+        if (src_surface->resource.format->id == WINED3DFMT_P8_UINT
+                || dst_surface->resource.format->id == WINED3DFMT_P8_UINT)
         {
             TRACE("P8 read back not supported by frame buffer to texture blit\n");
             return WINED3DERR_INVALIDCALL;
@@ -3600,11 +3585,14 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
          * FBO support, so it doesn't really make sense to try and make it work with different offscreen rendering
          * backends.
          */
-        if (fbo_blit_supported(&device->adapter->gl_info, BLIT_OP_BLIT,
-                &src_rect, src_surface->resource.usage, src_surface->resource.pool, src_surface->resource.format_desc,
-                &dst_rect, dst_surface->resource.usage, dst_surface->resource.pool, dst_surface->resource.format_desc))
+        if (fbo_blit_supported(gl_info, BLIT_OP_BLIT,
+                &src_rect, src_surface->resource.usage, src_surface->resource.pool, src_surface->resource.format,
+                &dst_rect, dst_surface->resource.usage, dst_surface->resource.pool, dst_surface->resource.format))
         {
-            stretch_rect_fbo(device, src_surface, &src_rect, dst_surface, &dst_rect, Filter);
+            surface_blt_fbo(device, Filter,
+                    src_surface, SFLAG_INDRAWABLE, &src_rect,
+                    dst_surface, SFLAG_INDRAWABLE, &dst_rect);
+            surface_modify_location(dst_surface, SFLAG_INDRAWABLE, TRUE);
         }
         else if (!stretchx || dst_rect.right - dst_rect.left > src_surface->currentDesc.Width
                 || dst_rect.bottom - dst_rect.top > src_surface->currentDesc.Height)
@@ -3639,25 +3627,28 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
         TRACE("Blt from surface %p to rendertarget %p\n", src_surface, dst_surface);
 
         if (!(Flags & (WINEDDBLT_KEYSRC | WINEDDBLT_KEYSRCOVERRIDE))
-                && fbo_blit_supported(&device->adapter->gl_info, BLIT_OP_BLIT,
+                && fbo_blit_supported(gl_info, BLIT_OP_BLIT,
                         &src_rect, src_surface->resource.usage, src_surface->resource.pool,
-                        src_surface->resource.format_desc,
+                        src_surface->resource.format,
                         &dst_rect, dst_surface->resource.usage, dst_surface->resource.pool,
-                        dst_surface->resource.format_desc))
+                        dst_surface->resource.format))
         {
-            TRACE("Using stretch_rect_fbo\n");
+            TRACE("Using surface_blt_fbo.\n");
             /* The source is always a texture, but never the currently active render target, and the texture
              * contents are never upside down. */
-            stretch_rect_fbo(device, src_surface, &src_rect, dst_surface, &dst_rect, Filter);
+            surface_blt_fbo(device, Filter,
+                    src_surface, SFLAG_INDRAWABLE, &src_rect,
+                    dst_surface, SFLAG_INDRAWABLE, &dst_rect);
+            surface_modify_location(dst_surface, SFLAG_INDRAWABLE, TRUE);
             return WINED3D_OK;
         }
 
         if (!(Flags & (WINEDDBLT_KEYSRC | WINEDDBLT_KEYSRCOVERRIDE))
-                && arbfp_blit.blit_supported(&device->adapter->gl_info, BLIT_OP_BLIT,
+                && arbfp_blit.blit_supported(gl_info, BLIT_OP_BLIT,
                         &src_rect, src_surface->resource.usage, src_surface->resource.pool,
-                        src_surface->resource.format_desc,
+                        src_surface->resource.format,
                         &dst_rect, dst_surface->resource.usage, dst_surface->resource.pool,
-                        dst_surface->resource.format_desc))
+                        dst_surface->resource.format))
         {
             return arbfp_blit_surface(device, src_surface, &src_rect, dst_surface, &dst_rect, BLIT_OP_BLIT, Filter);
         }
@@ -3690,9 +3681,9 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
         if (dstSwapchain && dst_surface == dstSwapchain->front_buffer)
             surface_translate_frontbuffer_coords(dst_surface, context->win_handle, &dst_rect);
 
-        if (!device->blitter->blit_supported(&device->adapter->gl_info, BLIT_OP_BLIT,
-                &src_rect, src_surface->resource.usage, src_surface->resource.pool, src_surface->resource.format_desc,
-                &dst_rect, dst_surface->resource.usage, dst_surface->resource.pool, dst_surface->resource.format_desc))
+        if (!device->blitter->blit_supported(gl_info, BLIT_OP_BLIT,
+                &src_rect, src_surface->resource.usage, src_surface->resource.pool, src_surface->resource.format,
+                &dst_rect, dst_surface->resource.usage, dst_surface->resource.pool, dst_surface->resource.format))
         {
             FIXME("Unsupported blit operation falling back to software\n");
             return WINED3DERR_INVALIDCALL;
@@ -3749,40 +3740,24 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
         /* The surface is now in the drawable. On onscreen surfaces or without fbos the texture
          * is outdated now
          */
-        IWineD3DSurface_ModifyLocation((IWineD3DSurface *)dst_surface, SFLAG_INDRAWABLE, TRUE);
+        surface_modify_location(dst_surface, SFLAG_INDRAWABLE, TRUE);
 
         return WINED3D_OK;
-    } else {
+    }
+    else
+    {
         /* Source-Less Blit to render target */
-        if (Flags & WINEDDBLT_COLORFILL) {
-            DWORD color;
+        if (Flags & WINEDDBLT_COLORFILL)
+        {
+            WINED3DCOLORVALUE color;
 
             TRACE("Colorfill\n");
 
-            /* The color as given in the Blt function is in the format of the frame-buffer...
-             * 'clear' expect it in ARGB format => we need to do some conversion :-)
-             */
-            if (!surface_convert_color_to_argb(dst_surface, DDBltFx->u5.dwFillColor, &color))
-            {
-                /* The color conversion function already prints an error, so need to do it here */
+            /* The color as given in the Blt function is in the surface format. */
+            if (!surface_convert_color_to_float(dst_surface, DDBltFx->u5.dwFillColor, &color))
                 return WINED3DERR_INVALIDCALL;
-            }
 
-            if (ffp_blit.blit_supported(&device->adapter->gl_info, BLIT_OP_COLOR_FILL,
-                    NULL, 0, 0, NULL,
-                    &dst_rect, dst_surface->resource.usage, dst_surface->resource.pool,
-                    dst_surface->resource.format_desc))
-            {
-                return ffp_blit.color_fill(device, dst_surface, &dst_rect, color);
-            }
-            else if (cpu_blit.blit_supported(&device->adapter->gl_info, BLIT_OP_COLOR_FILL,
-                    NULL, 0, 0, NULL,
-                    &dst_rect, dst_surface->resource.usage, dst_surface->resource.pool,
-                    dst_surface->resource.format_desc))
-            {
-                return cpu_blit.color_fill(device, dst_surface, &dst_rect, color);
-            }
-            return WINED3DERR_INVALIDCALL;
+            return surface_color_fill(dst_surface, &dst_rect, &color);
         }
     }
 
@@ -3792,19 +3767,20 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *dst_surface,
 }
 
 static HRESULT IWineD3DSurfaceImpl_BltZ(IWineD3DSurfaceImpl *This, const RECT *DestRect,
-        IWineD3DSurface *SrcSurface, const RECT *SrcRect, DWORD Flags, const WINEDDBLTFX *DDBltFx)
+        IWineD3DSurface *src_surface, const RECT *src_rect, DWORD Flags, const WINEDDBLTFX *DDBltFx)
 {
     IWineD3DDeviceImpl *device = This->resource.device;
     float depth;
 
-    if (Flags & WINEDDBLT_DEPTHFILL) {
-        switch(This->resource.format_desc->format)
+    if (Flags & WINEDDBLT_DEPTHFILL)
+    {
+        switch (This->resource.format->id)
         {
             case WINED3DFMT_D16_UNORM:
                 depth = (float) DDBltFx->u5.dwFillDepth / (float) 0x0000ffff;
                 break;
             case WINED3DFMT_S1_UINT_D15_UNORM:
-                depth = (float) DDBltFx->u5.dwFillDepth / (float) 0x0000fffe;
+                depth = (float) DDBltFx->u5.dwFillDepth / (float) 0x00007fff;
                 break;
             case WINED3DFMT_D24_UNORM_S8_UINT:
             case WINED3DFMT_X8D24_UNORM:
@@ -3815,10 +3791,10 @@ static HRESULT IWineD3DSurfaceImpl_BltZ(IWineD3DSurfaceImpl *This, const RECT *D
                 break;
             default:
                 depth = 0.0f;
-                ERR("Unexpected format for depth fill: %s\n", debug_d3dformat(This->resource.format_desc->format));
+                ERR("Unexpected format for depth fill: %s.\n", debug_d3dformat(This->resource.format->id));
         }
 
-        return IWineD3DDevice_Clear((IWineD3DDevice *)device, DestRect ? 1 : 0, (const WINED3DRECT *)DestRect,
+        return IWineD3DDevice_Clear((IWineD3DDevice *)device, DestRect ? 1 : 0, DestRect,
                 WINED3DCLEAR_ZBUFFER, 0x00000000, depth, 0x00000000);
     }
 
@@ -3826,16 +3802,20 @@ static HRESULT IWineD3DSurfaceImpl_BltZ(IWineD3DSurfaceImpl *This, const RECT *D
     return WINED3DERR_INVALIDCALL;
 }
 
-static HRESULT WINAPI IWineD3DSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *DestRect, IWineD3DSurface *SrcSurface,
-        const RECT *SrcRect, DWORD Flags, const WINEDDBLTFX *DDBltFx, WINED3DTEXTUREFILTERTYPE Filter) {
+static HRESULT WINAPI IWineD3DSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *DestRect,
+        IWineD3DSurface *src_surface, const RECT *SrcRect, DWORD Flags,
+        const WINEDDBLTFX *DDBltFx, WINED3DTEXTUREFILTERTYPE Filter)
+{
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-    IWineD3DSurfaceImpl *Src = (IWineD3DSurfaceImpl *) SrcSurface;
+    IWineD3DSurfaceImpl *src = (IWineD3DSurfaceImpl *)src_surface;
     IWineD3DDeviceImpl *device = This->resource.device;
 
-    TRACE("(%p)->(%p,%p,%p,%x,%p)\n", This, DestRect, SrcSurface, SrcRect, Flags, DDBltFx);
-    TRACE("(%p): Usage is %s\n", This, debug_d3dusage(This->resource.usage));
+    TRACE("iface %p, dst_rect %s, src_surface %p, src_rect %s, flags %#x, fx %p, filter %s.\n",
+            iface, wine_dbgstr_rect(DestRect), src_surface, wine_dbgstr_rect(SrcRect),
+            Flags, DDBltFx, debug_d3dtexturefiltertype(Filter));
+    TRACE("Usage is %s.\n", debug_d3dusage(This->resource.usage));
 
-    if ( (This->Flags & SFLAG_LOCKED) || ((Src != NULL) && (Src->Flags & SFLAG_LOCKED)))
+    if ((This->Flags & SFLAG_LOCKED) || (src && (src->Flags & SFLAG_LOCKED)))
     {
         WARN(" Surface is busy, returning DDERR_SURFACEBUSY\n");
         return WINEDDERR_SURFACEBUSY;
@@ -3844,13 +3824,15 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT
     /* Accessing the depth stencil is supposed to fail between a BeginScene and EndScene pair,
      * except depth blits, which seem to work
      */
-    if (This == device->depth_stencil || (Src && Src == device->depth_stencil))
+    if (This == device->depth_stencil || (src && src == device->depth_stencil))
     {
         if (device->inScene && !(Flags & WINEDDBLT_DEPTHFILL))
         {
             TRACE("Attempt to access the depth stencil surface in a BeginScene / EndScene pair, returning WINED3DERR_INVALIDCALL\n");
             return WINED3DERR_INVALIDCALL;
-        } else if(IWineD3DSurfaceImpl_BltZ(This, DestRect, SrcSurface, SrcRect, Flags, DDBltFx) == WINED3D_OK) {
+        }
+        else if (SUCCEEDED(IWineD3DSurfaceImpl_BltZ(This, DestRect, src_surface, SrcRect, Flags, DDBltFx)))
+        {
             TRACE("Z Blit override handled the blit\n");
             return WINED3D_OK;
         }
@@ -3858,48 +3840,49 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT
 
     /* Special cases for RenderTargets */
     if ((This->resource.usage & WINED3DUSAGE_RENDERTARGET)
-            || (Src && (Src->resource.usage & WINED3DUSAGE_RENDERTARGET)))
+            || (src && (src->resource.usage & WINED3DUSAGE_RENDERTARGET)))
     {
-        if (SUCCEEDED(IWineD3DSurfaceImpl_BltOverride(This, DestRect, Src, SrcRect, Flags, DDBltFx, Filter)))
+        if (SUCCEEDED(IWineD3DSurfaceImpl_BltOverride(This, DestRect, src, SrcRect, Flags, DDBltFx, Filter)))
             return WINED3D_OK;
     }
 
     /* For the rest call the X11 surface implementation.
      * For RenderTargets this should be implemented OpenGL accelerated in BltOverride,
-     * other Blts are rather rare
-     */
-    return IWineD3DBaseSurfaceImpl_Blt(iface, DestRect, SrcSurface, SrcRect, Flags, DDBltFx, Filter);
+     * other Blts are rather rare. */
+    return IWineD3DBaseSurfaceImpl_Blt(iface, DestRect, src_surface, SrcRect, Flags, DDBltFx, Filter);
 }
 
 static HRESULT WINAPI IWineD3DSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dstx, DWORD dsty,
-        IWineD3DSurface *Source, const RECT *rsrc, DWORD trans)
+        IWineD3DSurface *src_surface, const RECT *rsrc, DWORD trans)
 {
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
-    IWineD3DSurfaceImpl *srcImpl = (IWineD3DSurfaceImpl *) Source;
+    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
+    IWineD3DSurfaceImpl *src = (IWineD3DSurfaceImpl *)src_surface;
     IWineD3DDeviceImpl *device = This->resource.device;
 
-    TRACE("(%p)->(%d, %d, %p, %p, %08x\n", iface, dstx, dsty, Source, rsrc, trans);
+    TRACE("iface %p, dst_x %u, dst_y %u, src_surface %p, src_rect %s, flags %#x.\n",
+            iface, dstx, dsty, src_surface, wine_dbgstr_rect(rsrc), trans);
 
-    if ( (This->Flags & SFLAG_LOCKED) || (srcImpl->Flags & SFLAG_LOCKED))
+    if ((This->Flags & SFLAG_LOCKED) || (src->Flags & SFLAG_LOCKED))
     {
         WARN(" Surface is busy, returning DDERR_SURFACEBUSY\n");
         return WINEDDERR_SURFACEBUSY;
     }
 
-    if (device->inScene && (This == device->depth_stencil || srcImpl == device->depth_stencil))
+    if (device->inScene && (This == device->depth_stencil || src == device->depth_stencil))
     {
         TRACE("Attempt to access the depth stencil surface in a BeginScene / EndScene pair, returning WINED3DERR_INVALIDCALL\n");
         return WINED3DERR_INVALIDCALL;
     }
 
     /* Special cases for RenderTargets */
-    if( (This->resource.usage & WINED3DUSAGE_RENDERTARGET) ||
-        (srcImpl->resource.usage & WINED3DUSAGE_RENDERTARGET) ) {
+    if ((This->resource.usage & WINED3DUSAGE_RENDERTARGET)
+            || (src->resource.usage & WINED3DUSAGE_RENDERTARGET))
+    {
 
         RECT SrcRect, DstRect;
         DWORD Flags=0;
 
-        surface_get_rect(srcImpl, rsrc, &SrcRect);
+        surface_get_rect(src, rsrc, &SrcRect);
 
         DstRect.left = dstx;
         DstRect.top=dsty;
@@ -3917,12 +3900,11 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD
             Flags |= WINEDDBLT_DONOTWAIT;
 
         if (SUCCEEDED(IWineD3DSurfaceImpl_BltOverride(This,
-                &DstRect, srcImpl, &SrcRect, Flags, NULL, WINED3DTEXF_POINT)))
+                &DstRect, src, &SrcRect, Flags, NULL, WINED3DTEXF_POINT)))
             return WINED3D_OK;
     }
 
-
-    return IWineD3DBaseSurfaceImpl_BltFast(iface, dstx, dsty, Source, rsrc, trans);
+    return IWineD3DBaseSurfaceImpl_BltFast(iface, dstx, dsty, src_surface, rsrc, trans);
 }
 
 static HRESULT WINAPI IWineD3DSurfaceImpl_RealizePalette(IWineD3DSurface *iface)
@@ -3935,23 +3917,27 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_RealizePalette(IWineD3DSurface *iface)
 
     if (!pal) return WINED3D_OK;
 
-    if (This->resource.format_desc->format == WINED3DFMT_P8_UINT
-            || This->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM)
+    if (This->resource.format->id == WINED3DFMT_P8_UINT
+            || This->resource.format->id == WINED3DFMT_P8_UINT_A8_UNORM)
     {
-        if(This->resource.usage & WINED3DUSAGE_RENDERTARGET)
+        if (This->resource.usage & WINED3DUSAGE_RENDERTARGET)
         {
-            /* Make sure the texture is up to date. This call doesn't do anything if the texture is already up to date. */
-            IWineD3DSurface_LoadLocation(iface, SFLAG_INTEXTURE, NULL);
+            /* Make sure the texture is up to date. This call doesn't do
+             * anything if the texture is already up to date. */
+            surface_load_location(This, SFLAG_INTEXTURE, NULL);
 
             /* We want to force a palette refresh, so mark the drawable as not being up to date */
-            IWineD3DSurface_ModifyLocation(iface, SFLAG_INDRAWABLE, FALSE);
-        } else {
-            if(!(This->Flags & SFLAG_INSYSMEM)) {
-                TRACE("Palette changed with surface that does not have an up to date system memory copy\n");
-                IWineD3DSurface_LoadLocation(iface, SFLAG_INSYSMEM, NULL);
+            surface_modify_location(This, SFLAG_INDRAWABLE, FALSE);
+        }
+        else
+        {
+            if (!(This->Flags & SFLAG_INSYSMEM))
+            {
+                TRACE("Palette changed with surface that does not have an up to date system memory copy.\n");
+                surface_load_location(This, SFLAG_INSYSMEM, NULL);
             }
             TRACE("Dirtifying surface\n");
-            IWineD3DSurface_ModifyLocation(iface, SFLAG_INSYSMEM, TRUE);
+            surface_modify_location(This, SFLAG_INSYSMEM, TRUE);
         }
     }
 
@@ -3967,8 +3953,8 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_RealizePalette(IWineD3DSurface *iface)
     }
 
     /* Propagate the changes to the drawable when we have a palette. */
-    if(This->resource.usage & WINED3DUSAGE_RENDERTARGET)
-        IWineD3DSurface_LoadLocation(iface, SFLAG_INDRAWABLE, NULL);
+    if (This->resource.usage & WINED3DUSAGE_RENDERTARGET)
+        surface_load_location(This, SFLAG_INDRAWABLE, NULL);
 
     return WINED3D_OK;
 }
@@ -3983,7 +3969,7 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_PrivateSetup(IWineD3DSurface *iface) {
     This->texture_target = GL_TEXTURE_2D;
 
     /* Non-power2 support */
-    if (gl_info->supported[ARB_TEXTURE_NON_POWER_OF_TWO] || gl_info->supported[WINE_NORMALIZED_TEXRECT])
+    if (gl_info->supported[ARB_TEXTURE_NON_POWER_OF_TWO] || gl_info->supported[WINED3D_GL_NORMALIZED_TEXRECT])
     {
         pow2Width = This->currentDesc.Width;
         pow2Height = This->currentDesc.Height;
@@ -3998,9 +3984,10 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_PrivateSetup(IWineD3DSurface *iface) {
     This->pow2Width  = pow2Width;
     This->pow2Height = pow2Height;
 
-    if (pow2Width > This->currentDesc.Width || pow2Height > This->currentDesc.Height) {
-        /** TODO: add support for non power two compressed textures **/
-        if (This->resource.format_desc->Flags & WINED3DFMT_FLAG_COMPRESSED)
+    if (pow2Width > This->currentDesc.Width || pow2Height > This->currentDesc.Height)
+    {
+        /* TODO: Add support for non power two compressed textures. */
+        if (This->resource.format->Flags & WINED3DFMT_FLAG_COMPRESSED)
         {
             FIXME("(%p) Compressed non-power-two textures are not supported w(%d) h(%d)\n",
                   This, This->currentDesc.Width, This->currentDesc.Height);
@@ -4039,7 +4026,7 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_PrivateSetup(IWineD3DSurface *iface) {
            doesn't work in combination with ARB_TEXTURE_RECTANGLE.
         */
         if (This->Flags & SFLAG_NONPOW2 && gl_info->supported[ARB_TEXTURE_RECTANGLE]
-                && !(This->resource.format_desc->format == WINED3DFMT_P8_UINT
+                && !(This->resource.format->id == WINED3DFMT_P8_UINT
                 && gl_info->supported[EXT_PALETTED_TEXTURE]
                 && wined3d_settings.rendertargetlock_mode == RTL_READTEX))
         {
@@ -4050,11 +4037,19 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_PrivateSetup(IWineD3DSurface *iface) {
         }
     }
 
-    if(This->resource.usage & WINED3DUSAGE_RENDERTARGET) {
-        switch(wined3d_settings.offscreen_rendering_mode) {
-            case ORM_FBO:        This->get_drawable_size = get_drawable_size_fbo;        break;
-            case ORM_BACKBUFFER: This->get_drawable_size = get_drawable_size_backbuffer; break;
-        }
+    switch (wined3d_settings.offscreen_rendering_mode)
+    {
+        case ORM_FBO:
+            This->get_drawable_size = get_drawable_size_fbo;
+            break;
+
+        case ORM_BACKBUFFER:
+            This->get_drawable_size = get_drawable_size_backbuffer;
+            break;
+
+        default:
+            ERR("Unhandled offscreen rendering mode %#x.\n", wined3d_settings.offscreen_rendering_mode);
+            return WINED3DERR_INVALIDCALL;
     }
 
     This->Flags |= SFLAG_INSYSMEM;
@@ -4171,6 +4166,14 @@ void surface_load_ds_location(IWineD3DSurfaceImpl *surface, struct wined3d_conte
     {
         GLint old_binding = 0;
         GLenum bind_target;
+        GLsizei w, h;
+
+        /* The render target is allowed to be smaller than the depth/stencil
+         * buffer, so the onscreen depth/stencil buffer is potentially smaller
+         * than the offscreen surface. Don't overwrite the offscreen surface
+         * with undefined data. */
+        w = min(surface->currentDesc.Width, context->swapchain->presentParms.BackBufferWidth);
+        h = min(surface->currentDesc.Height, context->swapchain->presentParms.BackBufferHeight);
 
         TRACE("Copying onscreen depth buffer to depth texture.\n");
 
@@ -4195,8 +4198,7 @@ void surface_load_ds_location(IWineD3DSurfaceImpl *surface, struct wined3d_conte
             bind_target = GL_TEXTURE_2D;
         }
         glBindTexture(bind_target, device->depth_blt_texture);
-        glCopyTexImage2D(bind_target, surface->texture_level, surface->resource.format_desc->glInternal,
-                0, 0, surface->currentDesc.Width, surface->currentDesc.Height, 0);
+        glCopyTexImage2D(bind_target, surface->texture_level, surface->resource.format->glInternal, 0, 0, w, h, 0);
         glTexParameteri(bind_target, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
         glTexParameteri(bind_target, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
         glTexParameteri(bind_target, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
@@ -4211,16 +4213,14 @@ void surface_load_ds_location(IWineD3DSurfaceImpl *surface, struct wined3d_conte
             gl_info->fbo_ops.glGenRenderbuffers(1, &device->depth_blt_rb);
             checkGLcall("glGenRenderbuffersEXT");
         }
-        if (device->depth_blt_rb_w != surface->currentDesc.Width
-                || device->depth_blt_rb_h != surface->currentDesc.Height)
+        if (device->depth_blt_rb_w != w || device->depth_blt_rb_h != h)
         {
             gl_info->fbo_ops.glBindRenderbuffer(GL_RENDERBUFFER, device->depth_blt_rb);
             checkGLcall("glBindRenderbufferEXT");
-            gl_info->fbo_ops.glRenderbufferStorage(GL_RENDERBUFFER, GL_RGBA8,
-                    surface->currentDesc.Width, surface->currentDesc.Height);
+            gl_info->fbo_ops.glRenderbufferStorage(GL_RENDERBUFFER, GL_RGBA8, w, h);
             checkGLcall("glRenderbufferStorageEXT");
-            device->depth_blt_rb_w = surface->currentDesc.Width;
-            device->depth_blt_rb_h = surface->currentDesc.Height;
+            device->depth_blt_rb_w = w;
+            device->depth_blt_rb_h = h;
         }
 
         context_bind_fbo(context, GL_FRAMEBUFFER, &context->dst_fbo);
@@ -4230,8 +4230,7 @@ void surface_load_ds_location(IWineD3DSurfaceImpl *surface, struct wined3d_conte
         context_attach_depth_stencil_fbo(context, GL_FRAMEBUFFER, surface, FALSE);
 
         /* Do the actual blit */
-        surface_depth_blt(surface, gl_info, device->depth_blt_texture,
-                surface->currentDesc.Width, surface->currentDesc.Height, bind_target);
+        surface_depth_blt(surface, gl_info, device->depth_blt_texture, w, h, bind_target);
         checkGLcall("depth_blt");
 
         if (context->current_fbo) context_bind_fbo(context, GL_FRAMEBUFFER, &context->current_fbo->id);
@@ -4268,58 +4267,65 @@ void surface_load_ds_location(IWineD3DSurfaceImpl *surface, struct wined3d_conte
     surface->ds_current_size.cy = surface->currentDesc.Height;
 }
 
-static void WINAPI IWineD3DSurfaceImpl_ModifyLocation(IWineD3DSurface *iface, DWORD flag, BOOL persistent) {
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
-    IWineD3DBaseTexture *texture;
+void surface_modify_location(IWineD3DSurfaceImpl *surface, DWORD flag, BOOL persistent)
+{
     IWineD3DSurfaceImpl *overlay;
 
-    TRACE("(%p)->(%s, %s)\n", iface, debug_surflocation(flag),
-          persistent ? "TRUE" : "FALSE");
+    TRACE("surface %p, location %s, persistent %#x.\n",
+            surface, debug_surflocation(flag), persistent);
 
     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
     {
-        if (surface_is_offscreen(This))
+        if (surface_is_offscreen(surface))
         {
             /* With ORM_FBO, SFLAG_INTEXTURE and SFLAG_INDRAWABLE are the same for offscreen targets. */
             if (flag & (SFLAG_INTEXTURE | SFLAG_INDRAWABLE)) flag |= (SFLAG_INTEXTURE | SFLAG_INDRAWABLE);
         }
         else
         {
-            TRACE("Surface %p is an onscreen surface\n", iface);
+            TRACE("Surface %p is an onscreen surface.\n", surface);
         }
     }
 
-    if(persistent) {
-        if(((This->Flags & SFLAG_INTEXTURE) && !(flag & SFLAG_INTEXTURE)) ||
-           ((This->Flags & SFLAG_INSRGBTEX) && !(flag & SFLAG_INSRGBTEX))) {
-            if (IWineD3DSurface_GetContainer(iface, &IID_IWineD3DBaseTexture, (void **)&texture) == WINED3D_OK) {
-                TRACE("Passing to container\n");
-                IWineD3DBaseTexture_SetDirty(texture, TRUE);
-                IWineD3DBaseTexture_Release(texture);
+    if (persistent)
+    {
+        if (((surface->Flags & SFLAG_INTEXTURE) && !(flag & SFLAG_INTEXTURE))
+                || ((surface->Flags & SFLAG_INSRGBTEX) && !(flag & SFLAG_INSRGBTEX)))
+        {
+            if (surface->container.type == WINED3D_CONTAINER_TEXTURE)
+            {
+                TRACE("Passing to container.\n");
+                IWineD3DBaseTexture_SetDirty((IWineD3DBaseTexture *)surface->container.u.texture, TRUE);
             }
         }
-        This->Flags &= ~SFLAG_LOCATIONS;
-        This->Flags |= flag;
+        surface->Flags &= ~SFLAG_LOCATIONS;
+        surface->Flags |= flag;
 
         /* Redraw emulated overlays, if any */
-        if(flag & SFLAG_INDRAWABLE && !list_empty(&This->overlays)) {
-            LIST_FOR_EACH_ENTRY(overlay, &This->overlays, IWineD3DSurfaceImpl, overlay_entry) {
-                IWineD3DSurface_DrawOverlay((IWineD3DSurface *) overlay);
+        if (flag & SFLAG_INDRAWABLE && !list_empty(&surface->overlays))
+        {
+            LIST_FOR_EACH_ENTRY(overlay, &surface->overlays, IWineD3DSurfaceImpl, overlay_entry)
+            {
+                IWineD3DSurface_DrawOverlay((IWineD3DSurface *)overlay);
             }
         }
-    } else {
-        if((This->Flags & (SFLAG_INTEXTURE | SFLAG_INSRGBTEX)) && (flag & (SFLAG_INTEXTURE | SFLAG_INSRGBTEX))) {
-            if (IWineD3DSurface_GetContainer(iface, &IID_IWineD3DBaseTexture, (void **)&texture) == WINED3D_OK) {
+    }
+    else
+    {
+        if ((surface->Flags & (SFLAG_INTEXTURE | SFLAG_INSRGBTEX)) && (flag & (SFLAG_INTEXTURE | SFLAG_INSRGBTEX)))
+        {
+            if (surface->container.type == WINED3D_CONTAINER_TEXTURE)
+            {
                 TRACE("Passing to container\n");
-                IWineD3DBaseTexture_SetDirty(texture, TRUE);
-                IWineD3DBaseTexture_Release(texture);
+                IWineD3DBaseTexture_SetDirty((IWineD3DBaseTexture *)surface->container.u.texture, TRUE);
             }
         }
-        This->Flags &= ~flag;
+        surface->Flags &= ~flag;
     }
 
-    if(!(This->Flags & SFLAG_LOCATIONS)) {
-        ERR("%p: Surface does not have any up to date location\n", This);
+    if (!(surface->Flags & SFLAG_LOCATIONS))
+    {
+        ERR("Surface %p does not have any up to date location.\n", surface);
     }
 }
 
@@ -4346,7 +4352,8 @@ static inline void surface_blt_to_drawable(IWineD3DSurfaceImpl *This, const RECT
         dst_rect = src_rect;
     }
 
-    if ((This->Flags & SFLAG_SWAPCHAIN) && This == ((IWineD3DSwapChainImpl *)This->container)->front_buffer)
+    swapchain = This->container.type == WINED3D_CONTAINER_SWAPCHAIN ? This->container.u.swapchain : NULL;
+    if (swapchain && This == swapchain->front_buffer)
         surface_translate_frontbuffer_coords(This, context->win_handle, &dst_rect);
 
     device->blitter->set_shader((IWineD3DDevice *) device, This);
@@ -4355,9 +4362,8 @@ static inline void surface_blt_to_drawable(IWineD3DSurfaceImpl *This, const RECT
     draw_textured_quad(This, &src_rect, &dst_rect, WINED3DTEXF_POINT);
     LEAVE_GL();
 
-    device->blitter->set_shader((IWineD3DDevice *) device, This);
+    device->blitter->unset_shader((IWineD3DDevice *) device);
 
-    swapchain = (This->Flags & SFLAG_SWAPCHAIN) ? (IWineD3DSwapChainImpl *)This->container : NULL;
     if (wined3d_settings.strict_draw_ordering || (swapchain
             && (This == swapchain->front_buffer || swapchain->num_contexts > 1)))
         wglFlush(); /* Flush to ensure ordering across contexts. */
@@ -4365,57 +4371,38 @@ static inline void surface_blt_to_drawable(IWineD3DSurfaceImpl *This, const RECT
     context_release(context);
 }
 
-/*****************************************************************************
- * IWineD3DSurface::LoadLocation
- *
- * Copies the current surface data from wherever it is to the requested
- * location. The location is one of the surface flags, SFLAG_INSYSMEM,
- * SFLAG_INTEXTURE and SFLAG_INDRAWABLE. When the surface is current in
- * multiple locations, the gl texture is preferred over the drawable, which is
- * preferred over system memory. The PBO counts as system memory. If rect is
- * not NULL, only the specified rectangle is copied (only supported for
- * sysmem<->drawable copies at the moment). If rect is NULL, the destination
- * location is marked up to date after the copy.
- *
- * Parameters:
- *  flag: Surface location flag to be updated
- *  rect: rectangle to be copied
- *
- * Returns:
- *  WINED3D_OK on success
- *  WINED3DERR_DEVICELOST on an internal error
- *
- *****************************************************************************/
-static HRESULT WINAPI IWineD3DSurfaceImpl_LoadLocation(IWineD3DSurface *iface, DWORD flag, const RECT *rect) {
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
-    IWineD3DDeviceImpl *device = This->resource.device;
+HRESULT surface_load_location(IWineD3DSurfaceImpl *surface, DWORD flag, const RECT *rect)
+{
+    IWineD3DDeviceImpl *device = surface->resource.device;
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    struct wined3d_format_desc desc;
+    BOOL drawable_read_ok = surface_is_offscreen(surface);
+    struct wined3d_format format;
     CONVERT_TYPES convert;
     int width, pitch, outpitch;
     BYTE *mem;
-    BOOL drawable_read_ok = TRUE;
     BOOL in_fbo = FALSE;
 
-    if (This->resource.usage & WINED3DUSAGE_DEPTHSTENCIL)
+    TRACE("surface %p, location %s, rect %s.\n", surface, debug_surflocation(flag), wine_dbgstr_rect(rect));
+
+    if (surface->resource.usage & WINED3DUSAGE_DEPTHSTENCIL)
     {
         if (flag == SFLAG_INTEXTURE)
         {
             struct wined3d_context *context = context_acquire(device, NULL);
-            surface_load_ds_location(This, context, SFLAG_DS_OFFSCREEN);
+            surface_load_ds_location(surface, context, SFLAG_DS_OFFSCREEN);
             context_release(context);
             return WINED3D_OK;
         }
         else
         {
-            FIXME("Unimplemented location %#x for depth/stencil buffers.\n", flag);
+            FIXME("Unimplemented location %s for depth/stencil buffers.\n", debug_surflocation(flag));
             return WINED3DERR_INVALIDCALL;
         }
     }
 
     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
     {
-        if (surface_is_offscreen(This))
+        if (surface_is_offscreen(surface))
         {
             /* With ORM_FBO, SFLAG_INTEXTURE and SFLAG_INDRAWABLE are the same for offscreen targets.
              * Prefer SFLAG_INTEXTURE. */
@@ -4425,83 +4412,88 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadLocation(IWineD3DSurface *iface, D
         }
         else
         {
-            TRACE("Surface %p is an onscreen surface\n", iface);
+            TRACE("Surface %p is an onscreen surface.\n", surface);
         }
     }
 
-    TRACE("(%p)->(%s, %p)\n", iface, debug_surflocation(flag), rect);
-    if(rect) {
-        TRACE("Rectangle: (%d,%d)-(%d,%d)\n", rect->left, rect->top, rect->right, rect->bottom);
-    }
-
-    if(This->Flags & flag) {
+    if (surface->Flags & flag)
+    {
         TRACE("Location already up to date\n");
         return WINED3D_OK;
     }
 
-    if(!(This->Flags & SFLAG_LOCATIONS)) {
-        ERR("%p: Surface does not have any up to date location\n", This);
-        This->Flags |= SFLAG_LOST;
+    if (!(surface->Flags & SFLAG_LOCATIONS))
+    {
+        ERR("Surface %p does not have any up to date location.\n", surface);
+        surface->Flags |= SFLAG_LOST;
         return WINED3DERR_DEVICELOST;
     }
 
-    if(flag == SFLAG_INSYSMEM) {
-        surface_prepare_system_memory(This);
+    if (flag == SFLAG_INSYSMEM)
+    {
+        surface_prepare_system_memory(surface);
 
         /* Download the surface to system memory */
-        if (This->Flags & (SFLAG_INTEXTURE | SFLAG_INSRGBTEX))
+        if (surface->Flags & (SFLAG_INTEXTURE | SFLAG_INSRGBTEX))
         {
             struct wined3d_context *context = NULL;
 
             if (!device->isInDraw) context = context_acquire(device, NULL);
 
-            surface_bind_and_dirtify(This, !(This->Flags & SFLAG_INTEXTURE));
-            surface_download_data(This, gl_info);
+            surface_bind_and_dirtify(surface, !(surface->Flags & SFLAG_INTEXTURE));
+            surface_download_data(surface, gl_info);
 
             if (context) context_release(context);
         }
         else
         {
             /* Note: It might be faster to download into a texture first. */
-            read_from_framebuffer(This, rect,
-                                  This->resource.allocatedMemory,
-                                  IWineD3DSurface_GetPitch(iface));
+            read_from_framebuffer(surface, rect, surface->resource.allocatedMemory,
+                    IWineD3DSurface_GetPitch((IWineD3DSurface *)surface));
         }
-    } else if(flag == SFLAG_INDRAWABLE) {
-        if(This->Flags & SFLAG_INTEXTURE) {
-            surface_blt_to_drawable(This, rect);
-        } else {
+    }
+    else if (flag == SFLAG_INDRAWABLE)
+    {
+        if (surface->Flags & SFLAG_INTEXTURE)
+        {
+            surface_blt_to_drawable(surface, rect);
+        }
+        else
+        {
             int byte_count;
-            if((This->Flags & SFLAG_LOCATIONS) == SFLAG_INSRGBTEX) {
+            if ((surface->Flags & SFLAG_LOCATIONS) == SFLAG_INSRGBTEX)
+            {
                 /* This needs a shader to convert the srgb data sampled from the GL texture into RGB
                  * values, otherwise we get incorrect values in the target. For now go the slow way
                  * via a system memory copy
                  */
-                IWineD3DSurfaceImpl_LoadLocation(iface, SFLAG_INSYSMEM, rect);
+                surface_load_location(surface, SFLAG_INSYSMEM, rect);
             }
 
-            d3dfmt_get_conv(This, FALSE /* We need color keying */, FALSE /* We won't use textures */, &desc, &convert);
+            d3dfmt_get_conv(surface, FALSE /* We need color keying */,
+                    FALSE /* We won't use textures */, &format, &convert);
 
             /* The width is in 'length' not in bytes */
-            width = This->currentDesc.Width;
-            pitch = IWineD3DSurface_GetPitch(iface);
+            width = surface->currentDesc.Width;
+            pitch = IWineD3DSurface_GetPitch((IWineD3DSurface *)surface);
 
             /* Don't use PBOs for converted surfaces. During PBO conversion we look at SFLAG_CONVERTED
              * but it isn't set (yet) in all cases it is getting called. */
-            if ((convert != NO_CONVERSION) && (This->Flags & SFLAG_PBO))
+            if ((convert != NO_CONVERSION) && (surface->Flags & SFLAG_PBO))
             {
                 struct wined3d_context *context = NULL;
 
-                TRACE("Removing the pbo attached to surface %p\n", This);
+                TRACE("Removing the pbo attached to surface %p.\n", surface);
 
                 if (!device->isInDraw) context = context_acquire(device, NULL);
-                surface_remove_pbo(This, gl_info);
+                surface_remove_pbo(surface, gl_info);
                 if (context) context_release(context);
             }
 
-            if((convert != NO_CONVERSION) && This->resource.allocatedMemory) {
-                int height = This->currentDesc.Height;
-                byte_count = desc.conv_byte_count;
+            if ((convert != NO_CONVERSION) && surface->resource.allocatedMemory)
+            {
+                int height = surface->currentDesc.Height;
+                byte_count = format.conv_byte_count;
 
                 /* Stick to the alignment for the converted surface too, makes it easier to load the surface */
                 outpitch = width * byte_count;
@@ -4512,24 +4504,44 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadLocation(IWineD3DSurface *iface, D
                     ERR("Out of memory %d, %d!\n", outpitch, height);
                     return WINED3DERR_OUTOFVIDEOMEMORY;
                 }
-                d3dfmt_convert_surface(This->resource.allocatedMemory, mem, pitch, width, height, outpitch, convert, This);
+                d3dfmt_convert_surface(surface->resource.allocatedMemory, mem, pitch,
+                        width, height, outpitch, convert, surface);
 
-                This->Flags |= SFLAG_CONVERTED;
-            } else {
-                This->Flags &= ~SFLAG_CONVERTED;
-                mem = This->resource.allocatedMemory;
-                byte_count = desc.byte_count;
+                surface->Flags |= SFLAG_CONVERTED;
+            }
+            else
+            {
+                surface->Flags &= ~SFLAG_CONVERTED;
+                mem = surface->resource.allocatedMemory;
+                byte_count = format.byte_count;
             }
 
-            flush_to_framebuffer_drawpixels(This, desc.glFormat, desc.glType, byte_count, mem);
+            flush_to_framebuffer_drawpixels(surface, format.glFormat, format.glType, byte_count, mem);
 
             /* Don't delete PBO memory */
-            if((mem != This->resource.allocatedMemory) && !(This->Flags & SFLAG_PBO))
+            if ((mem != surface->resource.allocatedMemory) && !(surface->Flags & SFLAG_PBO))
                 HeapFree(GetProcessHeap(), 0, mem);
         }
-    } else /* if(flag & (SFLAG_INTEXTURE | SFLAG_INSRGBTEX)) */ {
-        if (drawable_read_ok && (This->Flags & SFLAG_INDRAWABLE)) {
-            read_from_framebuffer_texture(This, flag == SFLAG_INSRGBTEX);
+    }
+    else /* if(flag & (SFLAG_INTEXTURE | SFLAG_INSRGBTEX)) */
+    {
+        const DWORD attach_flags = WINED3DFMT_FLAG_FBO_ATTACHABLE | WINED3DFMT_FLAG_FBO_ATTACHABLE_SRGB;
+
+        if (drawable_read_ok && (surface->Flags & SFLAG_INDRAWABLE))
+        {
+            read_from_framebuffer_texture(surface, flag == SFLAG_INSRGBTEX);
+        }
+        else if (surface->Flags & (SFLAG_INSRGBTEX | SFLAG_INTEXTURE)
+                && (surface->resource.format->Flags & attach_flags) == attach_flags
+                && fbo_blit_supported(gl_info, BLIT_OP_BLIT,
+                        NULL, surface->resource.usage, surface->resource.pool, surface->resource.format,
+                        NULL, surface->resource.usage, surface->resource.pool, surface->resource.format))
+        {
+            DWORD src_location = flag == SFLAG_INSRGBTEX ? SFLAG_INTEXTURE : SFLAG_INSRGBTEX;
+            RECT rect = {0, 0, surface->currentDesc.Width, surface->currentDesc.Height};
+
+            surface_blt_fbo(surface->resource.device, WINED3DTEXF_POINT,
+                    surface, src_location, &rect, surface, flag, &rect);
         }
         else
         {
@@ -4537,57 +4549,65 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadLocation(IWineD3DSurface *iface, D
             BOOL srgb = flag == SFLAG_INSRGBTEX;
             struct wined3d_context *context = NULL;
 
-            d3dfmt_get_conv(This, TRUE /* We need color keying */, TRUE /* We will use textures */,
-                    &desc, &convert);
+            d3dfmt_get_conv(surface, TRUE /* We need color keying */,
+                    TRUE /* We will use textures */, &format, &convert);
 
-            if(srgb) {
-                if((This->Flags & (SFLAG_INTEXTURE | SFLAG_INSYSMEM)) == SFLAG_INTEXTURE) {
-                    /* Performance warning ... */
-                    FIXME("%p: Downloading rgb texture to reload it as srgb\n", This);
-                    IWineD3DSurfaceImpl_LoadLocation(iface, SFLAG_INSYSMEM, rect);
+            if (srgb)
+            {
+                if ((surface->Flags & (SFLAG_INTEXTURE | SFLAG_INSYSMEM)) == SFLAG_INTEXTURE)
+                {
+                    /* Performance warning... */
+                    FIXME("Downloading RGB surface %p to reload it as sRGB.\n", surface);
+                    surface_load_location(surface, SFLAG_INSYSMEM, rect);
                 }
-            } else {
-                if((This->Flags & (SFLAG_INSRGBTEX | SFLAG_INSYSMEM)) == SFLAG_INSRGBTEX) {
-                    /* Performance warning ... */
-                    FIXME("%p: Downloading srgb texture to reload it as rgb\n", This);
-                    IWineD3DSurfaceImpl_LoadLocation(iface, SFLAG_INSYSMEM, rect);
+            }
+            else
+            {
+                if ((surface->Flags & (SFLAG_INSRGBTEX | SFLAG_INSYSMEM)) == SFLAG_INSRGBTEX)
+                {
+                    /* Performance warning... */
+                    FIXME("Downloading sRGB surface %p to reload it as RGB.\n", surface);
+                    surface_load_location(surface, SFLAG_INSYSMEM, rect);
                 }
             }
-            if(!(This->Flags & SFLAG_INSYSMEM)) {
-                /* Should not happen */
-                ERR("Trying to load a texture from sysmem, but SFLAG_INSYSMEM is not set\n");
+            if (!(surface->Flags & SFLAG_INSYSMEM))
+            {
+                WARN("Trying to load a texture from sysmem, but SFLAG_INSYSMEM is not set.\n");
                 /* Lets hope we get it from somewhere... */
-                IWineD3DSurfaceImpl_LoadLocation(iface, SFLAG_INSYSMEM, rect);
+                surface_load_location(surface, SFLAG_INSYSMEM, rect);
             }
 
             if (!device->isInDraw) context = context_acquire(device, NULL);
 
-            surface_prepare_texture(This, gl_info, srgb);
-            surface_bind_and_dirtify(This, srgb);
+            surface_prepare_texture(surface, gl_info, srgb);
+            surface_bind_and_dirtify(surface, srgb);
 
-            if(This->CKeyFlags & WINEDDSD_CKSRCBLT) {
-                This->Flags |= SFLAG_GLCKEY;
-                This->glCKey = This->SrcBltCKey;
+            if (surface->CKeyFlags & WINEDDSD_CKSRCBLT)
+            {
+                surface->Flags |= SFLAG_GLCKEY;
+                surface->glCKey = surface->SrcBltCKey;
             }
-            else This->Flags &= ~SFLAG_GLCKEY;
+            else surface->Flags &= ~SFLAG_GLCKEY;
 
             /* The width is in 'length' not in bytes */
-            width = This->currentDesc.Width;
-            pitch = IWineD3DSurface_GetPitch(iface);
+            width = surface->currentDesc.Width;
+            pitch = IWineD3DSurface_GetPitch((IWineD3DSurface *)surface);
 
             /* Don't use PBOs for converted surfaces. During PBO conversion we look at SFLAG_CONVERTED
              * but it isn't set (yet) in all cases it is getting called. */
-            if(((convert != NO_CONVERSION) || desc.convert) && (This->Flags & SFLAG_PBO)) {
-                TRACE("Removing the pbo attached to surface %p\n", This);
-                surface_remove_pbo(This, gl_info);
+            if ((convert != NO_CONVERSION || format.convert) && (surface->Flags & SFLAG_PBO))
+            {
+                TRACE("Removing the pbo attached to surface %p.\n", surface);
+                surface_remove_pbo(surface, gl_info);
             }
 
-            if(desc.convert) {
+            if (format.convert)
+            {
                 /* This code is entered for texture formats which need a fixup. */
-                int height = This->currentDesc.Height;
+                int height = surface->currentDesc.Height;
 
                 /* Stick to the alignment for the converted surface too, makes it easier to load the surface */
-                outpitch = width * desc.conv_byte_count;
+                outpitch = width * format.conv_byte_count;
                 outpitch = (outpitch + device->surface_alignment - 1) & ~(device->surface_alignment - 1);
 
                 mem = HeapAlloc(GetProcessHeap(), 0, outpitch * height);
@@ -4596,13 +4616,15 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadLocation(IWineD3DSurface *iface, D
                     if (context) context_release(context);
                     return WINED3DERR_OUTOFVIDEOMEMORY;
                 }
-                desc.convert(This->resource.allocatedMemory, mem, pitch, width, height);
-            } else if((convert != NO_CONVERSION) && This->resource.allocatedMemory) {
+                format.convert(surface->resource.allocatedMemory, mem, pitch, width, height);
+            }
+            else if (convert != NO_CONVERSION && surface->resource.allocatedMemory)
+            {
                 /* This code is only entered for color keying fixups */
-                int height = This->currentDesc.Height;
+                int height = surface->currentDesc.Height;
 
                 /* Stick to the alignment for the converted surface too, makes it easier to load the surface */
-                outpitch = width * desc.conv_byte_count;
+                outpitch = width * format.conv_byte_count;
                 outpitch = (outpitch + device->surface_alignment - 1) & ~(device->surface_alignment - 1);
 
                 mem = HeapAlloc(GetProcessHeap(), 0, outpitch * height);
@@ -4611,9 +4633,12 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadLocation(IWineD3DSurface *iface, D
                     if (context) context_release(context);
                     return WINED3DERR_OUTOFVIDEOMEMORY;
                 }
-                d3dfmt_convert_surface(This->resource.allocatedMemory, mem, pitch, width, height, outpitch, convert, This);
-            } else {
-                mem = This->resource.allocatedMemory;
+                d3dfmt_convert_surface(surface->resource.allocatedMemory, mem, pitch,
+                        width, height, outpitch, convert, surface);
+            }
+            else
+            {
+                mem = surface->resource.allocatedMemory;
             }
 
             /* Make sure the correct pitch is used */
@@ -4621,8 +4646,8 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadLocation(IWineD3DSurface *iface, D
             glPixelStorei(GL_UNPACK_ROW_LENGTH, width);
             LEAVE_GL();
 
-            if (mem || (This->Flags & SFLAG_PBO))
-                surface_upload_data(This, gl_info, &desc, srgb, mem);
+            if (mem || (surface->Flags & SFLAG_PBO))
+                surface_upload_data(surface, gl_info, &format, srgb, mem);
 
             /* Restore the default pitch */
             ENTER_GL();
@@ -4632,45 +4657,22 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_LoadLocation(IWineD3DSurface *iface, D
             if (context) context_release(context);
 
             /* Don't delete PBO memory */
-            if((mem != This->resource.allocatedMemory) && !(This->Flags & SFLAG_PBO))
+            if ((mem != surface->resource.allocatedMemory) && !(surface->Flags & SFLAG_PBO))
                 HeapFree(GetProcessHeap(), 0, mem);
         }
     }
 
-    if(rect == NULL) {
-        This->Flags |= flag;
-    }
+    if (!rect) surface->Flags |= flag;
 
-    if (in_fbo && (This->Flags & (SFLAG_INTEXTURE | SFLAG_INDRAWABLE))) {
+    if (in_fbo && (surface->Flags & (SFLAG_INTEXTURE | SFLAG_INDRAWABLE)))
+    {
         /* With ORM_FBO, SFLAG_INTEXTURE and SFLAG_INDRAWABLE are the same for offscreen targets. */
-        This->Flags |= (SFLAG_INTEXTURE | SFLAG_INDRAWABLE);
+        surface->Flags |= (SFLAG_INTEXTURE | SFLAG_INDRAWABLE);
     }
 
     return WINED3D_OK;
 }
 
-static HRESULT WINAPI IWineD3DSurfaceImpl_SetContainer(IWineD3DSurface *iface, IWineD3DBase *container)
-{
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
-    IWineD3DSwapChain *swapchain = NULL;
-
-    /* Update the drawable size method */
-    if(container) {
-        IWineD3DBase_QueryInterface(container, &IID_IWineD3DSwapChain, (void **) &swapchain);
-    }
-    if(swapchain) {
-        This->get_drawable_size = get_drawable_size_swapchain;
-        IWineD3DSwapChain_Release(swapchain);
-    } else if(This->resource.usage & WINED3DUSAGE_RENDERTARGET) {
-        switch(wined3d_settings.offscreen_rendering_mode) {
-            case ORM_FBO:        This->get_drawable_size = get_drawable_size_fbo;        break;
-            case ORM_BACKBUFFER: This->get_drawable_size = get_drawable_size_backbuffer; break;
-        }
-    }
-
-    return IWineD3DBaseSurfaceImpl_SetContainer(iface, container);
-}
-
 static WINED3DSURFTYPE WINAPI IWineD3DSurfaceImpl_GetImplType(IWineD3DSurface *iface) {
     return SURFACE_OPENGL;
 }
@@ -4699,10 +4701,10 @@ static HRESULT WINAPI IWineD3DSurfaceImpl_DrawOverlay(IWineD3DSurface *iface) {
 
 BOOL surface_is_offscreen(IWineD3DSurfaceImpl *surface)
 {
-    IWineD3DSwapChainImpl *swapchain = (IWineD3DSwapChainImpl *)surface->container;
+    IWineD3DSwapChainImpl *swapchain = surface->container.u.swapchain;
 
     /* Not on a swapchain - must be offscreen */
-    if (!(surface->Flags & SFLAG_SWAPCHAIN)) return TRUE;
+    if (surface->container.type != WINED3D_CONTAINER_SWAPCHAIN) return TRUE;
 
     /* The front buffer is always onscreen */
     if (surface == swapchain->front_buffer) return FALSE;
@@ -4729,7 +4731,6 @@ const IWineD3DSurfaceVtbl IWineD3DSurface_Vtbl =
     IWineD3DSurfaceImpl_UnLoad,
     IWineD3DBaseSurfaceImpl_GetType,
     /* IWineD3DSurface */
-    IWineD3DBaseSurfaceImpl_GetContainer,
     IWineD3DBaseSurfaceImpl_GetDesc,
     IWineD3DSurfaceImpl_LockRect,
     IWineD3DSurfaceImpl_UnlockRect,
@@ -4757,13 +4758,9 @@ const IWineD3DSurfaceVtbl IWineD3DSurface_Vtbl =
     /* Internal use: */
     IWineD3DSurfaceImpl_LoadTexture,
     IWineD3DSurfaceImpl_BindTexture,
-    IWineD3DSurfaceImpl_SaveSnapshot,
-    IWineD3DSurfaceImpl_SetContainer,
     IWineD3DBaseSurfaceImpl_GetData,
     IWineD3DSurfaceImpl_SetFormat,
     IWineD3DSurfaceImpl_PrivateSetup,
-    IWineD3DSurfaceImpl_ModifyLocation,
-    IWineD3DSurfaceImpl_LoadLocation,
     IWineD3DSurfaceImpl_GetImplType,
     IWineD3DSurfaceImpl_DrawOverlay
 };
@@ -4792,7 +4789,7 @@ static HRESULT ffp_blit_set(IWineD3DDevice *iface, IWineD3DSurfaceImpl *surface)
 {
     IWineD3DDeviceImpl *device = (IWineD3DDeviceImpl *) iface;
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    enum complex_fixup fixup = get_complex_fixup(surface->resource.format_desc->color_fixup);
+    enum complex_fixup fixup = get_complex_fixup(surface->resource.format->color_fixup);
 
     /* When EXT_PALETTED_TEXTURE is around, palette conversion is done by the GPU
      * else the surface is converted in software at upload time in LoadLocation.
@@ -4830,10 +4827,8 @@ static void ffp_blit_unset(IWineD3DDevice *iface)
 }
 
 static BOOL ffp_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_operation blit_op,
-                               const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool,
-                               const struct wined3d_format_desc *src_format_desc,
-                               const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool,
-                               const struct wined3d_format_desc *dst_format_desc)
+        const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool, const struct wined3d_format *src_format,
+        const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool, const struct wined3d_format *dst_format)
 {
     enum complex_fixup src_fixup;
 
@@ -4848,11 +4843,11 @@ static BOOL ffp_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_
         return TRUE;
     }
 
-    src_fixup = get_complex_fixup(src_format_desc->color_fixup);
+    src_fixup = get_complex_fixup(src_format->color_fixup);
     if (TRACE_ON(d3d_surface) && TRACE_ON(d3d))
     {
         TRACE("Checking support for fixup:\n");
-        dump_color_fixup_desc(src_format_desc->color_fixup);
+        dump_color_fixup_desc(src_format->color_fixup);
     }
 
     if (blit_op != BLIT_OP_BLIT)
@@ -4861,7 +4856,7 @@ static BOOL ffp_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_
         return FALSE;
      }
 
-    if (!is_identity_fixup(dst_format_desc->color_fixup))
+    if (!is_identity_fixup(dst_format->color_fixup))
     {
         TRACE("Destination fixups are not supported\n");
         return FALSE;
@@ -4874,7 +4869,7 @@ static BOOL ffp_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_
     }
 
     /* We only support identity conversions. */
-    if (is_identity_fixup(src_format_desc->color_fixup))
+    if (is_identity_fixup(src_format->color_fixup))
     {
         TRACE("[OK]\n");
         return TRUE;
@@ -4884,10 +4879,14 @@ static BOOL ffp_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_
     return FALSE;
 }
 
-static HRESULT ffp_blit_color_fill(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *dst_surface, const RECT *dst_rect, DWORD fill_color)
+/* Do not call while under the GL lock. */
+static HRESULT ffp_blit_color_fill(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *dst_surface,
+        const RECT *dst_rect, const WINED3DCOLORVALUE *color)
 {
-    return IWineD3DDeviceImpl_ClearSurface(device, dst_surface, 1 /* Number of rectangles */,
-                                           (const WINED3DRECT*)dst_rect, WINED3DCLEAR_TARGET, fill_color, 0.0f /* Z */, 0 /* Stencil */);
+    const RECT draw_rect = {0, 0, dst_surface->currentDesc.Width, dst_surface->currentDesc.Height};
+
+    return device_clear_render_targets(device, 1 /* rt_count */, &dst_surface, 1 /* rect_count */,
+            dst_rect, &draw_rect, WINED3DCLEAR_TARGET, color, 0.0f /* depth */, 0 /* stencil */);
 }
 
 const struct blit_shader ffp_blit =  {
@@ -4921,10 +4920,8 @@ static void cpu_blit_unset(IWineD3DDevice *iface)
 }
 
 static BOOL cpu_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_operation blit_op,
-                               const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool,
-                               const struct wined3d_format_desc *src_format_desc,
-                               const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool,
-                               const struct wined3d_format_desc *dst_format_desc)
+        const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool, const struct wined3d_format *src_format,
+        const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool, const struct wined3d_format *dst_format)
 {
     if (blit_op == BLIT_OP_COLOR_FILL)
     {
@@ -4934,13 +4931,17 @@ static BOOL cpu_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_
     return FALSE;
 }
 
-static HRESULT cpu_blit_color_fill(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *dst_surface, const RECT *dst_rect, DWORD fill_color)
+/* Do not call while under the GL lock. */
+static HRESULT cpu_blit_color_fill(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *dst_surface,
+        const RECT *dst_rect, const WINED3DCOLORVALUE *color)
 {
     WINEDDBLTFX BltFx;
+
     memset(&BltFx, 0, sizeof(BltFx));
     BltFx.dwSize = sizeof(BltFx);
-    BltFx.u5.dwFillColor = color_convert_argb_to_fmt(fill_color, dst_surface->resource.format_desc->format);
-    return IWineD3DBaseSurfaceImpl_Blt((IWineD3DSurface*)dst_surface, dst_rect, NULL, NULL, WINEDDBLT_COLORFILL, &BltFx, WINED3DTEXF_POINT);
+    BltFx.u5.dwFillColor = wined3d_format_convert_from_float(dst_surface->resource.format, color);
+    return IWineD3DBaseSurfaceImpl_Blt((IWineD3DSurface*)dst_surface, dst_rect,
+            NULL, NULL, WINEDDBLT_COLORFILL, &BltFx, WINED3DTEXF_POINT);
 }
 
 const struct blit_shader cpu_blit =  {
@@ -4953,10 +4954,8 @@ const struct blit_shader cpu_blit =  {
 };
 
 static BOOL fbo_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_operation blit_op,
-                               const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool,
-                               const struct wined3d_format_desc *src_format_desc,
-                               const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool,
-                               const struct wined3d_format_desc *dst_format_desc)
+        const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool, const struct wined3d_format *src_format,
+        const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool, const struct wined3d_format *dst_format)
 {
     if ((wined3d_settings.offscreen_rendering_mode != ORM_FBO) || !gl_info->fbo_ops.glBlitFramebuffer)
         return FALSE;
@@ -4971,17 +4970,17 @@ static BOOL fbo_blit_supported(const struct wined3d_gl_info *gl_info, enum blit_
     if (src_pool == WINED3DPOOL_SYSTEMMEM || dst_pool == WINED3DPOOL_SYSTEMMEM)
         return FALSE;
 
-    if(!((src_format_desc->Flags & WINED3DFMT_FLAG_FBO_ATTACHABLE) || (src_usage & WINED3DUSAGE_RENDERTARGET))
-        && ((dst_format_desc->Flags & WINED3DFMT_FLAG_FBO_ATTACHABLE) || (dst_usage & WINED3DUSAGE_RENDERTARGET)))
+    if (!((src_format->Flags & WINED3DFMT_FLAG_FBO_ATTACHABLE) || (src_usage & WINED3DUSAGE_RENDERTARGET))
+            && ((dst_format->Flags & WINED3DFMT_FLAG_FBO_ATTACHABLE) || (dst_usage & WINED3DUSAGE_RENDERTARGET)))
         return FALSE;
 
-    if (!is_identity_fixup(src_format_desc->color_fixup) ||
-        !is_identity_fixup(dst_format_desc->color_fixup))
+    if (!is_identity_fixup(src_format->color_fixup)
+            || !is_identity_fixup(dst_format->color_fixup))
         return FALSE;
 
-    if (!(src_format_desc->format == dst_format_desc->format
-        || (is_identity_fixup(src_format_desc->color_fixup)
-        && is_identity_fixup(dst_format_desc->color_fixup))))
+    if (!(src_format->id == dst_format->id
+            || (is_identity_fixup(src_format->color_fixup)
+            && is_identity_fixup(dst_format->color_fixup))))
         return FALSE;
 
     return TRUE;
index 2b6cdb4..e4dd853 100644 (file)
@@ -46,18 +46,18 @@ static inline unsigned short float_32_to_16(const float *in)
     if(isnan(*in)) return 0x7C01;
     if (isinf(*in)) return (*in < 0.0f ? 0xFC00 : 0x7c00);
 
-    if(tmp < pow(2, 10)) {
+    if(tmp < powf(2, 10)) {
         do
         {
             tmp = tmp * 2.0f;
             exp--;
-        }while(tmp < pow(2, 10));
-    } else if(tmp >= pow(2, 11)) {
+        }while(tmp < powf(2, 10));
+    } else if(tmp >= powf(2, 11)) {
         do
         {
             tmp /= 2.0f;
             exp++;
-        }while(tmp >= pow(2, 11));
+        }while(tmp >= powf(2, 11));
     }
 
     mantissa = (unsigned int) tmp;
@@ -139,49 +139,28 @@ WINED3DRESOURCETYPE WINAPI IWineD3DBaseSurfaceImpl_GetType(IWineD3DSurface *ifac
     return resource_get_type((IWineD3DResource *)iface);
 }
 
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetParent(IWineD3DSurface *iface, IUnknown **pParent) {
-    TRACE("(%p) : calling resourceimpl_GetParent\n", iface);
-    return resource_get_parent((IWineD3DResource *)iface, pParent);
-}
-
-/* ******************************************************
-   IWineD3DSurface IWineD3DSurface parts follow
-   ****************************************************** */
-
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetContainer(IWineD3DSurface* iface, REFIID riid, void** ppContainer) {
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-    IWineD3DBase *container = 0;
-
-    TRACE("(This %p, riid %s, ppContainer %p)\n", This, debugstr_guid(riid), ppContainer);
-
-    if (!ppContainer) {
-        ERR("Called without a valid ppContainer.\n");
-    }
-
-    /* Standalone surfaces return the device as container. */
-    if (This->container) container = This->container;
-    else container = (IWineD3DBase *)This->resource.device;
+void * WINAPI IWineD3DBaseSurfaceImpl_GetParent(IWineD3DSurface *iface)
+{
+    TRACE("iface %p.\n", iface);
 
-    TRACE("Relaying to QueryInterface\n");
-    return IUnknown_QueryInterface(container, riid, ppContainer);
+    return ((IWineD3DSurfaceImpl *)iface)->resource.parent;
 }
 
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetDesc(IWineD3DSurface *iface, WINED3DSURFACE_DESC *pDesc) {
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-
-    TRACE("(%p) : copying into %p\n", This, pDesc);
-
-    pDesc->format = This->resource.format_desc->format;
-    pDesc->resource_type = This->resource.resourceType;
-    pDesc->usage = This->resource.usage;
-    pDesc->pool = This->resource.pool;
-    pDesc->size = This->resource.size; /* dx8 only */
-    pDesc->multisample_type = This->currentDesc.MultiSampleType;
-    pDesc->multisample_quality = This->currentDesc.MultiSampleQuality;
-    pDesc->width = This->currentDesc.Width;
-    pDesc->height = This->currentDesc.Height;
-
-    return WINED3D_OK;
+void WINAPI IWineD3DBaseSurfaceImpl_GetDesc(IWineD3DSurface *iface, WINED3DSURFACE_DESC *desc)
+{
+    IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)iface;
+
+    TRACE("iface %p, desc %p.\n", iface, desc);
+
+    desc->format = surface->resource.format->id;
+    desc->resource_type = surface->resource.resourceType;
+    desc->usage = surface->resource.usage;
+    desc->pool = surface->resource.pool;
+    desc->size = surface->resource.size; /* dx8 only */
+    desc->multisample_type = surface->currentDesc.MultiSampleType;
+    desc->multisample_quality = surface->currentDesc.MultiSampleQuality;
+    desc->width = surface->currentDesc.Width;
+    desc->height = surface->currentDesc.Height;
 }
 
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetBltStatus(IWineD3DSurface *iface, DWORD Flags)
@@ -240,16 +219,16 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetPalette(IWineD3DSurface *iface, IWineD
         return WINED3D_OK;
     }
 
-    if(This->palette != NULL)
-        if(This->resource.usage & WINED3DUSAGE_RENDERTARGET)
+    if (This->palette)
+        if (This->resource.usage & WINED3DUSAGE_RENDERTARGET)
             This->palette->Flags &= ~WINEDDPCAPS_PRIMARYSURFACE;
 
     This->palette = PalImpl;
 
-    if(PalImpl != NULL) {
-        if(This->resource.usage & WINED3DUSAGE_RENDERTARGET) {
-            (PalImpl)->Flags |= WINEDDPCAPS_PRIMARYSURFACE;
-        }
+    if (PalImpl)
+    {
+        if (This->resource.usage & WINED3DUSAGE_RENDERTARGET)
+            PalImpl->Flags |= WINEDDPCAPS_PRIMARYSURFACE;
 
         return IWineD3DSurface_RealizePalette(iface);
     }
@@ -261,7 +240,8 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetColorKey(IWineD3DSurface *iface, DWORD
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
     TRACE("(%p)->(%08x,%p)\n", This, Flags, CKey);
 
-    if ((Flags & WINEDDCKEY_COLORSPACE) != 0) {
+    if (Flags & WINEDDCKEY_COLORSPACE)
+    {
         FIXME(" colorkey value not supported (%08x) !\n", Flags);
         return WINED3DERR_INVALIDCALL;
     }
@@ -321,23 +301,24 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetPalette(IWineD3DSurface *iface, IWineD
     return WINED3D_OK;
 }
 
-DWORD WINAPI IWineD3DBaseSurfaceImpl_GetPitch(IWineD3DSurface *iface) {
+DWORD WINAPI IWineD3DBaseSurfaceImpl_GetPitch(IWineD3DSurface *iface)
+{
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
-    const struct wined3d_format_desc *format_desc = This->resource.format_desc;
+    const struct wined3d_format *format = This->resource.format;
     DWORD ret;
     TRACE("(%p)\n", This);
 
-    if (format_desc->Flags & WINED3DFMT_FLAG_COMPRESSED)
+    if ((format->Flags & (WINED3DFMT_FLAG_COMPRESSED | WINED3DFMT_FLAG_BROKEN_PITCH)) == WINED3DFMT_FLAG_COMPRESSED)
     {
         /* Since compressed formats are block based, pitch means the amount of
          * bytes to the next row of block rather than the next row of pixels. */
-        UINT row_block_count = (This->currentDesc.Width + format_desc->block_width - 1) / format_desc->block_width;
-        ret = row_block_count * format_desc->block_byte_count;
+        UINT row_block_count = (This->currentDesc.Width + format->block_width - 1) / format->block_width;
+        ret = row_block_count * format->block_byte_count;
     }
     else
     {
         unsigned char alignment = This->resource.device->surface_alignment;
-        ret = This->resource.format_desc->byte_count * This->currentDesc.Width;  /* Bytes / row */
+        ret = This->resource.format->byte_count * This->currentDesc.Width;  /* Bytes / row */
         ret = (ret + alignment - 1) & ~(alignment - 1);
     }
     TRACE("(%p) Returning %d\n", This, ret);
@@ -379,7 +360,9 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetOverlayPosition(IWineD3DSurface *iface
         TRACE("(%p): Not an overlay surface\n", This);
         return WINEDDERR_NOTAOVERLAYSURFACE;
     }
-    if(This->overlay_dest == NULL) {
+
+    if (!This->overlay_dest)
+    {
         *X = 0; *Y = 0;
         hr = WINEDDERR_OVERLAYNOTVISIBLE;
     } else {
@@ -484,47 +467,35 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetClipper(IWineD3DSurface *iface, IWineD
     return WINED3D_OK;
 }
 
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetContainer(IWineD3DSurface *iface, IWineD3DBase *container) {
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-
-    TRACE("This %p, container %p\n", This, container);
-
-    /* We can't keep a reference to the container, since the container already keeps a reference to us. */
-
-    TRACE("Setting container to %p from %p\n", container, This->container);
-    This->container = container;
-
-    return WINED3D_OK;
-}
-
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetFormat(IWineD3DSurface *iface, WINED3DFORMAT format) {
+HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetFormat(IWineD3DSurface *iface, enum wined3d_format_id format_id)
+{
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(format,
-            &This->resource.device->adapter->gl_info);
+    const struct wined3d_format *format = wined3d_get_format(&This->resource.device->adapter->gl_info, format_id);
 
-    if (This->resource.format_desc->format != WINED3DFMT_UNKNOWN)
+    if (This->resource.format->id != WINED3DFMT_UNKNOWN)
     {
         FIXME("(%p) : The format of the surface must be WINED3DFORMAT_UNKNOWN\n", This);
         return WINED3DERR_INVALIDCALL;
     }
 
-    TRACE("(%p) : Setting texture format to (%d,%s)\n", This, format, debug_d3dformat(format));
+    TRACE("(%p) : Setting texture format to %s (%#x).\n", This, debug_d3dformat(format_id), format_id);
 
-    This->resource.size = surface_calculate_size(format_desc, This->resource.device->surface_alignment,
+    This->resource.size = wined3d_format_calculate_size(format, This->resource.device->surface_alignment,
             This->pow2Width, This->pow2Height);
 
-    This->Flags |= (WINED3DFMT_D16_LOCKABLE == format) ? SFLAG_LOCKABLE : 0;
+    This->Flags |= (WINED3DFMT_D16_LOCKABLE == format_id) ? SFLAG_LOCKABLE : 0;
 
-    This->resource.format_desc = format_desc;
+    This->resource.format = format;
 
-    TRACE("(%p) : Size %d, bytesPerPixel %d\n", This, This->resource.size, format_desc->byte_count);
+    TRACE("(%p) : Size %d, bytesPerPixel %d\n", This, This->resource.size, format->byte_count);
 
     return WINED3D_OK;
 }
 
-HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) {
+HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface)
+{
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-    const struct wined3d_format_desc *format_desc = This->resource.format_desc;
+    const struct wined3d_format *format = This->resource.format;
     int extraline = 0;
     SYSTEM_INFO sysInfo;
     BITMAPINFO* b_info;
@@ -532,13 +503,13 @@ HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) {
     DWORD *masks;
     UINT usage;
 
-    if(!(format_desc->Flags & WINED3DFMT_FLAG_GETDC))
+    if (!(format->Flags & WINED3DFMT_FLAG_GETDC))
     {
-        WARN("Cannot use GetDC on a %s surface\n", debug_d3dformat(format_desc->format));
+        WARN("Cannot use GetDC on a %s surface\n", debug_d3dformat(format->id));
         return WINED3DERR_INVALIDCALL;
     }
 
-    switch (format_desc->byte_count)
+    switch (format->byte_count)
     {
         case 2:
         case 4:
@@ -553,7 +524,7 @@ HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) {
         default:
             /* Allocate extra space for a palette. */
             b_info = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
-                    sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * (1 << (format_desc->byte_count * 8)));
+                    sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * (1 << (format->byte_count * 8)));
             break;
     }
 
@@ -573,11 +544,11 @@ HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) {
 
     b_info->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
     /* TODO: Is there a nicer way to force a specific alignment? (8 byte for ddraw) */
-    b_info->bmiHeader.biWidth = IWineD3DSurface_GetPitch(iface) / format_desc->byte_count;
+    b_info->bmiHeader.biWidth = IWineD3DSurface_GetPitch(iface) / format->byte_count;
     b_info->bmiHeader.biHeight = -This->currentDesc.Height -extraline;
     b_info->bmiHeader.biSizeImage = ( This->currentDesc.Height + extraline) * IWineD3DSurface_GetPitch(iface);
     b_info->bmiHeader.biPlanes = 1;
-    b_info->bmiHeader.biBitCount = format_desc->byte_count * 8;
+    b_info->bmiHeader.biBitCount = format->byte_count * 8;
 
     b_info->bmiHeader.biXPelsPerMeter = 0;
     b_info->bmiHeader.biYPelsPerMeter = 0;
@@ -586,7 +557,7 @@ HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) {
 
     /* Get the bit masks */
     masks = (DWORD *)b_info->bmiColors;
-    switch (This->resource.format_desc->format)
+    switch (This->resource.format->id)
     {
         case WINED3DFMT_B8G8R8_UNORM:
             usage = DIB_RGB_COLORS;
@@ -607,9 +578,9 @@ HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) {
         case WINED3DFMT_R16G16B16A16_UNORM:
             usage = 0;
             b_info->bmiHeader.biCompression = BI_BITFIELDS;
-            masks[0] = format_desc->red_mask;
-            masks[1] = format_desc->green_mask;
-            masks[2] = format_desc->blue_mask;
+            masks[0] = format->red_mask;
+            masks[1] = format->green_mask;
+            masks[2] = format->blue_mask;
             break;
 
         default:
@@ -619,8 +590,8 @@ HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) {
             break;
     }
 
-    ddc = GetDC(0);
-    if (ddc == 0) {
+    if (!(ddc = GetDC(0)))
+    {
         HeapFree(GetProcessHeap(), 0, b_info);
         return HRESULT_FROM_WIN32(GetLastError());
     }
@@ -788,8 +759,9 @@ static void convert_yuy2_x8r8g8b8(const BYTE *src, BYTE *dst,
     }
 }
 
-struct d3dfmt_convertor_desc {
-    WINED3DFORMAT from, to;
+struct d3dfmt_convertor_desc
+{
+    enum wined3d_format_id from, to;
     void (*convert)(const BYTE *src, BYTE *dst, DWORD pitch_in, DWORD pitch_out, unsigned int w, unsigned int h);
 };
 
@@ -801,7 +773,7 @@ static const struct d3dfmt_convertor_desc convertors[] =
     {WINED3DFMT_YUY2,           WINED3DFMT_B8G8R8X8_UNORM,  convert_yuy2_x8r8g8b8},
 };
 
-static inline const struct d3dfmt_convertor_desc *find_convertor(WINED3DFORMAT from, WINED3DFORMAT to)
+static inline const struct d3dfmt_convertor_desc *find_convertor(enum wined3d_format_id from, enum wined3d_format_id to)
 {
     unsigned int i;
     for(i = 0; i < (sizeof(convertors) / sizeof(convertors[0])); i++) {
@@ -823,24 +795,26 @@ static inline const struct d3dfmt_convertor_desc *find_convertor(WINED3DFORMAT f
  *  fmt: Requested destination format
  *
  *****************************************************************************/
-static IWineD3DSurfaceImpl *surface_convert_format(IWineD3DSurfaceImpl *source, WINED3DFORMAT to_fmt) {
+static IWineD3DSurfaceImpl *surface_convert_format(IWineD3DSurfaceImpl *source, enum wined3d_format_id to_fmt)
+{
     IWineD3DSurface *ret = NULL;
     const struct d3dfmt_convertor_desc *conv;
     WINED3DLOCKED_RECT lock_src, lock_dst;
     HRESULT hr;
 
-    conv = find_convertor(source->resource.format_desc->format, to_fmt);
-    if(!conv) {
-        FIXME("Cannot find a conversion function from format %s to %s\n",
-              debug_d3dformat(source->resource.format_desc->format), debug_d3dformat(to_fmt));
+    conv = find_convertor(source->resource.format->id, to_fmt);
+    if (!conv)
+    {
+        FIXME("Cannot find a conversion function from format %s to %s.\n",
+                debug_d3dformat(source->resource.format->id), debug_d3dformat(to_fmt));
         return NULL;
     }
 
     IWineD3DDevice_CreateSurface((IWineD3DDevice *)source->resource.device, source->currentDesc.Width,
-            source->currentDesc.Height, to_fmt, TRUE /* lockable */, TRUE /* discard  */, 0 /* level */, &ret,
+            source->currentDesc.Height, to_fmt, TRUE /* lockable */, TRUE /* discard  */, 0 /* level */,
             0 /* usage */, WINED3DPOOL_SCRATCH, WINED3DMULTISAMPLE_NONE /* TODO: Multisampled conversion */,
             0 /* MultiSampleQuality */, IWineD3DSurface_GetImplType((IWineD3DSurface *) source),
-            NULL /* parent */, &wined3d_null_parent_ops);
+            NULL /* parent */, &wined3d_null_parent_ops, &ret);
     if(!ret) {
         ERR("Failed to create a destination surface for conversion\n");
         return NULL;
@@ -944,42 +918,28 @@ static HRESULT
  *
  * Params:
  *  DestRect: Destination rectangle to write to
- *  SrcSurface: Source surface, can be NULL
+ *  src_surface: Source surface, can be NULL
  *  SrcRect: Source rectangle
  *****************************************************************************/
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *DestRect, IWineD3DSurface *SrcSurface,
+HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *DestRect, IWineD3DSurface *src_surface,
         const RECT *SrcRect, DWORD Flags, const WINEDDBLTFX *DDBltFx, WINED3DTEXTUREFILTERTYPE Filter)
 {
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
-    IWineD3DSurfaceImpl *Src = (IWineD3DSurfaceImpl *) SrcSurface;
+    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
+    IWineD3DSurfaceImpl *src = (IWineD3DSurfaceImpl *)src_surface;
     RECT        xdst,xsrc;
     HRESULT     ret = WINED3D_OK;
     WINED3DLOCKED_RECT  dlock, slock;
     int bpp, srcheight, srcwidth, dstheight, dstwidth, width;
-    const struct wined3d_format_desc *sEntry, *dEntry;
+    const struct wined3d_format *sEntry, *dEntry;
     int x, y;
     const BYTE *sbuf;
     BYTE *dbuf;
-    TRACE("(%p)->(%p,%p,%p,%x,%p)\n", This, DestRect, Src, SrcRect, Flags, DDBltFx);
 
-    if (TRACE_ON(d3d_surface))
-    {
-        if (DestRect) TRACE("\tdestrect :%dx%d-%dx%d\n",
-            DestRect->left, DestRect->top, DestRect->right, DestRect->bottom);
-        if (SrcRect) TRACE("\tsrcrect  :%dx%d-%dx%d\n",
-            SrcRect->left, SrcRect->top, SrcRect->right, SrcRect->bottom);
-#if 0
-        TRACE("\tflags: ");
-                      DDRAW_dump_DDBLT(Flags);
-                      if (Flags & WINEDDBLT_DDFX)
-              {
-                      TRACE("\tblitfx: ");
-                      DDRAW_dump_DDBLTFX(DDBltFx->dwDDFX);
-    }
-#endif
-    }
-
-    if ( (This->Flags & SFLAG_LOCKED) || ((Src != NULL) && (Src->Flags & SFLAG_LOCKED)))
+    TRACE("iface %p, dst_rect %s, src_surface %p, src_rect %s, flags %#x, fx %p, filter %s.\n",
+            iface, wine_dbgstr_rect(DestRect), src_surface, wine_dbgstr_rect(SrcRect),
+            Flags, DDBltFx, debug_d3dtexturefiltertype(Filter));
+
+    if ((This->Flags & SFLAG_LOCKED) || (src && (src->Flags & SFLAG_LOCKED)))
     {
         WARN(" Surface is busy, returning DDERR_SURFACEBUSY\n");
         return WINEDDERR_SURFACEBUSY;
@@ -995,21 +955,21 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
 
     if (SrcRect)
     {
-        if (Src)
+        if (src)
         {
             if (SrcRect->right < SrcRect->left || SrcRect->bottom < SrcRect->top
-                    || SrcRect->left > Src->currentDesc.Width || SrcRect->left < 0
-                    || SrcRect->top > Src->currentDesc.Height || SrcRect->top < 0
-                    || SrcRect->right > Src->currentDesc.Width || SrcRect->right < 0
-                    || SrcRect->bottom > Src->currentDesc.Height || SrcRect->bottom < 0)
+                    || SrcRect->left > src->currentDesc.Width || SrcRect->left < 0
+                    || SrcRect->top > src->currentDesc.Height || SrcRect->top < 0
+                    || SrcRect->right > src->currentDesc.Width || SrcRect->right < 0
+                    || SrcRect->bottom > src->currentDesc.Height || SrcRect->bottom < 0)
             {
                 WARN("Application gave us bad source rectangle for Blt.\n");
                 return WINEDDERR_INVALIDRECT;
             }
 
             if (!SrcRect->right || !SrcRect->bottom
-                    || SrcRect->left == (int)Src->currentDesc.Width
-                    || SrcRect->top == (int)Src->currentDesc.Height)
+                    || SrcRect->left == (int)src->currentDesc.Width
+                    || SrcRect->top == (int)src->currentDesc.Height)
             {
                 TRACE("Nothing to be done.\n");
                 return WINED3D_OK;
@@ -1018,12 +978,12 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
 
         xsrc = *SrcRect;
     }
-    else if (Src)
+    else if (src)
     {
         xsrc.left = 0;
         xsrc.top = 0;
-        xsrc.right = Src->currentDesc.Width;
-        xsrc.bottom = Src->currentDesc.Height;
+        xsrc.right = src->currentDesc.Width;
+        xsrc.bottom = src->currentDesc.Height;
     }
     else
     {
@@ -1052,7 +1012,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
             return WINED3D_OK;
         }
 
-        if (!Src)
+        if (!src)
         {
             RECT full_rect;
 
@@ -1114,8 +1074,8 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
                         || (xdst.left >= (int)This->currentDesc.Width)
                         || (xdst.top >= (int)This->currentDesc.Height)
                         || (xsrc.right <= 0) || (xsrc.bottom <= 0)
-                        || (xsrc.left >= (int) Src->currentDesc.Width)
-                        || (xsrc.top >= (int)Src->currentDesc.Height))
+                        || (xsrc.left >= (int)src->currentDesc.Width)
+                        || (xsrc.top >= (int)src->currentDesc.Height))
                 {
                     TRACE("Nothing to be done after clipping.\n");
                     return WINED3D_OK;
@@ -1131,29 +1091,30 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
         xdst.bottom = This->currentDesc.Height;
     }
 
-    if (Src == This)
+    if (src == This)
     {
         IWineD3DSurface_LockRect(iface, &dlock, NULL, 0);
         slock = dlock;
-        sEntry = This->resource.format_desc;
+        sEntry = This->resource.format;
         dEntry = sEntry;
     }
     else
     {
-        dEntry = This->resource.format_desc;
-        if (Src)
+        dEntry = This->resource.format;
+        if (src)
         {
-            if (This->resource.format_desc->format != Src->resource.format_desc->format)
+            if (This->resource.format->id != src->resource.format->id)
             {
-                Src = surface_convert_format(Src, dEntry->format);
-                if(!Src) {
+                src = surface_convert_format(src, dEntry->id);
+                if (!src)
+                {
                     /* The conv function writes a FIXME */
                     WARN("Cannot convert source surface format to dest format\n");
                     goto release;
                 }
             }
-            IWineD3DSurface_LockRect((IWineD3DSurface *) Src, &slock, NULL, WINED3DLOCK_READONLY);
-            sEntry = Src->resource.format_desc;
+            IWineD3DSurface_LockRect((IWineD3DSurface *)src, &slock, NULL, WINED3DLOCK_READONLY);
+            sEntry = src->resource.format;
         }
         else
         {
@@ -1169,21 +1130,21 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
 
     if (sEntry->Flags & dEntry->Flags & WINED3DFMT_FLAG_FOURCC)
     {
-        if (!DestRect || Src == This)
+        if (!DestRect || src == This)
         {
             memcpy(dlock.pBits, slock.pBits, This->resource.size);
             goto release;
         }
     }
 
-    bpp = This->resource.format_desc->byte_count;
+    bpp = This->resource.format->byte_count;
     srcheight = xsrc.bottom - xsrc.top;
     srcwidth = xsrc.right - xsrc.left;
     dstheight = xdst.bottom - xdst.top;
     dstwidth = xdst.right - xdst.left;
     width = (xdst.right - xdst.left) * bpp;
 
-    if (DestRect && Src != This)
+    if (DestRect && src != This)
         dbuf = dlock.pBits;
     else
         dbuf = (BYTE*)dlock.pBits+(xdst.top*dlock.Pitch)+(xdst.left*bpp);
@@ -1248,7 +1209,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
         FIXME("\tDdraw Raster Ops: %08x  Pattern: %p\n", DDBltFx->dwDDROP, DDBltFx->u5.lpDDSPattern);
     }
     /* Now the 'with source' blits */
-    if (Src)
+    if (src)
     {
         const BYTE *sbase;
         int sx, xinc, sy, yinc;
@@ -1271,7 +1232,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
                     sbuf = sbase;
 
                     /* check for overlapping surfaces */
-                    if (Src != This || xdst.top < xsrc.top ||
+                    if (src != This || xdst.top < xsrc.top ||
                         xdst.right <= xsrc.left || xsrc.right <= xdst.left)
                     {
                         /* no overlap, or dst above src, so copy from top downwards */
@@ -1379,8 +1340,8 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
                 /* The color keying flags are checked for correctness in ddraw */
                 if (Flags & WINEDDBLT_KEYSRC)
                 {
-                    keylow  = Src->SrcBltCKey.dwColorSpaceLowValue;
-                    keyhigh = Src->SrcBltCKey.dwColorSpaceHighValue;
+                    keylow  = src->SrcBltCKey.dwColorSpaceLowValue;
+                    keyhigh = src->SrcBltCKey.dwColorSpaceHighValue;
                 }
                 else  if (Flags & WINEDDBLT_KEYSRCOVERRIDE)
                 {
@@ -1391,8 +1352,8 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
                 if (Flags & WINEDDBLT_KEYDEST)
                 {
                     /* Destination color keys are taken from the source surface ! */
-                    destkeylow  = Src->DestBltCKey.dwColorSpaceLowValue;
-                    destkeyhigh = Src->DestBltCKey.dwColorSpaceHighValue;
+                    destkeylow  = src->DestBltCKey.dwColorSpaceLowValue;
+                    destkeyhigh = src->DestBltCKey.dwColorSpaceHighValue;
                 }
                 else if (Flags & WINEDDBLT_KEYDESTOVERRIDE)
                 {
@@ -1563,9 +1524,9 @@ error:
 
 release:
     IWineD3DSurface_UnlockRect(iface);
-    if (Src && Src != This) IWineD3DSurface_UnlockRect((IWineD3DSurface *) Src);
+    if (src && src != This) IWineD3DSurface_UnlockRect((IWineD3DSurface *)src);
     /* Release the converted surface if any */
-    if (Src && SrcSurface != (IWineD3DSurface *) Src) IWineD3DSurface_Release((IWineD3DSurface *) Src);
+    if (src && src_surface != (IWineD3DSurface *)src) IWineD3DSurface_Release((IWineD3DSurface *)src);
     return ret;
 }
 
@@ -1579,7 +1540,7 @@ release:
  * Params:
  *  dstx:
  *  dsty:
- *  Source: Source surface to copy from
+ *  src_surface: Source surface to copy from
  *  rsrc: Source rectangle
  *  trans: Some Flags
  *
@@ -1588,10 +1549,10 @@ release:
  *
  *****************************************************************************/
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dstx, DWORD dsty,
-        IWineD3DSurface *Source, const RECT *rsrc, DWORD trans)
+        IWineD3DSurface *src_surface, const RECT *rsrc, DWORD trans)
 {
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
-    IWineD3DSurfaceImpl *Src = (IWineD3DSurfaceImpl *) Source;
+    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
+    IWineD3DSurfaceImpl *src = (IWineD3DSurfaceImpl *)src_surface;
 
     int                 bpp, w, h, x, y;
     WINED3DLOCKED_RECT  dlock,slock;
@@ -1600,25 +1561,12 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
     RECT                lock_src, lock_dst, lock_union;
     const BYTE          *sbuf;
     BYTE                *dbuf;
-    const struct wined3d_format_desc *sEntry, *dEntry;
+    const struct wined3d_format *sEntry, *dEntry;
 
-    if (TRACE_ON(d3d_surface))
-    {
-        TRACE("(%p)->(%d,%d,%p,%p,%08x)\n", This,dstx,dsty,Src,rsrc,trans);
+    TRACE("iface %p, dst_x %u, dst_y %u, src_surface %p, src_rect %s, flags %#x.\n",
+            iface, dstx, dsty, src_surface, wine_dbgstr_rect(rsrc), trans);
 
-        if (rsrc)
-        {
-            TRACE("\tsrcrect: %dx%d-%dx%d\n",rsrc->left,rsrc->top,
-                  rsrc->right,rsrc->bottom);
-        }
-        else
-        {
-            TRACE(" srcrect: NULL\n");
-        }
-    }
-
-    if ((This->Flags & SFLAG_LOCKED) ||
-            (Src->Flags & SFLAG_LOCKED))
+    if ((This->Flags & SFLAG_LOCKED) || (src->Flags & SFLAG_LOCKED))
     {
         WARN(" Surface is busy, returning DDERR_SURFACEBUSY\n");
         return WINEDDERR_SURFACEBUSY;
@@ -1629,17 +1577,17 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
         WARN("rsrc is NULL!\n");
         rsrc2.left = 0;
         rsrc2.top = 0;
-        rsrc2.right = Src->currentDesc.Width;
-        rsrc2.bottom = Src->currentDesc.Height;
+        rsrc2.right = src->currentDesc.Width;
+        rsrc2.bottom = src->currentDesc.Height;
         rsrc = &rsrc2;
     }
 
     /* Check source rect for validity. Copied from normal Blt. Fixes Baldur's Gate.*/
-    if ((rsrc->bottom > Src->currentDesc.Height) || (rsrc->bottom < 0) ||
-         (rsrc->top    > Src->currentDesc.Height) || (rsrc->top    < 0) ||
-         (rsrc->left   > Src->currentDesc.Width)  || (rsrc->left   < 0) ||
-         (rsrc->right  > Src->currentDesc.Width)  || (rsrc->right  < 0) ||
-         (rsrc->right  < rsrc->left)              || (rsrc->bottom < rsrc->top))
+    if ((rsrc->bottom > src->currentDesc.Height) || (rsrc->bottom < 0)
+            || (rsrc->top   > src->currentDesc.Height) || (rsrc->top    < 0)
+            || (rsrc->left  > src->currentDesc.Width)  || (rsrc->left   < 0)
+            || (rsrc->right > src->currentDesc.Width)  || (rsrc->right  < 0)
+            || (rsrc->right < rsrc->left)              || (rsrc->bottom < rsrc->top))
     {
         WARN("Application gave us bad source rectangle for BltFast.\n");
         return WINEDDERR_INVALIDRECT;
@@ -1647,12 +1595,12 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
 
     h = rsrc->bottom - rsrc->top;
     if (h > This->currentDesc.Height-dsty) h = This->currentDesc.Height-dsty;
-    if (h > Src->currentDesc.Height-rsrc->top) h=Src->currentDesc.Height-rsrc->top;
+    if (h > src->currentDesc.Height-rsrc->top) h = src->currentDesc.Height-rsrc->top;
     if (h <= 0) return WINEDDERR_INVALIDRECT;
 
     w = rsrc->right - rsrc->left;
     if (w > This->currentDesc.Width-dstx) w = This->currentDesc.Width-dstx;
-    if (w > Src->currentDesc.Width-rsrc->left) w = Src->currentDesc.Width-rsrc->left;
+    if (w > src->currentDesc.Width-rsrc->left) w = src->currentDesc.Width-rsrc->left;
     if (w <= 0) return WINEDDERR_INVALIDRECT;
 
     /* Now compute the locking rectangle... */
@@ -1666,10 +1614,10 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
     lock_dst.right = dstx + w;
     lock_dst.bottom = dsty + h;
 
-    bpp = This->resource.format_desc->byte_count;
+    bpp = This->resource.format->byte_count;
 
     /* We need to lock the surfaces, or we won't get refreshes when done. */
-    if (Src == This)
+    if (src == This)
     {
         int pitch;
 
@@ -1685,12 +1633,12 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
         /* Since slock was originally copied from this surface's description, we can just reuse it */
         sbuf = This->resource.allocatedMemory + lock_src.top * pitch + lock_src.left * bpp;
         dbuf = This->resource.allocatedMemory + lock_dst.top * pitch + lock_dst.left * bpp;
-        sEntry = Src->resource.format_desc;
+        sEntry = src->resource.format;
         dEntry = sEntry;
     }
     else
     {
-        ret = IWineD3DSurface_LockRect(Source, &slock, &lock_src, WINED3DLOCK_READONLY);
+        ret = IWineD3DSurface_LockRect(src_surface, &slock, &lock_src, WINED3DLOCK_READONLY);
         if(ret != WINED3D_OK) goto error;
         ret = IWineD3DSurface_LockRect(iface, &dlock, &lock_dst, 0);
         if(ret != WINED3D_OK) goto error;
@@ -1699,8 +1647,8 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
         dbuf = dlock.pBits;
         TRACE("Dst is at %p, Src is at %p\n", dbuf, sbuf);
 
-        sEntry = Src->resource.format_desc;
-        dEntry = This->resource.format_desc;
+        sEntry = src->resource.format;
+        dEntry = This->resource.format;
     }
 
     /* Handle compressed surfaces first... */
@@ -1713,7 +1661,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
             FIXME("trans arg not supported when a compressed surface is involved\n");
         if (dstx || dsty)
             FIXME("offset for destination surface is not supported\n");
-        if (Src->resource.format_desc->format != This->resource.format_desc->format)
+        if (src->resource.format->id != This->resource.format->id)
         {
             FIXME("compressed -> compressed copy only supported for the same type of surface\n");
             ret = WINED3DERR_WRONGTEXTUREFORMAT;
@@ -1742,9 +1690,9 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
     if (trans & (WINEDDBLTFAST_SRCCOLORKEY | WINEDDBLTFAST_DESTCOLORKEY))
     {
         DWORD keylow, keyhigh;
-        DWORD mask = Src->resource.format_desc->red_mask |
-                     Src->resource.format_desc->green_mask |
-                     Src->resource.format_desc->blue_mask;
+        DWORD mask = src->resource.format->red_mask
+                | src->resource.format->green_mask
+                | src->resource.format->blue_mask;
 
         /* For some 8-bit formats like L8 and P8 color masks don't make sense */
         if(!mask && bpp==1)
@@ -1753,8 +1701,8 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
         TRACE("Color keyed copy\n");
         if (trans & WINEDDBLTFAST_SRCCOLORKEY)
         {
-            keylow  = Src->SrcBltCKey.dwColorSpaceLowValue;
-            keyhigh = Src->SrcBltCKey.dwColorSpaceHighValue;
+            keylow  = src->SrcBltCKey.dwColorSpaceLowValue;
+            keyhigh = src->SrcBltCKey.dwColorSpaceHighValue;
         }
         else
         {
@@ -1845,14 +1793,14 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
     }
 
 error:
-    if (Src == This)
+    if (src == This)
     {
         IWineD3DSurface_UnlockRect(iface);
     }
     else
     {
         IWineD3DSurface_UnlockRect(iface);
-        IWineD3DSurface_UnlockRect(Source);
+        IWineD3DSurface_UnlockRect(src_surface);
     }
 
     return ret;
@@ -1867,7 +1815,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_LockRect(IWineD3DSurface *iface, WINED3DL
 
     pLockedRect->Pitch = IWineD3DSurface_GetPitch(iface);
 
-    if (NULL == pRect)
+    if (!pRect)
     {
         pLockedRect->pBits = This->resource.allocatedMemory;
         This->lockedRect.left   = 0;
@@ -1881,24 +1829,24 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_LockRect(IWineD3DSurface *iface, WINED3DL
     }
     else
     {
-        const struct wined3d_format_desc *format_desc = This->resource.format_desc;
+        const struct wined3d_format *format = This->resource.format;
 
         TRACE("Lock Rect (%p) = l %d, t %d, r %d, b %d\n",
               pRect, pRect->left, pRect->top, pRect->right, pRect->bottom);
 
-        if (format_desc->Flags & WINED3DFMT_FLAG_COMPRESSED)
+        if ((format->Flags & (WINED3DFMT_FLAG_COMPRESSED | WINED3DFMT_FLAG_BROKEN_PITCH)) == WINED3DFMT_FLAG_COMPRESSED)
         {
             /* Compressed textures are block based, so calculate the offset of
              * the block that contains the top-left pixel of the locked rectangle. */
             pLockedRect->pBits = This->resource.allocatedMemory
-                    + ((pRect->top / format_desc->block_height) * pLockedRect->Pitch)
-                    + ((pRect->left / format_desc->block_width) * format_desc->block_byte_count);
+                    + ((pRect->top / format->block_height) * pLockedRect->Pitch)
+                    + ((pRect->left / format->block_width) * format->block_byte_count);
         }
         else
         {
             pLockedRect->pBits = This->resource.allocatedMemory +
                     (pLockedRect->Pitch * pRect->top) +
-                    (pRect->left * format_desc->byte_count);
+                    (pRect->left * format->byte_count);
         }
         This->lockedRect.left   = pRect->left;
         This->lockedRect.top    = pRect->top;
@@ -1912,10 +1860,6 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_LockRect(IWineD3DSurface *iface, WINED3DL
     return WINED3D_OK;
 }
 
-void WINAPI IWineD3DBaseSurfaceImpl_BindTexture(IWineD3DSurface *iface, BOOL srgb) {
-    ERR("Should not be called on base texture\n");
-}
-
 /* TODO: think about moving this down to resource? */
 const void *WINAPI IWineD3DBaseSurfaceImpl_GetData(IWineD3DSurface *iface)
 {
index 580c88a..a640b79 100644 (file)
@@ -167,7 +167,6 @@ static HRESULT WINAPI
 IWineGDISurfaceImpl_UnlockRect(IWineD3DSurface *iface)
 {
     IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-    IWineD3DSwapChainImpl *swapchain = NULL;
     TRACE("(%p)\n", This);
 
     if (!(This->Flags & SFLAG_LOCKED))
@@ -176,35 +175,14 @@ IWineGDISurfaceImpl_UnlockRect(IWineD3DSurface *iface)
         return WINEDDERR_NOTLOCKED;
     }
 
-    /* Can be useful for debugging */
-#if 0
-        {
-            static unsigned int gen = 0;
-            char buffer[4096];
-            ++gen;
-            if ((gen % 10) == 0) {
-                snprintf(buffer, sizeof(buffer), "/tmp/surface%p_type%u_level%u_%u.ppm",
-                        This, This->texture_target, This->texture_level, gen);
-                IWineD3DSurfaceImpl_SaveSnapshot(iface, buffer);
-            }
-            /*
-             * debugging crash code
-            if (gen == 250) {
-              void** test = NULL;
-              *test = 0;
-            }
-            */
-        }
-#endif
-
     /* Tell the swapchain to update the screen */
-    if (SUCCEEDED(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DSwapChain, (void **)&swapchain)))
+    if (This->container.type == WINED3D_CONTAINER_SWAPCHAIN)
     {
+        IWineD3DSwapChainImpl *swapchain = This->container.u.swapchain;
         if (This == swapchain->front_buffer)
         {
             x11_copy_to_screen(swapchain, &This->lockedRect);
         }
-        IWineD3DSwapChain_Release((IWineD3DSwapChain *) swapchain);
     }
 
     This->Flags &= ~SFLAG_LOCKED;
@@ -231,18 +209,20 @@ IWineGDISurfaceImpl_Flip(IWineD3DSurface *iface,
                          IWineD3DSurface *override,
                          DWORD Flags)
 {
-    IWineD3DSwapChainImpl *swapchain = NULL;
+    IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)iface;
+    IWineD3DSwapChainImpl *swapchain;
     HRESULT hr;
 
-    if(FAILED(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DSwapChain, (void **)&swapchain)))
+    if (surface->container.type != WINED3D_CONTAINER_SWAPCHAIN)
     {
         ERR("Flipped surface is not on a swapchain\n");
         return WINEDDERR_NOTFLIPPABLE;
     }
 
+    swapchain = surface->container.u.swapchain;
     hr = IWineD3DSwapChain_Present((IWineD3DSwapChain *)swapchain,
             NULL, NULL, swapchain->win_handle, NULL, 0);
-    IWineD3DSwapChain_Release((IWineD3DSwapChain *) swapchain);
+
     return hr;
 }
 
@@ -262,118 +242,9 @@ IWineGDISurfaceImpl_LoadTexture(IWineD3DSurface *iface, BOOL srgb_mode)
     return WINED3DERR_INVALIDCALL;
 }
 
-/*****************************************************************************
- * IWineD3DSurface::SaveSnapshot, GDI version
- *
- * This method writes the surface's contents to the in tga format to the
- * file specified in filename.
- *
- * Params:
- *  filename: File to write to
- *
- * Returns:
- *  WINED3DERR_INVALIDCALL if the file couldn't be opened
- *  WINED3D_OK on success
- *
- *****************************************************************************/
-static int get_shift(DWORD color_mask) {
-    int shift = 0;
-    while (color_mask > 0xFF) {
-        color_mask >>= 1;
-        shift += 1;
-    }
-    while ((color_mask & 0x80) == 0) {
-        color_mask <<= 1;
-        shift -= 1;
-    }
-    return shift;
-}
-
-
-static HRESULT WINAPI
-IWineGDISurfaceImpl_SaveSnapshot(IWineD3DSurface *iface,
-const char* filename)
+static void WINAPI IWineGDISurfaceImpl_BindTexture(IWineD3DSurface *iface, BOOL srgb)
 {
-    FILE* f = NULL;
-    UINT y = 0, x = 0;
-    IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
-    const struct wined3d_format_desc *format_desc = This->resource.format_desc;
-    static char *output = NULL;
-    static UINT size = 0;
-
-    if (This->pow2Width > size) {
-        output = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, This->pow2Width * 3);
-        size = This->pow2Width;
-    }
-
-
-    f = fopen(filename, "w+");
-    if (NULL == f) {
-        ERR("opening of %s failed with\n", filename);
-        return WINED3DERR_INVALIDCALL;
-    }
-    fprintf(f, "P6\n%d %d\n255\n", This->pow2Width, This->pow2Height);
-
-    if (This->resource.format_desc->format == WINED3DFMT_P8_UINT)
-    {
-        unsigned char table[256][3];
-        int i;
-
-        if (This->palette == NULL) {
-            fclose(f);
-            return WINED3DERR_INVALIDCALL;
-        }
-        for (i = 0; i < 256; i++) {
-            table[i][0] = This->palette->palents[i].peRed;
-            table[i][1] = This->palette->palents[i].peGreen;
-            table[i][2] = This->palette->palents[i].peBlue;
-        }
-        for (y = 0; y < This->pow2Height; y++) {
-            unsigned char *src = This->resource.allocatedMemory + (y * 1 * IWineD3DSurface_GetPitch(iface));
-            for (x = 0; x < This->pow2Width; x++) {
-                unsigned char color = *src;
-                src += 1;
-
-                output[3 * x + 0] = table[color][0];
-                output[3 * x + 1] = table[color][1];
-                output[3 * x + 2] = table[color][2];
-            }
-            fwrite(output, 3 * This->pow2Width, 1, f);
-        }
-    } else {
-        int red_shift, green_shift, blue_shift, pix_width;
-
-        pix_width = format_desc->byte_count;
-
-        red_shift = get_shift(format_desc->red_mask);
-        green_shift = get_shift(format_desc->green_mask);
-        blue_shift = get_shift(format_desc->blue_mask);
-
-        for (y = 0; y < This->pow2Height; y++) {
-            const unsigned char *src = This->resource.allocatedMemory + (y * 1 * IWineD3DSurface_GetPitch(iface));
-            for (x = 0; x < This->pow2Width; x++) {
-                unsigned int color;
-                unsigned int comp;
-                int i;
-
-                color = 0;
-                for (i = 0; i < pix_width; i++) {
-                    color |= src[i] << (8 * i);
-                }
-                src += 1 * pix_width;
-
-                comp = color & format_desc->red_mask;
-                output[3 * x + 0] = red_shift > 0 ? comp >> red_shift : comp << -red_shift;
-                comp = color & format_desc->green_mask;
-                output[3 * x + 1] = green_shift > 0 ? comp >> green_shift : comp << -green_shift;
-                comp = color & format_desc->blue_mask;
-                output[3 * x + 2] = blue_shift > 0 ? comp >> blue_shift : comp << -blue_shift;
-            }
-            fwrite(output, 3 * This->pow2Width, 1, f);
-        }
-    }
-    fclose(f);
-    return WINED3D_OK;
+    ERR("Not supported.\n");
 }
 
 static HRESULT WINAPI IWineGDISurfaceImpl_GetDC(IWineD3DSurface *iface, HDC *pHDC) {
@@ -418,8 +289,8 @@ static HRESULT WINAPI IWineGDISurfaceImpl_GetDC(IWineD3DSurface *iface, HDC *pHD
         return hr;
     }
 
-    if (This->resource.format_desc->format == WINED3DFMT_P8_UINT
-            || This->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM)
+    if (This->resource.format->id == WINED3DFMT_P8_UINT
+            || This->resource.format->id == WINED3DFMT_P8_UINT_A8_UNORM)
     {
         unsigned int n;
         const PALETTEENTRY *pal = NULL;
@@ -479,7 +350,6 @@ static HRESULT WINAPI IWineGDISurfaceImpl_RealizePalette(IWineD3DSurface *iface)
     RGBQUAD col[256];
     IWineD3DPaletteImpl *pal = This->palette;
     unsigned int n;
-    IWineD3DSwapChainImpl *swapchain;
     TRACE("(%p)\n", This);
 
     if (!pal) return WINED3D_OK;
@@ -498,13 +368,13 @@ static HRESULT WINAPI IWineGDISurfaceImpl_RealizePalette(IWineD3DSurface *iface)
     /* Update the image because of the palette change. Some games like e.g Red Alert
        call SetEntries a lot to implement fading. */
     /* Tell the swapchain to update the screen */
-    if (SUCCEEDED(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DSwapChain, (void **)&swapchain)))
+    if (This->container.type == WINED3D_CONTAINER_SWAPCHAIN)
     {
+        IWineD3DSwapChainImpl *swapchain = This->container.u.swapchain;
         if (This == swapchain->front_buffer)
         {
             x11_copy_to_screen(swapchain, NULL);
         }
-        IWineD3DSwapChain_Release((IWineD3DSwapChain *) swapchain);
     }
 
     return WINED3D_OK;
@@ -604,28 +474,6 @@ static HRESULT WINAPI IWineGDISurfaceImpl_SetMem(IWineD3DSurface *iface, void *M
     return WINED3D_OK;
 }
 
-/***************************
- *
- ***************************/
-static void WINAPI IWineGDISurfaceImpl_ModifyLocation(IWineD3DSurface *iface, DWORD flag, BOOL persistent) {
-    TRACE("(%p)->(%s, %s)\n", iface,
-          flag == SFLAG_INSYSMEM ? "SFLAG_INSYSMEM" : flag == SFLAG_INDRAWABLE ? "SFLAG_INDRAWABLE" : "SFLAG_INTEXTURE",
-          persistent ? "TRUE" : "FALSE");
-    /* GDI surfaces can be in system memory only */
-    if(flag != SFLAG_INSYSMEM) {
-        ERR("GDI Surface requested in gl %s memory\n", flag == SFLAG_INDRAWABLE ? "drawable" : "texture");
-    }
-}
-
-static HRESULT WINAPI IWineGDISurfaceImpl_LoadLocation(IWineD3DSurface *iface, DWORD flag, const RECT *rect) {
-    if(flag != SFLAG_INSYSMEM) {
-        ERR("GDI Surface requested to be copied to gl %s\n", flag == SFLAG_INTEXTURE ? "texture" : "drawable");
-    } else {
-        TRACE("Surface requested in surface memory\n");
-    }
-    return WINED3D_OK;
-}
-
 static WINED3DSURFTYPE WINAPI IWineGDISurfaceImpl_GetImplType(IWineD3DSurface *iface) {
     return SURFACE_GDI;
 }
@@ -655,7 +503,6 @@ const IWineD3DSurfaceVtbl IWineGDISurface_Vtbl =
     IWineGDISurfaceImpl_UnLoad,
     IWineD3DBaseSurfaceImpl_GetType,
     /* IWineD3DSurface */
-    IWineD3DBaseSurfaceImpl_GetContainer,
     IWineD3DBaseSurfaceImpl_GetDesc,
     IWineGDISurfaceImpl_LockRect,
     IWineGDISurfaceImpl_UnlockRect,
@@ -682,14 +529,10 @@ const IWineD3DSurfaceVtbl IWineGDISurface_Vtbl =
     IWineD3DBaseSurfaceImpl_GetClipper,
     /* Internal use: */
     IWineGDISurfaceImpl_LoadTexture,
-    IWineD3DBaseSurfaceImpl_BindTexture,
-    IWineGDISurfaceImpl_SaveSnapshot,
-    IWineD3DBaseSurfaceImpl_SetContainer,
+    IWineGDISurfaceImpl_BindTexture,
     IWineD3DBaseSurfaceImpl_GetData,
     IWineD3DBaseSurfaceImpl_SetFormat,
     IWineGDISurfaceImpl_PrivateSetup,
-    IWineGDISurfaceImpl_ModifyLocation,
-    IWineGDISurfaceImpl_LoadLocation,
     IWineGDISurfaceImpl_GetImplType,
     IWineGDISurfaceImpl_DrawOverlay
 };
index b0d591a..35558ad 100644 (file)
@@ -33,7 +33,7 @@
 WINE_DEFAULT_DEBUG_CHANNEL(d3d);
 WINE_DECLARE_DEBUG_CHANNEL(fps);
 
-/*IWineD3DSwapChain parts follow: */
+/* Do not call while under the GL lock. */
 static void WINAPI IWineD3DSwapChainImpl_Destroy(IWineD3DSwapChain *iface)
 {
     IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface;
@@ -48,7 +48,7 @@ static void WINAPI IWineD3DSwapChainImpl_Destroy(IWineD3DSwapChain *iface)
      * the last buffer to be destroyed, FindContext() depends on that. */
     if (This->front_buffer)
     {
-        IWineD3DSurface_SetContainer((IWineD3DSurface *)This->front_buffer, NULL);
+        surface_set_container(This->front_buffer, WINED3D_CONTAINER_NONE, NULL);
         if (IWineD3DSurface_Release((IWineD3DSurface *)This->front_buffer))
         {
             WARN("(%p) Something's still holding the front buffer (%p).\n",
@@ -63,7 +63,7 @@ static void WINAPI IWineD3DSwapChainImpl_Destroy(IWineD3DSwapChain *iface)
 
         while (i--)
         {
-            IWineD3DSurface_SetContainer((IWineD3DSurface *)This->back_buffers[i], NULL);
+            surface_set_container(This->back_buffers[i], WINED3D_CONTAINER_NONE, NULL);
             if (IWineD3DSurface_Release((IWineD3DSurface *)This->back_buffers[i]))
                 WARN("(%p) Something's still holding back buffer %u (%p).\n",
                         This, i, This->back_buffers[i]);
@@ -81,7 +81,8 @@ static void WINAPI IWineD3DSwapChainImpl_Destroy(IWineD3DSwapChain *iface)
      * this will be the original desktop resolution. In case of d3d7 this will be a NOP because ddraw sets the resolution
      * before starting up Direct3D, thus orig_width and orig_height will be equal to the modes in the presentation params
      */
-    if(This->presentParms.Windowed == FALSE && This->presentParms.AutoRestoreDisplayMode) {
+    if (!This->presentParms.Windowed && This->presentParms.AutoRestoreDisplayMode)
+    {
         mode.Width = This->orig_width;
         mode.Height = This->orig_height;
         mode.RefreshRate = 0;
@@ -117,15 +118,21 @@ static void swapchain_blit(IWineD3DSwapChainImpl *This, struct wined3d_context *
     GetClientRect(This->win_handle, &win_rect);
     win_h = win_rect.bottom - win_rect.top;
 
-    if (gl_info->fbo_ops.glBlitFramebuffer && is_identity_fixup(backbuffer->resource.format_desc->color_fixup))
+    if (gl_info->fbo_ops.glBlitFramebuffer && is_identity_fixup(backbuffer->resource.format->color_fixup))
     {
         ENTER_GL();
-        context_apply_fbo_state_blit(context, GL_READ_FRAMEBUFFER, backbuffer, NULL);
+        context_apply_fbo_state_blit(context, GL_READ_FRAMEBUFFER, backbuffer, NULL, SFLAG_INTEXTURE);
         glReadBuffer(GL_COLOR_ATTACHMENT0);
 
         context_bind_fbo(context, GL_DRAW_FRAMEBUFFER, NULL);
         context_set_draw_buffer(context, GL_BACK);
 
+        glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE));
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE1));
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE2));
+        IWineD3DDeviceImpl_MarkStateDirty(device, STATE_RENDER(WINED3DRS_COLORWRITEENABLE3));
+
         glDisable(GL_SCISSOR_TEST);
         IWineD3DDeviceImpl_MarkStateDirty(This->device, STATE_RENDER(WINED3DRS_SCISSORTESTENABLE));
 
@@ -155,11 +162,11 @@ static void swapchain_blit(IWineD3DSwapChainImpl *This, struct wined3d_context *
             tex_bottom /= src_h;
         }
 
-        if (is_complex_fixup(backbuffer->resource.format_desc->color_fixup))
+        if (is_complex_fixup(backbuffer->resource.format->color_fixup))
             gl_filter = GL_NEAREST;
 
         ENTER_GL();
-        context_bind_fbo(context2, GL_DRAW_FRAMEBUFFER, NULL);
+        context_bind_fbo(context2, GL_FRAMEBUFFER, NULL);
 
         /* Set up the texture. The surface is not in a IWineD3D*Texture container,
          * so there are no d3d texture settings to dirtify
@@ -255,7 +262,7 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
         cursor.resource.ref = 1;
         cursor.resource.device = This->device;
         cursor.resource.pool = WINED3DPOOL_SCRATCH;
-        cursor.resource.format_desc = getFormatDescEntry(WINED3DFMT_B8G8R8A8_UNORM, gl_info);
+        cursor.resource.format = wined3d_get_format(gl_info, WINED3DFMT_B8G8R8A8_UNORM);
         cursor.resource.resourceType = WINED3DRTYPE_SURFACE;
         cursor.texture_name = This->device->cursorTexture;
         cursor.texture_target = GL_TEXTURE_2D;
@@ -325,12 +332,9 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
      */
     if (!This->render_to_fbo && render_to_fbo && wined3d_settings.offscreen_rendering_mode == ORM_FBO)
     {
-        IWineD3DSurface_LoadLocation((IWineD3DSurface *)This->back_buffers[0], SFLAG_INTEXTURE, NULL);
-        IWineD3DSurface_ModifyLocation((IWineD3DSurface *)This->back_buffers[0], SFLAG_INDRAWABLE, FALSE);
+        surface_load_location(This->back_buffers[0], SFLAG_INTEXTURE, NULL);
+        surface_modify_location(This->back_buffers[0], SFLAG_INDRAWABLE, FALSE);
         This->render_to_fbo = TRUE;
-
-        /* Force the context manager to update the render target configuration next draw. */
-        context->current_rt = NULL;
     }
 
     if(This->render_to_fbo)
@@ -367,46 +371,6 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
         }
     }
 
-#if defined(FRAME_DEBUGGING)
-{
-    if (GetFileAttributesA("C:\\D3DTRACE") != INVALID_FILE_ATTRIBUTES) {
-        if (!isOn) {
-            isOn = TRUE;
-            FIXME("Enabling D3D Trace\n");
-            __WINE_SET_DEBUGGING(__WINE_DBCL_TRACE, __wine_dbch_d3d, 1);
-#if defined(SHOW_FRAME_MAKEUP)
-            FIXME("Singe Frame snapshots Starting\n");
-            isDumpingFrames = TRUE;
-            ENTER_GL();
-            glClear(GL_COLOR_BUFFER_BIT);
-            LEAVE_GL();
-#endif
-
-#if defined(SINGLE_FRAME_DEBUGGING)
-        } else {
-#if defined(SHOW_FRAME_MAKEUP)
-            FIXME("Singe Frame snapshots Finishing\n");
-            isDumpingFrames = FALSE;
-#endif
-            FIXME("Singe Frame trace complete\n");
-            DeleteFileA("C:\\D3DTRACE");
-            __WINE_SET_DEBUGGING(__WINE_DBCL_TRACE, __wine_dbch_d3d, 0);
-#endif
-        }
-    } else {
-        if (isOn) {
-            isOn = FALSE;
-#if defined(SHOW_FRAME_MAKEUP)
-            FIXME("Single Frame snapshots Finishing\n");
-            isDumpingFrames = FALSE;
-#endif
-            FIXME("Disabling D3D Trace\n");
-            __WINE_SET_DEBUGGING(__WINE_DBCL_TRACE, __wine_dbch_d3d, 0);
-        }
-    }
-}
-#endif
-
     /* This is disabled, but the code left in for debug purposes.
      *
      * Since we're allowed to modify the new back buffer on a D3DSWAPEFFECT_DISCARD flip,
@@ -448,16 +412,18 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
              * This serves to update the emulated overlay, if any
              */
             fbflags = front->Flags;
-            IWineD3DSurface_ModifyLocation((IWineD3DSurface *)front, SFLAG_INDRAWABLE, TRUE);
+            surface_modify_location(front, SFLAG_INDRAWABLE, TRUE);
             front->Flags = fbflags;
-        } else {
-            IWineD3DSurface_ModifyLocation((IWineD3DSurface *) front, SFLAG_INDRAWABLE, TRUE);
-            IWineD3DSurface_ModifyLocation((IWineD3DSurface *) back, SFLAG_INDRAWABLE, TRUE);
+        }
+        else
+        {
+            surface_modify_location(front, SFLAG_INDRAWABLE, TRUE);
+            surface_modify_location(back, SFLAG_INDRAWABLE, TRUE);
         }
     }
     else
     {
-        IWineD3DSurface_ModifyLocation((IWineD3DSurface *)This->front_buffer, SFLAG_INDRAWABLE, TRUE);
+        surface_modify_location(This->front_buffer, SFLAG_INDRAWABLE, TRUE);
         /* If the swapeffect is DISCARD, the back buffer is undefined. That means the SYSMEM
          * and INTEXTURE copies can keep their old content if they have any defined content.
          * If the swapeffect is COPY, the content remains the same. If it is FLIP however,
@@ -465,7 +431,7 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
          */
         if (This->presentParms.SwapEffect == WINED3DSWAPEFFECT_FLIP)
         {
-            IWineD3DSurface_ModifyLocation((IWineD3DSurface *)This->back_buffers[0], SFLAG_INDRAWABLE, TRUE);
+            surface_modify_location(This->back_buffers[0], SFLAG_INDRAWABLE, TRUE);
         }
     }
 
@@ -488,10 +454,8 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
     if (This->presentParms.PresentationInterval != WINED3DPRESENT_INTERVAL_IMMEDIATE
             && gl_info->supported[SGI_VIDEO_SYNC])
     {
-        retval = GL_EXTCALL(glXGetVideoSyncSGI(&sync));
-        if(retval != 0) {
+        if ((retval = GL_EXTCALL(glXGetVideoSyncSGI(&sync))))
             ERR("glXGetVideoSyncSGI failed(retval = %d\n", retval);
-        }
 
         switch(This->presentParms.PresentationInterval) {
             case WINED3DPRESENT_INTERVAL_DEFAULT:
@@ -656,11 +620,12 @@ void swapchain_restore_fullscreen_window(IWineD3DSwapChainImpl *swapchain)
 }
 
 
+/* Do not call while under the GL lock. */
 HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface_type,
-        IWineD3DDeviceImpl *device, WINED3DPRESENT_PARAMETERS *present_parameters, IUnknown *parent)
+        IWineD3DDeviceImpl *device, WINED3DPRESENT_PARAMETERS *present_parameters, void *parent)
 {
     const struct wined3d_adapter *adapter = device->adapter;
-    const struct wined3d_format_desc *format_desc;
+    const struct wined3d_format *format;
     BOOL displaymode_set = FALSE;
     WINED3DDISPLAYMODE mode;
     RECT client_rect;
@@ -714,7 +679,7 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
     swapchain->orig_width = mode.Width;
     swapchain->orig_height = mode.Height;
     swapchain->orig_fmt = mode.Format;
-    format_desc = getFormatDescEntry(mode.Format, &adapter->gl_info);
+    format = wined3d_get_format(&adapter->gl_info, mode.Format);
 
     GetClientRect(window, &client_rect);
     if (present_parameters->Windowed
@@ -766,11 +731,10 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
         goto err;
     }
 
-    IWineD3DSurface_SetContainer((IWineD3DSurface *)swapchain->front_buffer, (IWineD3DBase *)swapchain);
-    swapchain->front_buffer->Flags |= SFLAG_SWAPCHAIN;
+    surface_set_container(swapchain->front_buffer, WINED3D_CONTAINER_SWAPCHAIN, (IWineD3DBase *)swapchain);
     if (surface_type == SURFACE_OPENGL)
     {
-        IWineD3DSurface_ModifyLocation((IWineD3DSurface *)swapchain->front_buffer, SFLAG_INDRAWABLE, TRUE);
+        surface_modify_location(swapchain->front_buffer, SFLAG_INDRAWABLE, TRUE);
     }
 
     /* MSDN says we're only allowed a single fullscreen swapchain per device,
@@ -807,7 +771,7 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
 
     if (surface_type == SURFACE_OPENGL)
     {
-        WINED3DFORMAT formats[] =
+        static const enum wined3d_format_id formats[] =
         {
             WINED3DFMT_D24_UNORM_S8_UINT,
             WINED3DFMT_D32_UNORM,
@@ -831,7 +795,7 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
          * issue needs to be fixed. */
         for (i = 0; i < (sizeof(formats) / sizeof(*formats)); i++)
         {
-            swapchain->ds_format = getFormatDescEntry(formats[i], gl_info);
+            swapchain->ds_format = wined3d_get_format(gl_info, formats[i]);
             swapchain->context[0] = context_create(swapchain, swapchain->front_buffer, swapchain->ds_format);
             if (swapchain->context[0]) break;
             TRACE("Depth stencil format %s is not supported, trying next format\n",
@@ -846,7 +810,7 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
         }
 
         if (!present_parameters->EnableAutoDepthStencil
-                || swapchain->presentParms.AutoDepthStencilFormat != swapchain->ds_format->format)
+                || swapchain->presentParms.AutoDepthStencilFormat != swapchain->ds_format->id)
         {
             FIXME("Add OpenGL context recreation support to context_validate_onscreen_formats\n");
         }
@@ -882,8 +846,7 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
                 goto err;
             }
 
-            IWineD3DSurface_SetContainer((IWineD3DSurface *)swapchain->back_buffers[i], (IWineD3DBase *)swapchain);
-            swapchain->back_buffers[i]->Flags |= SFLAG_SWAPCHAIN;
+            surface_set_container(swapchain->back_buffers[i], WINED3D_CONTAINER_SWAPCHAIN, (IWineD3DBase *)swapchain);
         }
     }
 
@@ -893,7 +856,7 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
         TRACE("Creating depth/stencil buffer.\n");
         if (!device->auto_depth_stencil)
         {
-            hr = IWineD3DDeviceParent_CreateDepthStencilSurface(device->device_parent, parent,
+            hr = IWineD3DDeviceParent_CreateDepthStencilSurface(device->device_parent,
                     swapchain->presentParms.BackBufferWidth, swapchain->presentParms.BackBufferHeight,
                     swapchain->presentParms.AutoDepthStencilFormat, swapchain->presentParms.MultiSampleType,
                     swapchain->presentParms.MultiSampleQuality, FALSE /* FIXME: Discard */,
@@ -904,7 +867,7 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
                 goto err;
             }
 
-            IWineD3DSurface_SetContainer((IWineD3DSurface *)device->auto_depth_stencil, NULL);
+            surface_set_container(device->auto_depth_stencil, WINED3D_CONTAINER_NONE, NULL);
         }
     }
 
@@ -923,7 +886,7 @@ err:
         memset(&devmode, 0, sizeof(devmode));
         devmode.dmSize = sizeof(devmode);
         devmode.dmFields = DM_BITSPERPEL | DM_PELSWIDTH | DM_PELSHEIGHT;
-        devmode.dmBitsPerPel = format_desc->byte_count * 8;
+        devmode.dmBitsPerPel = format->byte_count * CHAR_BIT;
         devmode.dmPelsWidth = swapchain->orig_width;
         devmode.dmPelsHeight = swapchain->orig_height;
         ChangeDisplaySettingsExW(adapter->DeviceName, &devmode, NULL, CDS_FULLSCREEN, NULL);
@@ -954,6 +917,7 @@ err:
     return hr;
 }
 
+/* Do not call while under the GL lock. */
 struct wined3d_context *swapchain_create_context_for_thread(IWineD3DSwapChain *iface)
 {
     IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *) iface;
@@ -969,7 +933,7 @@ struct wined3d_context *swapchain_create_context_for_thread(IWineD3DSwapChain *i
     }
     context_release(ctx);
 
-    newArray = HeapAlloc(GetProcessHeap(), 0, sizeof(*newArray) * This->num_contexts + 1);
+    newArray = HeapAlloc(GetProcessHeap(), 0, sizeof(*newArray) * (This->num_contexts + 1));
     if(!newArray) {
         ERR("Out of memory when trying to allocate a new context array\n");
         context_destroy(This->device, ctx);
index 1817de2..083585f 100644 (file)
@@ -53,30 +53,32 @@ ULONG WINAPI IWineD3DBaseSwapChainImpl_AddRef(IWineD3DSwapChain *iface) {
     return refCount;
 }
 
-ULONG WINAPI IWineD3DBaseSwapChainImpl_Release(IWineD3DSwapChain *iface) {
+/* Do not call while under the GL lock. */
+ULONG WINAPI IWineD3DBaseSwapChainImpl_Release(IWineD3DSwapChain *iface)
+{
     IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface;
     DWORD refCount;
     refCount = InterlockedDecrement(&This->ref);
     TRACE("(%p) : ReleaseRef to %d\n", This, refCount);
-    if (refCount == 0) {
-        IWineD3DSwapChain_Destroy(iface);
-    }
+
+    if (!refCount) IWineD3DSwapChain_Destroy(iface);
+
     return refCount;
 }
 
-HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetParent(IWineD3DSwapChain *iface, IUnknown ** ppParent){
-    IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface;
-    *ppParent = This->parent;
-    IUnknown_AddRef(*ppParent);
-    TRACE("(%p) returning %p\n", This , *ppParent);
-    return WINED3D_OK;
+void * WINAPI IWineD3DBaseSwapChainImpl_GetParent(IWineD3DSwapChain *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ((IWineD3DSwapChainImpl *)iface)->parent;
 }
 
-HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetFrontBufferData(IWineD3DSwapChain *iface, IWineD3DSurface *pDestSurface) {
+HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetFrontBufferData(IWineD3DSwapChain *iface, IWineD3DSurface *dst_surface)
+{
     IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface;
     POINT start;
 
-    TRACE("(%p) : iface(%p) pDestSurface(%p)\n", This, iface, pDestSurface);
+    TRACE("iface %p, dst_surface %p.\n", iface, dst_surface);
 
     start.x = 0;
     start.y = 0;
@@ -85,53 +87,54 @@ HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetFrontBufferData(IWineD3DSwapChain *i
         MapWindowPoints(This->win_handle, NULL, &start, 1);
     }
 
-    IWineD3DSurface_BltFast(pDestSurface, start.x, start.y, (IWineD3DSurface *)This->front_buffer, NULL, 0);
+    IWineD3DSurface_BltFast(dst_surface, start.x, start.y, (IWineD3DSurface *)This->front_buffer, NULL, 0);
     return WINED3D_OK;
 }
 
-HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetBackBuffer(IWineD3DSwapChain *iface, UINT iBackBuffer, WINED3DBACKBUFFER_TYPE Type, IWineD3DSurface **ppBackBuffer) {
-
-    IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface;
+HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetBackBuffer(IWineD3DSwapChain *iface,
+        UINT back_buffer_idx, WINED3DBACKBUFFER_TYPE type, IWineD3DSurface **back_buffer)
+{
+    IWineD3DSwapChainImpl *swapchain = (IWineD3DSwapChainImpl *)iface;
 
-    if (iBackBuffer > This->presentParms.BackBufferCount - 1) {
-        TRACE("Back buffer count out of range\n");
-        /* Native d3d9 doesn't set NULL here, just as wine's d3d9. But set it
-         * here in wined3d to avoid problems in other libs
-         */
-        *ppBackBuffer = NULL;
-        return WINED3DERR_INVALIDCALL;
-    }
+    TRACE("iface %p, back_buffer_idx %u, type %#x, back_buffer %p.\n",
+            iface, back_buffer_idx, type, back_buffer);
 
-    /* Return invalid if there is no backbuffer array, otherwise it will crash when ddraw is
-     * used (there This->backBuffer is always NULL). We need this because this function has
-     * to be called from IWineD3DStateBlockImpl_InitStartupStateBlock to get the default
+    /* Return invalid if there is no backbuffer array, otherwise it will
+     * crash when ddraw is used (there swapchain->back_buffers is always NULL).
+     * We need this because this function is called from
+     * IWineD3DStateBlockImpl_InitStartupStateBlock() to get the default
      * scissorrect dimensions. */
-    if (!This->back_buffers)
+    if (!swapchain->back_buffers || back_buffer_idx >= swapchain->presentParms.BackBufferCount)
     {
-        *ppBackBuffer = NULL;
+        WARN("Invalid back buffer index.\n");
+        /* Native d3d9 doesn't set NULL here, just as wine's d3d9. But set it
+         * here in wined3d to avoid problems in other libs. */
+        *back_buffer = NULL;
         return WINED3DERR_INVALIDCALL;
     }
 
-    *ppBackBuffer = (IWineD3DSurface *)This->back_buffers[iBackBuffer];
-    TRACE("(%p) : BackBuf %d Type %d  returning %p\n", This, iBackBuffer, Type, *ppBackBuffer);
+    *back_buffer = (IWineD3DSurface *)swapchain->back_buffers[back_buffer_idx];
+    if (*back_buffer) IWineD3DSurface_AddRef(*back_buffer);
 
-    /* Note inc ref on returned surface */
-    if(*ppBackBuffer) IWineD3DSurface_AddRef(*ppBackBuffer);
-    return WINED3D_OK;
+    TRACE("Returning back buffer %p.\n", *back_buffer);
 
+    return WINED3D_OK;
 }
 
 HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetRasterStatus(IWineD3DSwapChain *iface, WINED3DRASTER_STATUS *pRasterStatus) {
     static BOOL warned;
-    pRasterStatus->InVBlank = TRUE;
-    pRasterStatus->ScanLine = 0;
-    /* No openGL equivalent */
+    /* No OpenGL equivalent */
     if (!warned)
     {
         FIXME("iface %p, raster_status %p stub!\n", iface, pRasterStatus);
         warned = TRUE;
     }
-    return WINED3D_OK;
+    /* Obtaining the raster status is a widely implemented but optional feature.
+     * When this method returns OK then the application Starcraft 2 expects that
+     * the pRasterStatus->InVBlank value differs over time. To prevent Starcraft 2
+     * from running in an infinite loop at startup this method returns INVALIDCALL.
+     */
+    return WINED3DERR_INVALIDCALL;
 }
 
 HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetDisplayMode(IWineD3DSwapChain *iface, WINED3DDISPLAYMODE*pMode) {
index b80352c..8920cae 100644 (file)
@@ -39,7 +39,7 @@ static void WINAPI IWineGDISwapChainImpl_Destroy(IWineD3DSwapChain *iface)
     /* release the ref to the front and back buffer parents */
     if (This->front_buffer)
     {
-        IWineD3DSurface_SetContainer((IWineD3DSurface *)This->front_buffer, NULL);
+        surface_set_container(This->front_buffer, WINED3D_CONTAINER_NONE, NULL);
         if (IWineD3DSurface_Release((IWineD3DSurface *)This->front_buffer) > 0)
         {
             WARN("(%p) Something's still holding the front buffer\n",This);
@@ -51,7 +51,7 @@ static void WINAPI IWineGDISwapChainImpl_Destroy(IWineD3DSwapChain *iface)
         UINT i;
         for (i = 0; i < This->presentParms.BackBufferCount; ++i)
         {
-            IWineD3DSurface_SetContainer((IWineD3DSurface *)This->back_buffers[i], NULL);
+            surface_set_container(This->back_buffers[i], WINED3D_CONTAINER_NONE, NULL);
             if (IWineD3DSurface_Release((IWineD3DSurface *)This->back_buffers[i]))
             {
                 WARN("(%p) Something's still holding the back buffer\n",This);
@@ -65,7 +65,8 @@ static void WINAPI IWineGDISwapChainImpl_Destroy(IWineD3DSwapChain *iface)
      * this will be the original desktop resolution. In case of d3d7 this will be a NOP because ddraw sets the resolution
      * before starting up Direct3D, thus orig_width and orig_height will be equal to the modes in the presentation params
      */
-    if(This->presentParms.Windowed == FALSE && This->presentParms.AutoRestoreDisplayMode) {
+    if (!This->presentParms.Windowed && This->presentParms.AutoRestoreDisplayMode)
+    {
         mode.Width = This->orig_width;
         mode.Height = This->orig_height;
         mode.RefreshRate = 0;
index 98e7909..ce95567 100644 (file)
@@ -27,6 +27,7 @@
 
 WINE_DEFAULT_DEBUG_CHANNEL(d3d_texture);
 
+/* Do not call while under the GL lock. */
 static void texture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3DSRGB srgb)
 {
     /* Override the IWineD3DResource PreLoad method. */
@@ -66,8 +67,8 @@ static void texture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3DSRG
         context = context_acquire(device, NULL);
     }
 
-    if (This->resource.format_desc->format == WINED3DFMT_P8_UINT
-            || This->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM)
+    if (This->resource.format->id == WINED3DFMT_P8_UINT
+            || This->resource.format->id == WINED3DFMT_P8_UINT_A8_UNORM)
     {
         for (i = 0; i < This->baseTexture.level_count; ++i)
         {
@@ -76,9 +77,9 @@ static void texture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3DSRG
             {
                 TRACE("Reloading surface because the d3d8/9 palette was changed.\n");
                 /* TODO: This is not necessarily needed with hw palettized texture support. */
-                IWineD3DSurface_LoadLocation((IWineD3DSurface *)surface, SFLAG_INSYSMEM, NULL);
+                surface_load_location(surface, SFLAG_INSYSMEM, NULL);
                 /* Make sure the texture is reloaded because of the palette change, this kills performance though :( */
-                IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INTEXTURE, FALSE);
+                surface_modify_location(surface, SFLAG_INTEXTURE, FALSE);
             }
         }
     }
@@ -119,7 +120,7 @@ static void texture_cleanup(IWineD3DTextureImpl *This)
             surface_set_texture_name(surface, 0, TRUE);
             surface_set_texture_name(surface, 0, FALSE);
             surface_set_texture_target(surface, 0);
-            IWineD3DSurface_SetContainer((IWineD3DSurface *)surface, NULL);
+            surface_set_container(surface, WINED3D_CONTAINER_NONE, NULL);
             IWineD3DSurface_Release((IWineD3DSurface *)surface);
         }
     }
@@ -155,6 +156,7 @@ static ULONG WINAPI IWineD3DTextureImpl_AddRef(IWineD3DTexture *iface) {
     return InterlockedIncrement(&This->resource.ref);
 }
 
+/* Do not call while under the GL lock. */
 static ULONG WINAPI IWineD3DTextureImpl_Release(IWineD3DTexture *iface) {
     IWineD3DTextureImpl *This = (IWineD3DTextureImpl *)iface;
     ULONG ref;
@@ -193,10 +195,12 @@ static DWORD WINAPI IWineD3DTextureImpl_GetPriority(IWineD3DTexture *iface) {
     return resource_get_priority((IWineD3DResource *)iface);
 }
 
+/* Do not call while under the GL lock. */
 static void WINAPI IWineD3DTextureImpl_PreLoad(IWineD3DTexture *iface) {
     texture_internal_preload((IWineD3DBaseTexture *) iface, SRGB_ANY);
 }
 
+/* Do not call while under the GL lock. */
 static void WINAPI IWineD3DTextureImpl_UnLoad(IWineD3DTexture *iface) {
     unsigned int i;
     IWineD3DTextureImpl *This = (IWineD3DTextureImpl *)iface;
@@ -221,8 +225,11 @@ static WINED3DRESOURCETYPE WINAPI IWineD3DTextureImpl_GetType(IWineD3DTexture *i
     return resource_get_type((IWineD3DResource *)iface);
 }
 
-static HRESULT WINAPI IWineD3DTextureImpl_GetParent(IWineD3DTexture *iface, IUnknown **pParent) {
-    return resource_get_parent((IWineD3DResource *)iface, pParent);
+static void * WINAPI IWineD3DTextureImpl_GetParent(IWineD3DTexture *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ((IWineD3DTextureImpl *)iface)->resource.parent;
 }
 
 /* ******************************************************
@@ -294,16 +301,19 @@ static HRESULT WINAPI IWineD3DTextureImpl_BindTexture(IWineD3DTexture *iface, BO
          * state. The same applies to filtering. Even if the texture has only
          * one mip level, the default LINEAR_MIPMAP_LINEAR filter causes a SW
          * fallback on macos. */
-        if(IWineD3DBaseTexture_IsCondNP2(iface)) {
+        if (IWineD3DBaseTexture_IsCondNP2(iface))
+        {
+            GLenum target = This->baseTexture.target;
+
             ENTER_GL();
-            glTexParameteri(IWineD3DTexture_GetTextureDimensions(iface), GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
-            checkGLcall("glTexParameteri(dimension, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE)");
-            glTexParameteri(IWineD3DTexture_GetTextureDimensions(iface), GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
-            checkGLcall("glTexParameteri(dimension, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE)");
-            glTexParameteri(IWineD3DTexture_GetTextureDimensions(iface), GL_TEXTURE_MIN_FILTER, GL_NEAREST);
-            checkGLcall("glTexParameteri(dimension, GL_TEXTURE_MIN_FILTER, GL_NEAREST)");
-            glTexParameteri(IWineD3DTexture_GetTextureDimensions(iface), GL_TEXTURE_MAG_FILTER, GL_NEAREST);
-            checkGLcall("glTexParameteri(dimension, GL_TEXTURE_MAG_FILTER, GL_NEAREST)");
+            glTexParameteri(target, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+            checkGLcall("glTexParameteri(target, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE)");
+            glTexParameteri(target, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
+            checkGLcall("glTexParameteri(target, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE)");
+            glTexParameteri(target, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
+            checkGLcall("glTexParameteri(target, GL_TEXTURE_MIN_FILTER, GL_NEAREST)");
+            glTexParameteri(target, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
+            checkGLcall("glTexParameteri(target, GL_TEXTURE_MAG_FILTER, GL_NEAREST)");
             LEAVE_GL();
             gl_tex->states[WINED3DTEXSTA_ADDRESSU]      = WINED3DTADDRESS_CLAMP;
             gl_tex->states[WINED3DTEXSTA_ADDRESSV]      = WINED3DTADDRESS_CLAMP;
@@ -316,13 +326,6 @@ static HRESULT WINAPI IWineD3DTextureImpl_BindTexture(IWineD3DTexture *iface, BO
     return hr;
 }
 
-static UINT WINAPI IWineD3DTextureImpl_GetTextureDimensions(IWineD3DTexture *iface) {
-    IWineD3DTextureImpl *This = (IWineD3DTextureImpl *)iface;
-    TRACE("(%p)\n", This);
-
-    return This->target;
-}
-
 static BOOL WINAPI IWineD3DTextureImpl_IsCondNP2(IWineD3DTexture *iface) {
     IWineD3DTextureImpl *This = (IWineD3DTextureImpl *)iface;
     TRACE("(%p)\n", This);
@@ -346,7 +349,9 @@ static HRESULT WINAPI IWineD3DTextureImpl_GetLevelDesc(IWineD3DTexture *iface, U
         return WINED3DERR_INVALIDCALL;
     }
 
-    return IWineD3DSurface_GetDesc(surface, desc);
+    IWineD3DSurface_GetDesc(surface, desc);
+
+    return WINED3D_OK;
 }
 
 static HRESULT WINAPI IWineD3DTextureImpl_GetSurfaceLevel(IWineD3DTexture *iface,
@@ -451,7 +456,6 @@ static const IWineD3DTextureVtbl IWineD3DTexture_Vtbl =
     IWineD3DTextureImpl_SetDirty,
     IWineD3DTextureImpl_GetDirty,
     IWineD3DTextureImpl_BindTexture,
-    IWineD3DTextureImpl_GetTextureDimensions,
     IWineD3DTextureImpl_IsCondNP2,
     /* IWineD3DTexture */
     IWineD3DTextureImpl_GetLevelDesc,
@@ -462,11 +466,11 @@ static const IWineD3DTextureVtbl IWineD3DTexture_Vtbl =
 };
 
 HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT levels,
-        IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        IWineD3DDeviceImpl *device, DWORD usage, enum wined3d_format_id format_id, WINED3DPOOL pool,
+        void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, gl_info);
+    const struct wined3d_format *format = wined3d_get_format(gl_info, format_id);
     UINT pow2_width, pow2_height;
     UINT tmp_w, tmp_h;
     unsigned int i;
@@ -474,7 +478,7 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
 
     /* TODO: It should only be possible to create textures for formats
      * that are reported as supported. */
-    if (WINED3DFMT_UNKNOWN >= format)
+    if (WINED3DFMT_UNKNOWN >= format_id)
     {
         WARN("(%p) : Texture cannot be created with a format of WINED3DFMT_UNKNOWN.\n", texture);
         return WINED3DERR_INVALIDCALL;
@@ -530,7 +534,7 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
     texture->lpVtbl = &IWineD3DTexture_Vtbl;
 
     hr = basetexture_init((IWineD3DBaseTextureImpl *)texture, 1, levels,
-            WINED3DRTYPE_TEXTURE, device, 0, usage, format_desc, pool, parent, parent_ops);
+            WINED3DRTYPE_TEXTURE, device, 0, usage, format, pool, parent, parent_ops);
     if (FAILED(hr))
     {
         WARN("Failed to initialize basetexture, returning %#x.\n", hr);
@@ -541,18 +545,18 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
      * Second also don't use ARB_TEXTURE_RECTANGLE in case the surface format is P8 and EXT_PALETTED_TEXTURE
      * is used in combination with texture uploads (RTL_READTEX). The reason is that EXT_PALETTED_TEXTURE
      * doesn't work in combination with ARB_TEXTURE_RECTANGLE. */
-    if (gl_info->supported[WINE_NORMALIZED_TEXRECT] && (width != pow2_width || height != pow2_height))
+    if (gl_info->supported[WINED3D_GL_NORMALIZED_TEXRECT] && (width != pow2_width || height != pow2_height))
     {
         texture->baseTexture.pow2Matrix[0] = 1.0f;
         texture->baseTexture.pow2Matrix[5] = 1.0f;
         texture->baseTexture.pow2Matrix[10] = 1.0f;
         texture->baseTexture.pow2Matrix[15] = 1.0f;
-        texture->target = GL_TEXTURE_2D;
+        texture->baseTexture.target = GL_TEXTURE_2D;
         texture->cond_np2 = TRUE;
         texture->baseTexture.minMipLookup = minMipLookup_noFilter;
     }
     else if (gl_info->supported[ARB_TEXTURE_RECTANGLE] && (width != pow2_width || height != pow2_height)
-            && !(format_desc->format == WINED3DFMT_P8_UINT && gl_info->supported[EXT_PALETTED_TEXTURE]
+            && !(format->id == WINED3DFMT_P8_UINT && gl_info->supported[EXT_PALETTED_TEXTURE]
             && wined3d_settings.rendertargetlock_mode == RTL_READTEX))
     {
         if ((width != 1) || (height != 1)) texture->baseTexture.pow2Matrix_identity = FALSE;
@@ -561,10 +565,10 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
         texture->baseTexture.pow2Matrix[5] = (float)height;
         texture->baseTexture.pow2Matrix[10] = 1.0f;
         texture->baseTexture.pow2Matrix[15] = 1.0f;
-        texture->target = GL_TEXTURE_RECTANGLE_ARB;
+        texture->baseTexture.target = GL_TEXTURE_RECTANGLE_ARB;
         texture->cond_np2 = TRUE;
 
-        if(texture->resource.format_desc->Flags & WINED3DFMT_FLAG_FILTERING)
+        if(texture->resource.format->Flags & WINED3DFMT_FLAG_FILTERING)
         {
             texture->baseTexture.minMipLookup = minMipLookup_noMip;
         }
@@ -589,7 +593,7 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
 
         texture->baseTexture.pow2Matrix[10] = 1.0f;
         texture->baseTexture.pow2Matrix[15] = 1.0f;
-        texture->target = GL_TEXTURE_2D;
+        texture->baseTexture.target = GL_TEXTURE_2D;
         texture->cond_np2 = FALSE;
     }
     TRACE("xf(%f) yf(%f)\n", texture->baseTexture.pow2Matrix[0], texture->baseTexture.pow2Matrix[5]);
@@ -602,8 +606,8 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
         IWineD3DSurface *surface;
 
         /* Use the callback to create the texture surface. */
-        hr = IWineD3DDeviceParent_CreateSurface(device->device_parent, parent, tmp_w, tmp_h, format_desc->format,
-                usage, pool, i, 0, &surface);
+        hr = IWineD3DDeviceParent_CreateSurface(device->device_parent, parent, tmp_w, tmp_h,
+                format->id, usage, pool, i, 0, &surface);
         if (FAILED(hr))
         {
             FIXME("Failed to create surface %p, hr %#x\n", texture, hr);
@@ -611,8 +615,8 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
             return hr;
         }
 
-        IWineD3DSurface_SetContainer(surface, (IWineD3DBase *)texture);
-        surface_set_texture_target((IWineD3DSurfaceImpl *)surface, texture->target);
+        surface_set_container((IWineD3DSurfaceImpl *)surface, WINED3D_CONTAINER_TEXTURE, (IWineD3DBase *)texture);
+        surface_set_texture_target((IWineD3DSurfaceImpl *)surface, texture->baseTexture.target);
         texture->baseTexture.sub_resources[i] = (IWineD3DResourceImpl *)surface;
         TRACE("Created surface level %u @ %p.\n", i, surface);
         /* Calculate the next mipmap level. */
index b63a5f8..2957c5a 100644 (file)
@@ -31,7 +31,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d);
 
 struct StaticPixelFormatDesc
 {
-    WINED3DFORMAT format;
+    enum wined3d_format_id id;
     DWORD alphaMask, redMask, greenMask, blueMask;
     UINT bpp;
     short depthSize, stencilSize;
@@ -49,7 +49,7 @@ struct StaticPixelFormatDesc
  */
 static const struct StaticPixelFormatDesc formats[] =
 {
-  /* WINED3DFORMAT                       alphamask    redmask    greenmask    bluemask     bpp    depth  stencil */
+  /* format id                           alphamask    redmask    greenmask    bluemask     bpp    depth  stencil */
     {WINED3DFMT_UNKNOWN,                    0x0,        0x0,        0x0,        0x0,        0,      0,      0},
     /* FourCC formats */
     {WINED3DFMT_UYVY,                       0x0,        0x0,        0x0,        0x0,        2,      0,      0},
@@ -129,16 +129,20 @@ static const struct StaticPixelFormatDesc formats[] =
     {WINED3DFMT_R16G16B16A16_SNORM,         0x0,        0x0,        0x0,        0x0,        8,      0,      0},
     /* Vendor-specific formats */
     {WINED3DFMT_ATI2N,                      0x0,        0x0,        0x0,        0x0,        1,      0,      0},
+    {WINED3DFMT_NVDB,                       0x0,        0x0,        0x0,        0x0,        0,      0,      0},
     {WINED3DFMT_NVHU,                       0x0,        0x0,        0x0,        0x0,        2,      0,      0},
     {WINED3DFMT_NVHS,                       0x0,        0x0,        0x0,        0x0,        2,      0,      0},
 };
 
 struct wined3d_format_base_flags
 {
-    WINED3DFORMAT format;
+    enum wined3d_format_id id;
     DWORD flags;
 };
 
+/* The ATI2N format behaves like an uncompressed format in LockRect(), but
+ * still needs to use the correct block based calculation for e.g. the
+ * resource size. */
 static const struct wined3d_format_base_flags format_base_flags[] =
 {
     {WINED3DFMT_UYVY,               WINED3DFMT_FLAG_FOURCC},
@@ -163,7 +167,8 @@ static const struct wined3d_format_base_flags format_base_flags[] =
     {WINED3DFMT_B4G4R4X4_UNORM,     WINED3DFMT_FLAG_GETDC},
     {WINED3DFMT_R8G8B8A8_UNORM,     WINED3DFMT_FLAG_GETDC},
     {WINED3DFMT_R8G8B8X8_UNORM,     WINED3DFMT_FLAG_GETDC},
-    {WINED3DFMT_ATI2N,              WINED3DFMT_FLAG_FOURCC},
+    {WINED3DFMT_ATI2N,              WINED3DFMT_FLAG_FOURCC | WINED3DFMT_FLAG_BROKEN_PITCH},
+    {WINED3DFMT_NVDB,               WINED3DFMT_FLAG_FOURCC},
     {WINED3DFMT_NVHU,               WINED3DFMT_FLAG_FOURCC},
     {WINED3DFMT_NVHS,               WINED3DFMT_FLAG_FOURCC},
     {WINED3DFMT_R32_FLOAT,          WINED3DFMT_FLAG_FLOAT},
@@ -179,7 +184,7 @@ static const struct wined3d_format_base_flags format_base_flags[] =
 
 struct wined3d_format_compression_info
 {
-    WINED3DFORMAT format;
+    enum wined3d_format_id id;
     UINT block_width;
     UINT block_height;
     UINT block_byte_count;
@@ -192,12 +197,12 @@ static const struct wined3d_format_compression_info format_compression_info[] =
     {WINED3DFMT_DXT3,   4,  4,  16},
     {WINED3DFMT_DXT4,   4,  4,  16},
     {WINED3DFMT_DXT5,   4,  4,  16},
-    {WINED3DFMT_ATI2N,  1,  1,  1},
+    {WINED3DFMT_ATI2N,  4,  4,  16},
 };
 
 struct wined3d_format_vertex_info
 {
-    WINED3DFORMAT format;
+    enum wined3d_format_id id;
     enum wined3d_ffp_emit_idx emit_idx;
     GLint component_count;
     GLenum gl_vtx_type;
@@ -229,7 +234,7 @@ static const struct wined3d_format_vertex_info format_vertex_info[] =
 
 struct wined3d_format_texture_info
 {
-    WINED3DFORMAT format;
+    enum wined3d_format_id id;
     GLint gl_internal;
     GLint gl_srgb_internal;
     GLint gl_rt_internal;
@@ -549,7 +554,7 @@ static void convert_s8_uint_d24_float(const BYTE *src, BYTE *dst, UINT pitch, UI
 
 static const struct wined3d_format_texture_info format_texture_info[] =
 {
-    /* WINED3DFORMAT                    internal                          srgbInternal                       rtInternal
+    /* format id                        internal                          srgbInternal                       rtInternal
             format                      type
             flags
             extension */
@@ -845,26 +850,30 @@ static const struct wined3d_format_texture_info format_texture_info[] =
     /* Vendor-specific formats */
     {WINED3DFMT_ATI2N,                  GL_COMPRESSED_LUMINANCE_ALPHA_3DC_ATI, GL_COMPRESSED_LUMINANCE_ALPHA_3DC_ATI, 0,
             GL_LUMINANCE_ALPHA,         GL_UNSIGNED_BYTE,                 0,
-            0,
+            WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
             ATI_TEXTURE_COMPRESSION_3DC, NULL},
-    {WINED3DFMT_ATI2N,                  GL_COMPRESSED_RED_GREEN_RGTC2_EXT, GL_COMPRESSED_RED_GREEN_RGTC2_EXT,     0,
+    {WINED3DFMT_ATI2N,                  GL_COMPRESSED_RED_GREEN_RGTC2,    GL_COMPRESSED_RED_GREEN_RGTC2,         0,
             GL_LUMINANCE_ALPHA,         GL_UNSIGNED_BYTE,                 0,
-            0,
-            EXT_TEXTURE_COMPRESSION_RGTC, NULL},
+            WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
+            ARB_TEXTURE_COMPRESSION_RGTC, NULL},
 };
 
-static inline int getFmtIdx(WINED3DFORMAT fmt) {
+static inline int getFmtIdx(enum wined3d_format_id format_id)
+{
     /* First check if the format is at the position of its value.
-     * This will catch the argb formats before the loop is entered
-     */
-    if(fmt < (sizeof(formats) / sizeof(formats[0])) && formats[fmt].format == fmt) {
-        return fmt;
-    } else {
+     * This will catch the argb formats before the loop is entered. */
+    if (format_id < (sizeof(formats) / sizeof(*formats))
+            && formats[format_id].id == format_id)
+    {
+        return format_id;
+    }
+    else
+    {
         unsigned int i;
-        for(i = 0; i < (sizeof(formats) / sizeof(formats[0])); i++) {
-            if(formats[i].format == fmt) {
-                return i;
-            }
+
+        for (i = 0; i < (sizeof(formats) / sizeof(*formats)); ++i)
+        {
+            if (formats[i].id == format_id) return i;
         }
     }
     return -1;
@@ -875,8 +884,8 @@ static BOOL init_format_base_info(struct wined3d_gl_info *gl_info)
     UINT format_count = sizeof(formats) / sizeof(*formats);
     UINT i;
 
-    gl_info->gl_formats = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, format_count * sizeof(*gl_info->gl_formats));
-    if (!gl_info->gl_formats)
+    gl_info->formats = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, format_count * sizeof(*gl_info->formats));
+    if (!gl_info->formats)
     {
         ERR("Failed to allocate memory.\n");
         return FALSE;
@@ -884,30 +893,30 @@ static BOOL init_format_base_info(struct wined3d_gl_info *gl_info)
 
     for (i = 0; i < format_count; ++i)
     {
-        struct wined3d_format_desc *desc = &gl_info->gl_formats[i];
-        desc->format = formats[i].format;
-        desc->red_mask = formats[i].redMask;
-        desc->green_mask = formats[i].greenMask;
-        desc->blue_mask = formats[i].blueMask;
-        desc->alpha_mask = formats[i].alphaMask;
-        desc->byte_count = formats[i].bpp;
-        desc->depth_size = formats[i].depthSize;
-        desc->stencil_size = formats[i].stencilSize;
+        struct wined3d_format *format = &gl_info->formats[i];
+        format->id = formats[i].id;
+        format->red_mask = formats[i].redMask;
+        format->green_mask = formats[i].greenMask;
+        format->blue_mask = formats[i].blueMask;
+        format->alpha_mask = formats[i].alphaMask;
+        format->byte_count = formats[i].bpp;
+        format->depth_size = formats[i].depthSize;
+        format->stencil_size = formats[i].stencilSize;
     }
 
     for (i = 0; i < (sizeof(format_base_flags) / sizeof(*format_base_flags)); ++i)
     {
-        int fmt_idx = getFmtIdx(format_base_flags[i].format);
+        int fmt_idx = getFmtIdx(format_base_flags[i].id);
 
         if (fmt_idx == -1)
         {
             ERR("Format %s (%#x) not found.\n",
-                    debug_d3dformat(format_base_flags[i].format), format_base_flags[i].format);
-            HeapFree(GetProcessHeap(), 0, gl_info->gl_formats);
+                    debug_d3dformat(format_base_flags[i].id), format_base_flags[i].id);
+            HeapFree(GetProcessHeap(), 0, gl_info->formats);
             return FALSE;
         }
 
-        gl_info->gl_formats[fmt_idx].Flags |= format_base_flags[i].flags;
+        gl_info->formats[fmt_idx].Flags |= format_base_flags[i].flags;
     }
 
     return TRUE;
@@ -919,28 +928,28 @@ static BOOL init_format_compression_info(struct wined3d_gl_info *gl_info)
 
     for (i = 0; i < (sizeof(format_compression_info) / sizeof(*format_compression_info)); ++i)
     {
-        struct wined3d_format_desc *format_desc;
-        int fmt_idx = getFmtIdx(format_compression_info[i].format);
+        struct wined3d_format *format;
+        int fmt_idx = getFmtIdx(format_compression_info[i].id);
 
         if (fmt_idx == -1)
         {
             ERR("Format %s (%#x) not found.\n",
-                    debug_d3dformat(format_compression_info[i].format), format_compression_info[i].format);
+                    debug_d3dformat(format_compression_info[i].id), format_compression_info[i].id);
             return FALSE;
         }
 
-        format_desc = &gl_info->gl_formats[fmt_idx];
-        format_desc->block_width = format_compression_info[i].block_width;
-        format_desc->block_height = format_compression_info[i].block_height;
-        format_desc->block_byte_count = format_compression_info[i].block_byte_count;
-        format_desc->Flags |= WINED3DFMT_FLAG_COMPRESSED;
+        format = &gl_info->formats[fmt_idx];
+        format->block_width = format_compression_info[i].block_width;
+        format->block_height = format_compression_info[i].block_height;
+        format->block_byte_count = format_compression_info[i].block_byte_count;
+        format->Flags |= WINED3DFMT_FLAG_COMPRESSED;
     }
 
     return TRUE;
 }
 
 /* Context activation is done by the caller. */
-static void check_fbo_compat(const struct wined3d_gl_info *gl_info, struct wined3d_format_desc *format_desc)
+static void check_fbo_compat(const struct wined3d_gl_info *gl_info, struct wined3d_format *format)
 {
     /* Check if the default internal format is supported as a frame buffer
      * target, otherwise fall back to the render target internal.
@@ -957,8 +966,7 @@ static void check_fbo_compat(const struct wined3d_gl_info *gl_info, struct wined
     glGenTextures(1, &tex);
     glBindTexture(GL_TEXTURE_2D, tex);
 
-    glTexImage2D(GL_TEXTURE_2D, 0, format_desc->glInternal, 16, 16, 0,
-            format_desc->glFormat, format_desc->glType, NULL);
+    glTexImage2D(GL_TEXTURE_2D, 0, format->glInternal, 16, 16, 0, format->glFormat, format->glType, NULL);
     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
 
@@ -969,37 +977,36 @@ static void check_fbo_compat(const struct wined3d_gl_info *gl_info, struct wined
 
     if (status == GL_FRAMEBUFFER_COMPLETE)
     {
-        TRACE("Format %s is supported as FBO color attachment\n", debug_d3dformat(format_desc->format));
-        format_desc->Flags |= WINED3DFMT_FLAG_FBO_ATTACHABLE;
-        format_desc->rtInternal = format_desc->glInternal;
+        TRACE("Format %s is supported as FBO color attachment.\n", debug_d3dformat(format->id));
+        format->Flags |= WINED3DFMT_FLAG_FBO_ATTACHABLE;
+        format->rtInternal = format->glInternal;
     }
     else
     {
-        if (!format_desc->rtInternal)
+        if (!format->rtInternal)
         {
-            if (format_desc->Flags & WINED3DFMT_FLAG_RENDERTARGET)
+            if (format->Flags & WINED3DFMT_FLAG_RENDERTARGET)
             {
                 FIXME("Format %s with rendertarget flag is not supported as FBO color attachment,"
-                        " and no fallback specified.\n", debug_d3dformat(format_desc->format));
-                format_desc->Flags &= ~WINED3DFMT_FLAG_RENDERTARGET;
+                        " and no fallback specified.\n", debug_d3dformat(format->id));
+                format->Flags &= ~WINED3DFMT_FLAG_RENDERTARGET;
             }
             else
             {
-                TRACE("Format %s is not supported as FBO color attachment.\n", debug_d3dformat(format_desc->format));
+                TRACE("Format %s is not supported as FBO color attachment.\n", debug_d3dformat(format->id));
             }
-            format_desc->rtInternal = format_desc->glInternal;
+            format->rtInternal = format->glInternal;
         }
         else
         {
             TRACE("Format %s is not supported as FBO color attachment, trying rtInternal format as fallback.\n",
-                    debug_d3dformat(format_desc->format));
+                    debug_d3dformat(format->id));
 
             while(glGetError());
 
             gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, 0, 0);
 
-            glTexImage2D(GL_TEXTURE_2D, 0, format_desc->rtInternal, 16, 16, 0,
-                    format_desc->glFormat, format_desc->glType, NULL);
+            glTexImage2D(GL_TEXTURE_2D, 0, format->rtInternal, 16, 16, 0, format->glFormat, format->glType, NULL);
             glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
             glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
 
@@ -1010,19 +1017,19 @@ static void check_fbo_compat(const struct wined3d_gl_info *gl_info, struct wined
 
             if (status == GL_FRAMEBUFFER_COMPLETE)
             {
-                TRACE("Format %s rtInternal format is supported as FBO color attachment\n",
-                        debug_d3dformat(format_desc->format));
+                TRACE("Format %s rtInternal format is supported as FBO color attachment.\n",
+                        debug_d3dformat(format->id));
             }
             else
             {
                 FIXME("Format %s rtInternal format is not supported as FBO color attachment.\n",
-                        debug_d3dformat(format_desc->format));
-                format_desc->Flags &= ~WINED3DFMT_FLAG_RENDERTARGET;
+                        debug_d3dformat(format->id));
+                format->Flags &= ~WINED3DFMT_FLAG_RENDERTARGET;
             }
         }
     }
 
-    if (status == GL_FRAMEBUFFER_COMPLETE && format_desc->Flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING)
+    if (status == GL_FRAMEBUFFER_COMPLETE && format->Flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING)
     {
         GLuint rb;
 
@@ -1043,7 +1050,7 @@ static void check_fbo_compat(const struct wined3d_gl_info *gl_info, struct wined
         {
             while(glGetError());
             TRACE("Format doesn't support post-pixelshader blending.\n");
-            format_desc->Flags &= ~WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING;
+            format->Flags &= ~WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING;
         }
 
         if (gl_info->supported[ARB_FRAMEBUFFER_OBJECT]
@@ -1056,6 +1063,25 @@ static void check_fbo_compat(const struct wined3d_gl_info *gl_info, struct wined
         }
     }
 
+    if (format->glInternal != format->glGammaInternal)
+    {
+        glTexImage2D(GL_TEXTURE_2D, 0, format->glGammaInternal, 16, 16, 0, format->glFormat, format->glType, NULL);
+        gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex, 0);
+
+        status = gl_info->fbo_ops.glCheckFramebufferStatus(GL_FRAMEBUFFER);
+        checkGLcall("Framebuffer format check");
+
+        if (status == GL_FRAMEBUFFER_COMPLETE)
+        {
+            TRACE("Format %s's sRGB format is FBO attachable.\n", debug_d3dformat(format->id));
+            format->Flags |= WINED3DFMT_FLAG_FBO_ATTACHABLE_SRGB;
+        }
+        else
+        {
+            WARN("Format %s's sRGB format is not FBO attachable.\n", debug_d3dformat(format->id));
+        }
+    }
+
     glDeleteTextures(1, &tex);
 
     LEAVE_GL();
@@ -1079,32 +1105,32 @@ static void init_format_fbo_compat_info(struct wined3d_gl_info *gl_info)
 
     for (i = 0; i < sizeof(formats) / sizeof(*formats); ++i)
     {
-        struct wined3d_format_desc *desc = &gl_info->gl_formats[i];
+        struct wined3d_format *format = &gl_info->formats[i];
 
-        if (!desc->glInternal) continue;
+        if (!format->glInternal) continue;
 
-        if (desc->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL))
+        if (format->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL))
         {
             TRACE("Skipping format %s because it's a depth/stencil format.\n",
-                    debug_d3dformat(desc->format));
+                    debug_d3dformat(format->id));
             continue;
         }
 
-        if (desc->Flags & WINED3DFMT_FLAG_COMPRESSED)
+        if (format->Flags & WINED3DFMT_FLAG_COMPRESSED)
         {
             TRACE("Skipping format %s because it's a compressed format.\n",
-                    debug_d3dformat(desc->format));
+                    debug_d3dformat(format->id));
             continue;
         }
 
         if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
         {
-            TRACE("Checking if format %s is supported as FBO color attachment...\n", debug_d3dformat(desc->format));
-            check_fbo_compat(gl_info, desc);
+            TRACE("Checking if format %s is supported as FBO color attachment...\n", debug_d3dformat(format->id));
+            check_fbo_compat(gl_info, format);
         }
         else
         {
-            desc->rtInternal = desc->glInternal;
+            format->rtInternal = format->glInternal;
         }
     }
 
@@ -1124,31 +1150,31 @@ static BOOL init_format_texture_info(struct wined3d_gl_info *gl_info)
 
     for (i = 0; i < sizeof(format_texture_info) / sizeof(*format_texture_info); ++i)
     {
-        int fmt_idx = getFmtIdx(format_texture_info[i].format);
-        struct wined3d_format_desc *desc;
+        int fmt_idx = getFmtIdx(format_texture_info[i].id);
+        struct wined3d_format *format;
 
         if (fmt_idx == -1)
         {
             ERR("Format %s (%#x) not found.\n",
-                    debug_d3dformat(format_texture_info[i].format), format_texture_info[i].format);
+                    debug_d3dformat(format_texture_info[i].id), format_texture_info[i].id);
             return FALSE;
         }
 
         if (!gl_info->supported[format_texture_info[i].extension]) continue;
 
-        desc = &gl_info->gl_formats[fmt_idx];
-        desc->glInternal = format_texture_info[i].gl_internal;
-        desc->glGammaInternal = format_texture_info[i].gl_srgb_internal;
-        desc->rtInternal = format_texture_info[i].gl_rt_internal;
-        desc->glFormat = format_texture_info[i].gl_format;
-        desc->glType = format_texture_info[i].gl_type;
-        desc->color_fixup = COLOR_FIXUP_IDENTITY;
-        desc->Flags |= format_texture_info[i].flags;
-        desc->heightscale = 1.0f;
+        format = &gl_info->formats[fmt_idx];
+        format->glInternal = format_texture_info[i].gl_internal;
+        format->glGammaInternal = format_texture_info[i].gl_srgb_internal;
+        format->rtInternal = format_texture_info[i].gl_rt_internal;
+        format->glFormat = format_texture_info[i].gl_format;
+        format->glType = format_texture_info[i].gl_type;
+        format->color_fixup = COLOR_FIXUP_IDENTITY;
+        format->Flags |= format_texture_info[i].flags;
+        format->heightscale = 1.0f;
 
         /* Texture conversion stuff */
-        desc->convert = format_texture_info[i].convert;
-        desc->conv_byte_count = format_texture_info[i].conv_byte_count;
+        format->convert = format_texture_info[i].convert;
+        format->conv_byte_count = format_texture_info[i].conv_byte_count;
     }
 
     return TRUE;
@@ -1169,8 +1195,8 @@ static BOOL color_match(DWORD c1, DWORD c2, BYTE max_diff)
 /* A context is provided by the caller */
 static BOOL check_filter(const struct wined3d_gl_info *gl_info, GLenum internal)
 {
+    static const DWORD data[] = {0x00000000, 0xffffffff};
     GLuint tex, fbo, buffer;
-    const DWORD data[] = {0x00000000, 0xffffffff};
     DWORD readback[16 * 1];
     BOOL ret = FALSE;
 
@@ -1266,9 +1292,10 @@ static BOOL check_filter(const struct wined3d_gl_info *gl_info, GLenum internal)
 
 static void init_format_filter_info(struct wined3d_gl_info *gl_info, enum wined3d_pci_vendor vendor)
 {
-    struct wined3d_format_desc *desc;
+    struct wined3d_format *format;
     unsigned int fmt_idx, i;
-    WINED3DFORMAT fmts16[] = {
+    static const enum wined3d_format_id fmts16[] =
+    {
         WINED3DFMT_R16_FLOAT,
         WINED3DFMT_R16G16_FLOAT,
         WINED3DFMT_R16G16B16A16_FLOAT,
@@ -1299,7 +1326,7 @@ static void init_format_filter_info(struct wined3d_gl_info *gl_info, enum wined3
             for(i = 0; i < (sizeof(fmts16) / sizeof(*fmts16)); i++)
             {
                 fmt_idx = getFmtIdx(fmts16[i]);
-                gl_info->gl_formats[fmt_idx].Flags |= WINED3DFMT_FLAG_FILTERING;
+                gl_info->formats[fmt_idx].Flags |= WINED3DFMT_FLAG_FILTERING;
             }
         }
         return;
@@ -1308,14 +1335,14 @@ static void init_format_filter_info(struct wined3d_gl_info *gl_info, enum wined3
     for(i = 0; i < (sizeof(fmts16) / sizeof(*fmts16)); i++)
     {
         fmt_idx = getFmtIdx(fmts16[i]);
-        desc = &gl_info->gl_formats[fmt_idx];
-        if(!desc->glInternal) continue; /* Not supported by GL */
+        format = &gl_info->formats[fmt_idx];
+        if (!format->glInternal) continue; /* Not supported by GL */
 
-        filtered = check_filter(gl_info, gl_info->gl_formats[fmt_idx].glInternal);
+        filtered = check_filter(gl_info, gl_info->formats[fmt_idx].glInternal);
         if(filtered)
         {
             TRACE("Format %s supports filtering\n", debug_d3dformat(fmts16[i]));
-            desc->Flags |= WINED3DFMT_FLAG_FILTERING;
+            format->Flags |= WINED3DFMT_FLAG_FILTERING;
         }
         else
         {
@@ -1329,23 +1356,23 @@ static void apply_format_fixups(struct wined3d_gl_info *gl_info)
     int idx;
 
     idx = getFmtIdx(WINED3DFMT_R16_FLOAT);
-    gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+    gl_info->formats[idx].color_fixup = create_color_fixup_desc(
             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
 
     idx = getFmtIdx(WINED3DFMT_R32_FLOAT);
-    gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+    gl_info->formats[idx].color_fixup = create_color_fixup_desc(
             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
 
     idx = getFmtIdx(WINED3DFMT_R16G16_UNORM);
-    gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+    gl_info->formats[idx].color_fixup = create_color_fixup_desc(
             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
 
     idx = getFmtIdx(WINED3DFMT_R16G16_FLOAT);
-    gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+    gl_info->formats[idx].color_fixup = create_color_fixup_desc(
             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
 
     idx = getFmtIdx(WINED3DFMT_R32G32_FLOAT);
-    gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+    gl_info->formats[idx].color_fixup = create_color_fixup_desc(
             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
 
     /* V8U8 is supported natively by GL_ATI_envmap_bumpmap and GL_NV_texture_shader.
@@ -1360,20 +1387,20 @@ static void apply_format_fixups(struct wined3d_gl_info *gl_info)
     if (!gl_info->supported[NV_TEXTURE_SHADER])
     {
         idx = getFmtIdx(WINED3DFMT_R8G8_SNORM);
-        gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+        gl_info->formats[idx].color_fixup = create_color_fixup_desc(
                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
         idx = getFmtIdx(WINED3DFMT_R16G16_SNORM);
-        gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+        gl_info->formats[idx].color_fixup = create_color_fixup_desc(
                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
     }
     else
     {
         idx = getFmtIdx(WINED3DFMT_R8G8_SNORM);
-        gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+        gl_info->formats[idx].color_fixup = create_color_fixup_desc(
                 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
 
         idx = getFmtIdx(WINED3DFMT_R16G16_SNORM);
-        gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+        gl_info->formats[idx].color_fixup = create_color_fixup_desc(
                 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
     }
 
@@ -1383,13 +1410,13 @@ static void apply_format_fixups(struct wined3d_gl_info *gl_info)
          * with each other
          */
         idx = getFmtIdx(WINED3DFMT_R5G5_SNORM_L6_UNORM);
-        gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+        gl_info->formats[idx].color_fixup = create_color_fixup_desc(
                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Z, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE);
         idx = getFmtIdx(WINED3DFMT_R8G8_SNORM_L8X8_UNORM);
-        gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+        gl_info->formats[idx].color_fixup = create_color_fixup_desc(
                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_Z, 0, CHANNEL_SOURCE_W);
         idx = getFmtIdx(WINED3DFMT_R8G8B8A8_SNORM);
-        gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+        gl_info->formats[idx].color_fixup = create_color_fixup_desc(
                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 1, CHANNEL_SOURCE_Z, 1, CHANNEL_SOURCE_W);
     }
     else
@@ -1404,39 +1431,39 @@ static void apply_format_fixups(struct wined3d_gl_info *gl_info)
     if (gl_info->supported[EXT_TEXTURE_COMPRESSION_RGTC])
     {
         idx = getFmtIdx(WINED3DFMT_ATI2N);
-        gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
+        gl_info->formats[idx].color_fixup = create_color_fixup_desc(
                 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
     }
     else if (gl_info->supported[ATI_TEXTURE_COMPRESSION_3DC])
     {
         idx = getFmtIdx(WINED3DFMT_ATI2N);
-        gl_info->gl_formats[idx].color_fixup= create_color_fixup_desc(
+        gl_info->formats[idx].color_fixup= create_color_fixup_desc(
                 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_W, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
     }
 
     if (!gl_info->supported[APPLE_YCBCR_422])
     {
         idx = getFmtIdx(WINED3DFMT_YUY2);
-        gl_info->gl_formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_YUY2);
+        gl_info->formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_YUY2);
 
         idx = getFmtIdx(WINED3DFMT_UYVY);
-        gl_info->gl_formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_UYVY);
+        gl_info->formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_UYVY);
     }
 
     idx = getFmtIdx(WINED3DFMT_YV12);
-    gl_info->gl_formats[idx].heightscale = 1.5f;
-    gl_info->gl_formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_YV12);
+    gl_info->formats[idx].heightscale = 1.5f;
+    gl_info->formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_YV12);
 
     if (gl_info->supported[EXT_PALETTED_TEXTURE] || gl_info->supported[ARB_FRAGMENT_PROGRAM])
     {
         idx = getFmtIdx(WINED3DFMT_P8_UINT);
-        gl_info->gl_formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_P8);
+        gl_info->formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_P8);
     }
 
     if (gl_info->supported[ARB_VERTEX_ARRAY_BGRA])
     {
         idx = getFmtIdx(WINED3DFMT_B8G8R8A8_UNORM);
-        gl_info->gl_formats[idx].gl_vtx_format = GL_BGRA;
+        gl_info->formats[idx].gl_vtx_format = GL_BGRA;
     }
 
     if (gl_info->supported[ARB_HALF_FLOAT_VERTEX])
@@ -1444,10 +1471,10 @@ static void apply_format_fixups(struct wined3d_gl_info *gl_info)
         /* Do not change the size of the type, it is CPU side. We have to change the GPU-side information though.
          * It is the job of the vertex buffer code to make sure that the vbos have the right format */
         idx = getFmtIdx(WINED3DFMT_R16G16_FLOAT);
-        gl_info->gl_formats[idx].gl_vtx_type = GL_HALF_FLOAT; /* == GL_HALF_FLOAT_NV */
+        gl_info->formats[idx].gl_vtx_type = GL_HALF_FLOAT; /* == GL_HALF_FLOAT_NV */
 
         idx = getFmtIdx(WINED3DFMT_R16G16B16A16_FLOAT);
-        gl_info->gl_formats[idx].gl_vtx_type = GL_HALF_FLOAT;
+        gl_info->formats[idx].gl_vtx_type = GL_HALF_FLOAT;
     }
 }
 
@@ -1457,23 +1484,23 @@ static BOOL init_format_vertex_info(struct wined3d_gl_info *gl_info)
 
     for (i = 0; i < (sizeof(format_vertex_info) / sizeof(*format_vertex_info)); ++i)
     {
-        struct wined3d_format_desc *format_desc;
-        int fmt_idx = getFmtIdx(format_vertex_info[i].format);
+        struct wined3d_format *format;
+        int fmt_idx = getFmtIdx(format_vertex_info[i].id);
 
         if (fmt_idx == -1)
         {
             ERR("Format %s (%#x) not found.\n",
-                    debug_d3dformat(format_vertex_info[i].format), format_vertex_info[i].format);
+                    debug_d3dformat(format_vertex_info[i].id), format_vertex_info[i].id);
             return FALSE;
         }
 
-        format_desc = &gl_info->gl_formats[fmt_idx];
-        format_desc->emit_idx = format_vertex_info[i].emit_idx;
-        format_desc->component_count = format_vertex_info[i].component_count;
-        format_desc->gl_vtx_type = format_vertex_info[i].gl_vtx_type;
-        format_desc->gl_vtx_format = format_vertex_info[i].gl_vtx_format;
-        format_desc->gl_normalized = format_vertex_info[i].gl_normalized;
-        format_desc->component_size = format_vertex_info[i].component_size;
+        format = &gl_info->formats[fmt_idx];
+        format->emit_idx = format_vertex_info[i].emit_idx;
+        format->component_count = format_vertex_info[i].component_count;
+        format->gl_vtx_type = format_vertex_info[i].gl_vtx_type;
+        format->gl_vtx_format = format_vertex_info[i].gl_vtx_format;
+        format->gl_normalized = format_vertex_info[i].gl_normalized;
+        format->component_size = format_vertex_info[i].component_size;
     }
 
     return TRUE;
@@ -1485,8 +1512,8 @@ BOOL initPixelFormatsNoGL(struct wined3d_gl_info *gl_info)
 
     if (!init_format_compression_info(gl_info))
     {
-        HeapFree(GetProcessHeap(), 0, gl_info->gl_formats);
-        gl_info->gl_formats = NULL;
+        HeapFree(GetProcessHeap(), 0, gl_info->formats);
+        gl_info->formats = NULL;
         return FALSE;
     }
 
@@ -1509,194 +1536,226 @@ BOOL initPixelFormats(struct wined3d_gl_info *gl_info, enum wined3d_pci_vendor v
     return TRUE;
 
 fail:
-    HeapFree(GetProcessHeap(), 0, gl_info->gl_formats);
-    gl_info->gl_formats = NULL;
+    HeapFree(GetProcessHeap(), 0, gl_info->formats);
+    gl_info->formats = NULL;
     return FALSE;
 }
 
-const struct wined3d_format_desc *getFormatDescEntry(WINED3DFORMAT fmt, const struct wined3d_gl_info *gl_info)
+const struct wined3d_format *wined3d_get_format(const struct wined3d_gl_info *gl_info,
+        enum wined3d_format_id format_id)
 {
-    int idx = getFmtIdx(fmt);
+    int idx = getFmtIdx(format_id);
 
-    if(idx == -1) {
-        FIXME("Can't find format %s(%d) in the format lookup table\n", debug_d3dformat(fmt), fmt);
+    if (idx == -1)
+    {
+        FIXME("Can't find format %s (%#x) in the format lookup table\n",
+                debug_d3dformat(format_id), format_id);
         /* Get the caller a valid pointer */
         idx = getFmtIdx(WINED3DFMT_UNKNOWN);
     }
 
-    return &gl_info->gl_formats[idx];
+    return &gl_info->formats[idx];
+}
+
+UINT wined3d_format_calculate_size(const struct wined3d_format *format, UINT alignment, UINT width, UINT height)
+{
+    UINT size;
+
+    if (format->id == WINED3DFMT_UNKNOWN)
+    {
+        size = 0;
+    }
+    else if (format->Flags & WINED3DFMT_FLAG_COMPRESSED)
+    {
+        UINT row_block_count = (width + format->block_width - 1) / format->block_width;
+        UINT row_count = (height + format->block_height - 1) / format->block_height;
+        size = row_count * (((row_block_count * format->block_byte_count) + alignment - 1) & ~(alignment - 1));
+    }
+    else
+    {
+        size = height * (((width * format->byte_count) + alignment - 1) & ~(alignment - 1));
+    }
+
+    if (format->heightscale != 0.0f) size *= format->heightscale;
+
+    return size;
 }
 
 /*****************************************************************************
  * Trace formatting of useful values
  */
-const char* debug_d3dformat(WINED3DFORMAT fmt) {
-  switch (fmt) {
-#define FMT_TO_STR(fmt) case fmt: return #fmt
-    FMT_TO_STR(WINED3DFMT_UNKNOWN);
-    FMT_TO_STR(WINED3DFMT_B8G8R8_UNORM);
-    FMT_TO_STR(WINED3DFMT_B5G5R5X1_UNORM);
-    FMT_TO_STR(WINED3DFMT_B4G4R4A4_UNORM);
-    FMT_TO_STR(WINED3DFMT_B2G3R3_UNORM);
-    FMT_TO_STR(WINED3DFMT_B2G3R3A8_UNORM);
-    FMT_TO_STR(WINED3DFMT_B4G4R4X4_UNORM);
-    FMT_TO_STR(WINED3DFMT_R8G8B8X8_UNORM);
-    FMT_TO_STR(WINED3DFMT_B10G10R10A2_UNORM);
-    FMT_TO_STR(WINED3DFMT_P8_UINT_A8_UNORM);
-    FMT_TO_STR(WINED3DFMT_P8_UINT);
-    FMT_TO_STR(WINED3DFMT_L8_UNORM);
-    FMT_TO_STR(WINED3DFMT_L8A8_UNORM);
-    FMT_TO_STR(WINED3DFMT_L4A4_UNORM);
-    FMT_TO_STR(WINED3DFMT_R5G5_SNORM_L6_UNORM);
-    FMT_TO_STR(WINED3DFMT_R8G8_SNORM_L8X8_UNORM);
-    FMT_TO_STR(WINED3DFMT_R10G11B11_SNORM);
-    FMT_TO_STR(WINED3DFMT_R10G10B10_SNORM_A2_UNORM);
-    FMT_TO_STR(WINED3DFMT_UYVY);
-    FMT_TO_STR(WINED3DFMT_YUY2);
-    FMT_TO_STR(WINED3DFMT_YV12);
-    FMT_TO_STR(WINED3DFMT_DXT1);
-    FMT_TO_STR(WINED3DFMT_DXT2);
-    FMT_TO_STR(WINED3DFMT_DXT3);
-    FMT_TO_STR(WINED3DFMT_DXT4);
-    FMT_TO_STR(WINED3DFMT_DXT5);
-    FMT_TO_STR(WINED3DFMT_MULTI2_ARGB8);
-    FMT_TO_STR(WINED3DFMT_G8R8_G8B8);
-    FMT_TO_STR(WINED3DFMT_R8G8_B8G8);
-    FMT_TO_STR(WINED3DFMT_D16_LOCKABLE);
-    FMT_TO_STR(WINED3DFMT_D32_UNORM);
-    FMT_TO_STR(WINED3DFMT_S1_UINT_D15_UNORM);
-    FMT_TO_STR(WINED3DFMT_X8D24_UNORM);
-    FMT_TO_STR(WINED3DFMT_S4X4_UINT_D24_UNORM);
-    FMT_TO_STR(WINED3DFMT_L16_UNORM);
-    FMT_TO_STR(WINED3DFMT_S8_UINT_D24_FLOAT);
-    FMT_TO_STR(WINED3DFMT_VERTEXDATA);
-    FMT_TO_STR(WINED3DFMT_R8G8_SNORM_Cx);
-    FMT_TO_STR(WINED3DFMT_ATI2N);
-    FMT_TO_STR(WINED3DFMT_NVHU);
-    FMT_TO_STR(WINED3DFMT_NVHS);
-    FMT_TO_STR(WINED3DFMT_R32G32B32A32_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R32G32B32A32_FLOAT);
-    FMT_TO_STR(WINED3DFMT_R32G32B32A32_UINT);
-    FMT_TO_STR(WINED3DFMT_R32G32B32A32_SINT);
-    FMT_TO_STR(WINED3DFMT_R32G32B32_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R32G32B32_FLOAT);
-    FMT_TO_STR(WINED3DFMT_R32G32B32_UINT);
-    FMT_TO_STR(WINED3DFMT_R32G32B32_SINT);
-    FMT_TO_STR(WINED3DFMT_R16G16B16A16_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R16G16B16A16_FLOAT);
-    FMT_TO_STR(WINED3DFMT_R16G16B16A16_UNORM);
-    FMT_TO_STR(WINED3DFMT_R16G16B16A16_UINT);
-    FMT_TO_STR(WINED3DFMT_R16G16B16A16_SNORM);
-    FMT_TO_STR(WINED3DFMT_R16G16B16A16_SINT);
-    FMT_TO_STR(WINED3DFMT_R32G32_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R32G32_FLOAT);
-    FMT_TO_STR(WINED3DFMT_R32G32_UINT);
-    FMT_TO_STR(WINED3DFMT_R32G32_SINT);
-    FMT_TO_STR(WINED3DFMT_R32G8X24_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_D32_FLOAT_S8X24_UINT);
-    FMT_TO_STR(WINED3DFMT_R32_FLOAT_X8X24_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_X32_TYPELESS_G8X24_UINT);
-    FMT_TO_STR(WINED3DFMT_R10G10B10A2_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R10G10B10A2_UNORM);
-    FMT_TO_STR(WINED3DFMT_R10G10B10A2_UINT);
-    FMT_TO_STR(WINED3DFMT_R10G10B10A2_SNORM);
-    FMT_TO_STR(WINED3DFMT_R11G11B10_FLOAT);
-    FMT_TO_STR(WINED3DFMT_R8G8B8A8_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R8G8B8A8_UNORM);
-    FMT_TO_STR(WINED3DFMT_R8G8B8A8_UNORM_SRGB);
-    FMT_TO_STR(WINED3DFMT_R8G8B8A8_UINT);
-    FMT_TO_STR(WINED3DFMT_R8G8B8A8_SNORM);
-    FMT_TO_STR(WINED3DFMT_R8G8B8A8_SINT);
-    FMT_TO_STR(WINED3DFMT_R16G16_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R16G16_FLOAT);
-    FMT_TO_STR(WINED3DFMT_R16G16_UNORM);
-    FMT_TO_STR(WINED3DFMT_R16G16_UINT);
-    FMT_TO_STR(WINED3DFMT_R16G16_SNORM);
-    FMT_TO_STR(WINED3DFMT_R16G16_SINT);
-    FMT_TO_STR(WINED3DFMT_R32_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_D32_FLOAT);
-    FMT_TO_STR(WINED3DFMT_R32_FLOAT);
-    FMT_TO_STR(WINED3DFMT_R32_UINT);
-    FMT_TO_STR(WINED3DFMT_R32_SINT);
-    FMT_TO_STR(WINED3DFMT_R24G8_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_D24_UNORM_S8_UINT);
-    FMT_TO_STR(WINED3DFMT_R24_UNORM_X8_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_X24_TYPELESS_G8_UINT);
-    FMT_TO_STR(WINED3DFMT_R8G8_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R8G8_UNORM);
-    FMT_TO_STR(WINED3DFMT_R8G8_UINT);
-    FMT_TO_STR(WINED3DFMT_R8G8_SNORM);
-    FMT_TO_STR(WINED3DFMT_R8G8_SINT);
-    FMT_TO_STR(WINED3DFMT_R16_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R16_FLOAT);
-    FMT_TO_STR(WINED3DFMT_D16_UNORM);
-    FMT_TO_STR(WINED3DFMT_R16_UNORM);
-    FMT_TO_STR(WINED3DFMT_R16_UINT);
-    FMT_TO_STR(WINED3DFMT_R16_SNORM);
-    FMT_TO_STR(WINED3DFMT_R16_SINT);
-    FMT_TO_STR(WINED3DFMT_R8_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_R8_UNORM);
-    FMT_TO_STR(WINED3DFMT_R8_UINT);
-    FMT_TO_STR(WINED3DFMT_R8_SNORM);
-    FMT_TO_STR(WINED3DFMT_R8_SINT);
-    FMT_TO_STR(WINED3DFMT_A8_UNORM);
-    FMT_TO_STR(WINED3DFMT_R1_UNORM);
-    FMT_TO_STR(WINED3DFMT_R9G9B9E5_SHAREDEXP);
-    FMT_TO_STR(WINED3DFMT_R8G8_B8G8_UNORM);
-    FMT_TO_STR(WINED3DFMT_G8R8_G8B8_UNORM);
-    FMT_TO_STR(WINED3DFMT_BC1_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_BC1_UNORM);
-    FMT_TO_STR(WINED3DFMT_BC1_UNORM_SRGB);
-    FMT_TO_STR(WINED3DFMT_BC2_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_BC2_UNORM);
-    FMT_TO_STR(WINED3DFMT_BC2_UNORM_SRGB);
-    FMT_TO_STR(WINED3DFMT_BC3_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_BC3_UNORM);
-    FMT_TO_STR(WINED3DFMT_BC3_UNORM_SRGB);
-    FMT_TO_STR(WINED3DFMT_BC4_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_BC4_UNORM);
-    FMT_TO_STR(WINED3DFMT_BC4_SNORM);
-    FMT_TO_STR(WINED3DFMT_BC5_TYPELESS);
-    FMT_TO_STR(WINED3DFMT_BC5_UNORM);
-    FMT_TO_STR(WINED3DFMT_BC5_SNORM);
-    FMT_TO_STR(WINED3DFMT_B5G6R5_UNORM);
-    FMT_TO_STR(WINED3DFMT_B5G5R5A1_UNORM);
-    FMT_TO_STR(WINED3DFMT_B8G8R8A8_UNORM);
-    FMT_TO_STR(WINED3DFMT_B8G8R8X8_UNORM);
-#undef FMT_TO_STR
-  default:
+const char *debug_d3dformat(enum wined3d_format_id format_id)
+{
+    switch (format_id)
     {
-      char fourcc[5];
-      fourcc[0] = (char)(fmt);
-      fourcc[1] = (char)(fmt >> 8);
-      fourcc[2] = (char)(fmt >> 16);
-      fourcc[3] = (char)(fmt >> 24);
-      fourcc[4] = 0;
-      if( isprint(fourcc[0]) && isprint(fourcc[1]) && isprint(fourcc[2]) && isprint(fourcc[3]) )
-        FIXME("Unrecognized %u (as fourcc: %s) WINED3DFORMAT!\n", fmt, fourcc);
-      else
-        FIXME("Unrecognized %u WINED3DFORMAT!\n", fmt);
+#define FMT_TO_STR(format_id) case format_id: return #format_id
+        FMT_TO_STR(WINED3DFMT_UNKNOWN);
+        FMT_TO_STR(WINED3DFMT_B8G8R8_UNORM);
+        FMT_TO_STR(WINED3DFMT_B5G5R5X1_UNORM);
+        FMT_TO_STR(WINED3DFMT_B4G4R4A4_UNORM);
+        FMT_TO_STR(WINED3DFMT_B2G3R3_UNORM);
+        FMT_TO_STR(WINED3DFMT_B2G3R3A8_UNORM);
+        FMT_TO_STR(WINED3DFMT_B4G4R4X4_UNORM);
+        FMT_TO_STR(WINED3DFMT_R8G8B8X8_UNORM);
+        FMT_TO_STR(WINED3DFMT_B10G10R10A2_UNORM);
+        FMT_TO_STR(WINED3DFMT_P8_UINT_A8_UNORM);
+        FMT_TO_STR(WINED3DFMT_P8_UINT);
+        FMT_TO_STR(WINED3DFMT_L8_UNORM);
+        FMT_TO_STR(WINED3DFMT_L8A8_UNORM);
+        FMT_TO_STR(WINED3DFMT_L4A4_UNORM);
+        FMT_TO_STR(WINED3DFMT_R5G5_SNORM_L6_UNORM);
+        FMT_TO_STR(WINED3DFMT_R8G8_SNORM_L8X8_UNORM);
+        FMT_TO_STR(WINED3DFMT_R10G11B11_SNORM);
+        FMT_TO_STR(WINED3DFMT_R10G10B10_SNORM_A2_UNORM);
+        FMT_TO_STR(WINED3DFMT_UYVY);
+        FMT_TO_STR(WINED3DFMT_YUY2);
+        FMT_TO_STR(WINED3DFMT_YV12);
+        FMT_TO_STR(WINED3DFMT_DXT1);
+        FMT_TO_STR(WINED3DFMT_DXT2);
+        FMT_TO_STR(WINED3DFMT_DXT3);
+        FMT_TO_STR(WINED3DFMT_DXT4);
+        FMT_TO_STR(WINED3DFMT_DXT5);
+        FMT_TO_STR(WINED3DFMT_MULTI2_ARGB8);
+        FMT_TO_STR(WINED3DFMT_G8R8_G8B8);
+        FMT_TO_STR(WINED3DFMT_R8G8_B8G8);
+        FMT_TO_STR(WINED3DFMT_D16_LOCKABLE);
+        FMT_TO_STR(WINED3DFMT_D32_UNORM);
+        FMT_TO_STR(WINED3DFMT_S1_UINT_D15_UNORM);
+        FMT_TO_STR(WINED3DFMT_X8D24_UNORM);
+        FMT_TO_STR(WINED3DFMT_S4X4_UINT_D24_UNORM);
+        FMT_TO_STR(WINED3DFMT_L16_UNORM);
+        FMT_TO_STR(WINED3DFMT_S8_UINT_D24_FLOAT);
+        FMT_TO_STR(WINED3DFMT_VERTEXDATA);
+        FMT_TO_STR(WINED3DFMT_R8G8_SNORM_Cx);
+        FMT_TO_STR(WINED3DFMT_ATI2N);
+        FMT_TO_STR(WINED3DFMT_NVDB);
+        FMT_TO_STR(WINED3DFMT_NVHU);
+        FMT_TO_STR(WINED3DFMT_NVHS);
+        FMT_TO_STR(WINED3DFMT_R32G32B32A32_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R32G32B32A32_FLOAT);
+        FMT_TO_STR(WINED3DFMT_R32G32B32A32_UINT);
+        FMT_TO_STR(WINED3DFMT_R32G32B32A32_SINT);
+        FMT_TO_STR(WINED3DFMT_R32G32B32_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R32G32B32_FLOAT);
+        FMT_TO_STR(WINED3DFMT_R32G32B32_UINT);
+        FMT_TO_STR(WINED3DFMT_R32G32B32_SINT);
+        FMT_TO_STR(WINED3DFMT_R16G16B16A16_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R16G16B16A16_FLOAT);
+        FMT_TO_STR(WINED3DFMT_R16G16B16A16_UNORM);
+        FMT_TO_STR(WINED3DFMT_R16G16B16A16_UINT);
+        FMT_TO_STR(WINED3DFMT_R16G16B16A16_SNORM);
+        FMT_TO_STR(WINED3DFMT_R16G16B16A16_SINT);
+        FMT_TO_STR(WINED3DFMT_R32G32_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R32G32_FLOAT);
+        FMT_TO_STR(WINED3DFMT_R32G32_UINT);
+        FMT_TO_STR(WINED3DFMT_R32G32_SINT);
+        FMT_TO_STR(WINED3DFMT_R32G8X24_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_D32_FLOAT_S8X24_UINT);
+        FMT_TO_STR(WINED3DFMT_R32_FLOAT_X8X24_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_X32_TYPELESS_G8X24_UINT);
+        FMT_TO_STR(WINED3DFMT_R10G10B10A2_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R10G10B10A2_UNORM);
+        FMT_TO_STR(WINED3DFMT_R10G10B10A2_UINT);
+        FMT_TO_STR(WINED3DFMT_R10G10B10A2_SNORM);
+        FMT_TO_STR(WINED3DFMT_R11G11B10_FLOAT);
+        FMT_TO_STR(WINED3DFMT_R8G8B8A8_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R8G8B8A8_UNORM);
+        FMT_TO_STR(WINED3DFMT_R8G8B8A8_UNORM_SRGB);
+        FMT_TO_STR(WINED3DFMT_R8G8B8A8_UINT);
+        FMT_TO_STR(WINED3DFMT_R8G8B8A8_SNORM);
+        FMT_TO_STR(WINED3DFMT_R8G8B8A8_SINT);
+        FMT_TO_STR(WINED3DFMT_R16G16_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R16G16_FLOAT);
+        FMT_TO_STR(WINED3DFMT_R16G16_UNORM);
+        FMT_TO_STR(WINED3DFMT_R16G16_UINT);
+        FMT_TO_STR(WINED3DFMT_R16G16_SNORM);
+        FMT_TO_STR(WINED3DFMT_R16G16_SINT);
+        FMT_TO_STR(WINED3DFMT_R32_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_D32_FLOAT);
+        FMT_TO_STR(WINED3DFMT_R32_FLOAT);
+        FMT_TO_STR(WINED3DFMT_R32_UINT);
+        FMT_TO_STR(WINED3DFMT_R32_SINT);
+        FMT_TO_STR(WINED3DFMT_R24G8_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_D24_UNORM_S8_UINT);
+        FMT_TO_STR(WINED3DFMT_R24_UNORM_X8_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_X24_TYPELESS_G8_UINT);
+        FMT_TO_STR(WINED3DFMT_R8G8_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R8G8_UNORM);
+        FMT_TO_STR(WINED3DFMT_R8G8_UINT);
+        FMT_TO_STR(WINED3DFMT_R8G8_SNORM);
+        FMT_TO_STR(WINED3DFMT_R8G8_SINT);
+        FMT_TO_STR(WINED3DFMT_R16_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R16_FLOAT);
+        FMT_TO_STR(WINED3DFMT_D16_UNORM);
+        FMT_TO_STR(WINED3DFMT_R16_UNORM);
+        FMT_TO_STR(WINED3DFMT_R16_UINT);
+        FMT_TO_STR(WINED3DFMT_R16_SNORM);
+        FMT_TO_STR(WINED3DFMT_R16_SINT);
+        FMT_TO_STR(WINED3DFMT_R8_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_R8_UNORM);
+        FMT_TO_STR(WINED3DFMT_R8_UINT);
+        FMT_TO_STR(WINED3DFMT_R8_SNORM);
+        FMT_TO_STR(WINED3DFMT_R8_SINT);
+        FMT_TO_STR(WINED3DFMT_A8_UNORM);
+        FMT_TO_STR(WINED3DFMT_R1_UNORM);
+        FMT_TO_STR(WINED3DFMT_R9G9B9E5_SHAREDEXP);
+        FMT_TO_STR(WINED3DFMT_R8G8_B8G8_UNORM);
+        FMT_TO_STR(WINED3DFMT_G8R8_G8B8_UNORM);
+        FMT_TO_STR(WINED3DFMT_BC1_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_BC1_UNORM);
+        FMT_TO_STR(WINED3DFMT_BC1_UNORM_SRGB);
+        FMT_TO_STR(WINED3DFMT_BC2_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_BC2_UNORM);
+        FMT_TO_STR(WINED3DFMT_BC2_UNORM_SRGB);
+        FMT_TO_STR(WINED3DFMT_BC3_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_BC3_UNORM);
+        FMT_TO_STR(WINED3DFMT_BC3_UNORM_SRGB);
+        FMT_TO_STR(WINED3DFMT_BC4_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_BC4_UNORM);
+        FMT_TO_STR(WINED3DFMT_BC4_SNORM);
+        FMT_TO_STR(WINED3DFMT_BC5_TYPELESS);
+        FMT_TO_STR(WINED3DFMT_BC5_UNORM);
+        FMT_TO_STR(WINED3DFMT_BC5_SNORM);
+        FMT_TO_STR(WINED3DFMT_B5G6R5_UNORM);
+        FMT_TO_STR(WINED3DFMT_B5G5R5A1_UNORM);
+        FMT_TO_STR(WINED3DFMT_B8G8R8A8_UNORM);
+        FMT_TO_STR(WINED3DFMT_B8G8R8X8_UNORM);
+#undef FMT_TO_STR
+        default:
+        {
+            char fourcc[5];
+            fourcc[0] = (char)(format_id);
+            fourcc[1] = (char)(format_id >> 8);
+            fourcc[2] = (char)(format_id >> 16);
+            fourcc[3] = (char)(format_id >> 24);
+            fourcc[4] = 0;
+            if (isprint(fourcc[0]) && isprint(fourcc[1]) && isprint(fourcc[2]) && isprint(fourcc[3]))
+                FIXME("Unrecognized %#x (as fourcc: %s) WINED3DFORMAT!\n", format_id, fourcc);
+            else
+                FIXME("Unrecognized %#x WINED3DFORMAT!\n", format_id);
+        }
+        return "unrecognized";
     }
-    return "unrecognized";
-  }
 }
 
-const char* debug_d3ddevicetype(WINED3DDEVTYPE devtype) {
-  switch (devtype) {
+const char *debug_d3ddevicetype(WINED3DDEVTYPE devtype)
+{
+    switch (devtype)
+    {
 #define DEVTYPE_TO_STR(dev) case dev: return #dev
-    DEVTYPE_TO_STR(WINED3DDEVTYPE_HAL);
-    DEVTYPE_TO_STR(WINED3DDEVTYPE_REF);
-    DEVTYPE_TO_STR(WINED3DDEVTYPE_SW);
+        DEVTYPE_TO_STR(WINED3DDEVTYPE_HAL);
+        DEVTYPE_TO_STR(WINED3DDEVTYPE_REF);
+        DEVTYPE_TO_STR(WINED3DDEVTYPE_SW);
 #undef DEVTYPE_TO_STR
-  default:
-    FIXME("Unrecognized %u WINED3DDEVTYPE!\n", devtype);
-    return "unrecognized";
-  }
+        default:
+            FIXME("Unrecognized %u WINED3DDEVTYPE!\n", devtype);
+            return "unrecognized";
+    }
 }
 
 const char *debug_d3dusage(DWORD usage)
 {
-    char buf[284];
+    char buf[333];
 
     buf[0] = '\0';
 #define WINED3DUSAGE_TO_STR(u) if (usage & u) { strcat(buf, " | "#u); usage &= ~u; }
@@ -1711,6 +1770,8 @@ const char *debug_d3dusage(DWORD usage)
     WINED3DUSAGE_TO_STR(WINED3DUSAGE_DYNAMIC);
     WINED3DUSAGE_TO_STR(WINED3DUSAGE_AUTOGENMIPMAP);
     WINED3DUSAGE_TO_STR(WINED3DUSAGE_DMAP);
+    WINED3DUSAGE_TO_STR(WINED3DUSAGE_STATICDECL);
+    WINED3DUSAGE_TO_STR(WINED3DUSAGE_OVERLAY);
 #undef WINED3DUSAGE_TO_STR
     if (usage) FIXME("Unrecognized usage flag(s) %#x\n", usage);
 
@@ -1777,201 +1838,209 @@ const char* debug_d3ddeclusage(BYTE usage) {
     }
 }
 
-const char* debug_d3dresourcetype(WINED3DRESOURCETYPE res) {
-  switch (res) {
+const char *debug_d3dresourcetype(WINED3DRESOURCETYPE res)
+{
+    switch (res)
+    {
 #define RES_TO_STR(res) case res: return #res
-    RES_TO_STR(WINED3DRTYPE_SURFACE);
-    RES_TO_STR(WINED3DRTYPE_VOLUME);
-    RES_TO_STR(WINED3DRTYPE_TEXTURE);
-    RES_TO_STR(WINED3DRTYPE_VOLUMETEXTURE);
-    RES_TO_STR(WINED3DRTYPE_CUBETEXTURE);
-    RES_TO_STR(WINED3DRTYPE_BUFFER);
+        RES_TO_STR(WINED3DRTYPE_SURFACE);
+        RES_TO_STR(WINED3DRTYPE_VOLUME);
+        RES_TO_STR(WINED3DRTYPE_TEXTURE);
+        RES_TO_STR(WINED3DRTYPE_VOLUMETEXTURE);
+        RES_TO_STR(WINED3DRTYPE_CUBETEXTURE);
+        RES_TO_STR(WINED3DRTYPE_BUFFER);
 #undef  RES_TO_STR
-  default:
-    FIXME("Unrecognized %u WINED3DRESOURCETYPE!\n", res);
-    return "unrecognized";
-  }
+        default:
+            FIXME("Unrecognized %u WINED3DRESOURCETYPE!\n", res);
+            return "unrecognized";
+    }
 }
 
-const char* debug_d3dprimitivetype(WINED3DPRIMITIVETYPE PrimitiveType) {
-  switch (PrimitiveType) {
+const char *debug_d3dprimitivetype(WINED3DPRIMITIVETYPE PrimitiveType)
+{
+    switch (PrimitiveType)
+    {
 #define PRIM_TO_STR(prim) case prim: return #prim
-    PRIM_TO_STR(WINED3DPT_UNDEFINED);
-    PRIM_TO_STR(WINED3DPT_POINTLIST);
-    PRIM_TO_STR(WINED3DPT_LINELIST);
-    PRIM_TO_STR(WINED3DPT_LINESTRIP);
-    PRIM_TO_STR(WINED3DPT_TRIANGLELIST);
-    PRIM_TO_STR(WINED3DPT_TRIANGLESTRIP);
-    PRIM_TO_STR(WINED3DPT_TRIANGLEFAN);
-    PRIM_TO_STR(WINED3DPT_LINELIST_ADJ);
-    PRIM_TO_STR(WINED3DPT_LINESTRIP_ADJ);
-    PRIM_TO_STR(WINED3DPT_TRIANGLELIST_ADJ);
-    PRIM_TO_STR(WINED3DPT_TRIANGLESTRIP_ADJ);
+        PRIM_TO_STR(WINED3DPT_UNDEFINED);
+        PRIM_TO_STR(WINED3DPT_POINTLIST);
+        PRIM_TO_STR(WINED3DPT_LINELIST);
+        PRIM_TO_STR(WINED3DPT_LINESTRIP);
+        PRIM_TO_STR(WINED3DPT_TRIANGLELIST);
+        PRIM_TO_STR(WINED3DPT_TRIANGLESTRIP);
+        PRIM_TO_STR(WINED3DPT_TRIANGLEFAN);
+        PRIM_TO_STR(WINED3DPT_LINELIST_ADJ);
+        PRIM_TO_STR(WINED3DPT_LINESTRIP_ADJ);
+        PRIM_TO_STR(WINED3DPT_TRIANGLELIST_ADJ);
+        PRIM_TO_STR(WINED3DPT_TRIANGLESTRIP_ADJ);
 #undef  PRIM_TO_STR
-  default:
-    FIXME("Unrecognized %u WINED3DPRIMITIVETYPE!\n", PrimitiveType);
-    return "unrecognized";
-  }
+        default:
+            FIXME("Unrecognized %u WINED3DPRIMITIVETYPE!\n", PrimitiveType);
+            return "unrecognized";
+    }
 }
 
-const char* debug_d3drenderstate(DWORD state) {
-  switch (state) {
+const char *debug_d3drenderstate(WINED3DRENDERSTATETYPE state)
+{
+    switch (state)
+    {
 #define D3DSTATE_TO_STR(u) case u: return #u
-    D3DSTATE_TO_STR(WINED3DRS_ANTIALIAS                 );
-    D3DSTATE_TO_STR(WINED3DRS_TEXTUREPERSPECTIVE        );
-    D3DSTATE_TO_STR(WINED3DRS_WRAPU                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAPV                     );
-    D3DSTATE_TO_STR(WINED3DRS_ZENABLE                   );
-    D3DSTATE_TO_STR(WINED3DRS_FILLMODE                  );
-    D3DSTATE_TO_STR(WINED3DRS_SHADEMODE                 );
-    D3DSTATE_TO_STR(WINED3DRS_LINEPATTERN               );
-    D3DSTATE_TO_STR(WINED3DRS_MONOENABLE                );
-    D3DSTATE_TO_STR(WINED3DRS_ROP2                      );
-    D3DSTATE_TO_STR(WINED3DRS_PLANEMASK                 );
-    D3DSTATE_TO_STR(WINED3DRS_ZWRITEENABLE              );
-    D3DSTATE_TO_STR(WINED3DRS_ALPHATESTENABLE           );
-    D3DSTATE_TO_STR(WINED3DRS_LASTPIXEL                 );
-    D3DSTATE_TO_STR(WINED3DRS_SRCBLEND                  );
-    D3DSTATE_TO_STR(WINED3DRS_DESTBLEND                 );
-    D3DSTATE_TO_STR(WINED3DRS_CULLMODE                  );
-    D3DSTATE_TO_STR(WINED3DRS_ZFUNC                     );
-    D3DSTATE_TO_STR(WINED3DRS_ALPHAREF                  );
-    D3DSTATE_TO_STR(WINED3DRS_ALPHAFUNC                 );
-    D3DSTATE_TO_STR(WINED3DRS_DITHERENABLE              );
-    D3DSTATE_TO_STR(WINED3DRS_ALPHABLENDENABLE          );
-    D3DSTATE_TO_STR(WINED3DRS_FOGENABLE                 );
-    D3DSTATE_TO_STR(WINED3DRS_SPECULARENABLE            );
-    D3DSTATE_TO_STR(WINED3DRS_ZVISIBLE                  );
-    D3DSTATE_TO_STR(WINED3DRS_SUBPIXEL                  );
-    D3DSTATE_TO_STR(WINED3DRS_SUBPIXELX                 );
-    D3DSTATE_TO_STR(WINED3DRS_STIPPLEDALPHA             );
-    D3DSTATE_TO_STR(WINED3DRS_FOGCOLOR                  );
-    D3DSTATE_TO_STR(WINED3DRS_FOGTABLEMODE              );
-    D3DSTATE_TO_STR(WINED3DRS_FOGSTART                  );
-    D3DSTATE_TO_STR(WINED3DRS_FOGEND                    );
-    D3DSTATE_TO_STR(WINED3DRS_FOGDENSITY                );
-    D3DSTATE_TO_STR(WINED3DRS_STIPPLEENABLE             );
-    D3DSTATE_TO_STR(WINED3DRS_EDGEANTIALIAS             );
-    D3DSTATE_TO_STR(WINED3DRS_COLORKEYENABLE            );
-    D3DSTATE_TO_STR(WINED3DRS_MIPMAPLODBIAS             );
-    D3DSTATE_TO_STR(WINED3DRS_ZBIAS                     );
-    D3DSTATE_TO_STR(WINED3DRS_RANGEFOGENABLE            );
-    D3DSTATE_TO_STR(WINED3DRS_ANISOTROPY                );
-    D3DSTATE_TO_STR(WINED3DRS_FLUSHBATCH                );
-    D3DSTATE_TO_STR(WINED3DRS_TRANSLUCENTSORTINDEPENDENT);
-    D3DSTATE_TO_STR(WINED3DRS_STENCILENABLE             );
-    D3DSTATE_TO_STR(WINED3DRS_STENCILFAIL               );
-    D3DSTATE_TO_STR(WINED3DRS_STENCILZFAIL              );
-    D3DSTATE_TO_STR(WINED3DRS_STENCILPASS               );
-    D3DSTATE_TO_STR(WINED3DRS_STENCILFUNC               );
-    D3DSTATE_TO_STR(WINED3DRS_STENCILREF                );
-    D3DSTATE_TO_STR(WINED3DRS_STENCILMASK               );
-    D3DSTATE_TO_STR(WINED3DRS_STENCILWRITEMASK          );
-    D3DSTATE_TO_STR(WINED3DRS_TEXTUREFACTOR             );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP0                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP1                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP2                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP3                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP4                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP5                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP6                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP7                     );
-    D3DSTATE_TO_STR(WINED3DRS_CLIPPING                  );
-    D3DSTATE_TO_STR(WINED3DRS_LIGHTING                  );
-    D3DSTATE_TO_STR(WINED3DRS_EXTENTS                   );
-    D3DSTATE_TO_STR(WINED3DRS_AMBIENT                   );
-    D3DSTATE_TO_STR(WINED3DRS_FOGVERTEXMODE             );
-    D3DSTATE_TO_STR(WINED3DRS_COLORVERTEX               );
-    D3DSTATE_TO_STR(WINED3DRS_LOCALVIEWER               );
-    D3DSTATE_TO_STR(WINED3DRS_NORMALIZENORMALS          );
-    D3DSTATE_TO_STR(WINED3DRS_COLORKEYBLENDENABLE       );
-    D3DSTATE_TO_STR(WINED3DRS_DIFFUSEMATERIALSOURCE     );
-    D3DSTATE_TO_STR(WINED3DRS_SPECULARMATERIALSOURCE    );
-    D3DSTATE_TO_STR(WINED3DRS_AMBIENTMATERIALSOURCE     );
-    D3DSTATE_TO_STR(WINED3DRS_EMISSIVEMATERIALSOURCE    );
-    D3DSTATE_TO_STR(WINED3DRS_VERTEXBLEND               );
-    D3DSTATE_TO_STR(WINED3DRS_CLIPPLANEENABLE           );
-    D3DSTATE_TO_STR(WINED3DRS_SOFTWAREVERTEXPROCESSING  );
-    D3DSTATE_TO_STR(WINED3DRS_POINTSIZE                 );
-    D3DSTATE_TO_STR(WINED3DRS_POINTSIZE_MIN             );
-    D3DSTATE_TO_STR(WINED3DRS_POINTSPRITEENABLE         );
-    D3DSTATE_TO_STR(WINED3DRS_POINTSCALEENABLE          );
-    D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_A              );
-    D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_B              );
-    D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_C              );
-    D3DSTATE_TO_STR(WINED3DRS_MULTISAMPLEANTIALIAS      );
-    D3DSTATE_TO_STR(WINED3DRS_MULTISAMPLEMASK           );
-    D3DSTATE_TO_STR(WINED3DRS_PATCHEDGESTYLE            );
-    D3DSTATE_TO_STR(WINED3DRS_PATCHSEGMENTS             );
-    D3DSTATE_TO_STR(WINED3DRS_DEBUGMONITORTOKEN         );
-    D3DSTATE_TO_STR(WINED3DRS_POINTSIZE_MAX             );
-    D3DSTATE_TO_STR(WINED3DRS_INDEXEDVERTEXBLENDENABLE  );
-    D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE          );
-    D3DSTATE_TO_STR(WINED3DRS_TWEENFACTOR               );
-    D3DSTATE_TO_STR(WINED3DRS_BLENDOP                   );
-    D3DSTATE_TO_STR(WINED3DRS_POSITIONDEGREE            );
-    D3DSTATE_TO_STR(WINED3DRS_NORMALDEGREE              );
-    D3DSTATE_TO_STR(WINED3DRS_SCISSORTESTENABLE         );
-    D3DSTATE_TO_STR(WINED3DRS_SLOPESCALEDEPTHBIAS       );
-    D3DSTATE_TO_STR(WINED3DRS_ANTIALIASEDLINEENABLE     );
-    D3DSTATE_TO_STR(WINED3DRS_MINTESSELLATIONLEVEL      );
-    D3DSTATE_TO_STR(WINED3DRS_MAXTESSELLATIONLEVEL      );
-    D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_X            );
-    D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_Y            );
-    D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_Z            );
-    D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_W            );
-    D3DSTATE_TO_STR(WINED3DRS_ENABLEADAPTIVETESSELLATION);
-    D3DSTATE_TO_STR(WINED3DRS_TWOSIDEDSTENCILMODE       );
-    D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILFAIL           );
-    D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILZFAIL          );
-    D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILPASS           );
-    D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILFUNC           );
-    D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE1         );
-    D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE2         );
-    D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE3         );
-    D3DSTATE_TO_STR(WINED3DRS_BLENDFACTOR               );
-    D3DSTATE_TO_STR(WINED3DRS_SRGBWRITEENABLE           );
-    D3DSTATE_TO_STR(WINED3DRS_DEPTHBIAS                 );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP8                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP9                     );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP10                    );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP11                    );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP12                    );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP13                    );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP14                    );
-    D3DSTATE_TO_STR(WINED3DRS_WRAP15                    );
-    D3DSTATE_TO_STR(WINED3DRS_SEPARATEALPHABLENDENABLE  );
-    D3DSTATE_TO_STR(WINED3DRS_SRCBLENDALPHA             );
-    D3DSTATE_TO_STR(WINED3DRS_DESTBLENDALPHA            );
-    D3DSTATE_TO_STR(WINED3DRS_BLENDOPALPHA              );
+        D3DSTATE_TO_STR(WINED3DRS_ANTIALIAS);
+        D3DSTATE_TO_STR(WINED3DRS_TEXTUREPERSPECTIVE);
+        D3DSTATE_TO_STR(WINED3DRS_WRAPU);
+        D3DSTATE_TO_STR(WINED3DRS_WRAPV);
+        D3DSTATE_TO_STR(WINED3DRS_ZENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_FILLMODE);
+        D3DSTATE_TO_STR(WINED3DRS_SHADEMODE);
+        D3DSTATE_TO_STR(WINED3DRS_LINEPATTERN);
+        D3DSTATE_TO_STR(WINED3DRS_MONOENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_ROP2);
+        D3DSTATE_TO_STR(WINED3DRS_PLANEMASK);
+        D3DSTATE_TO_STR(WINED3DRS_ZWRITEENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_ALPHATESTENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_LASTPIXEL);
+        D3DSTATE_TO_STR(WINED3DRS_SRCBLEND);
+        D3DSTATE_TO_STR(WINED3DRS_DESTBLEND);
+        D3DSTATE_TO_STR(WINED3DRS_CULLMODE);
+        D3DSTATE_TO_STR(WINED3DRS_ZFUNC);
+        D3DSTATE_TO_STR(WINED3DRS_ALPHAREF);
+        D3DSTATE_TO_STR(WINED3DRS_ALPHAFUNC);
+        D3DSTATE_TO_STR(WINED3DRS_DITHERENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_ALPHABLENDENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_FOGENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_SPECULARENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_ZVISIBLE);
+        D3DSTATE_TO_STR(WINED3DRS_SUBPIXEL);
+        D3DSTATE_TO_STR(WINED3DRS_SUBPIXELX);
+        D3DSTATE_TO_STR(WINED3DRS_STIPPLEDALPHA);
+        D3DSTATE_TO_STR(WINED3DRS_FOGCOLOR);
+        D3DSTATE_TO_STR(WINED3DRS_FOGTABLEMODE);
+        D3DSTATE_TO_STR(WINED3DRS_FOGSTART);
+        D3DSTATE_TO_STR(WINED3DRS_FOGEND);
+        D3DSTATE_TO_STR(WINED3DRS_FOGDENSITY);
+        D3DSTATE_TO_STR(WINED3DRS_STIPPLEENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_EDGEANTIALIAS);
+        D3DSTATE_TO_STR(WINED3DRS_COLORKEYENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_MIPMAPLODBIAS);
+        D3DSTATE_TO_STR(WINED3DRS_ZBIAS);
+        D3DSTATE_TO_STR(WINED3DRS_RANGEFOGENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_ANISOTROPY);
+        D3DSTATE_TO_STR(WINED3DRS_FLUSHBATCH);
+        D3DSTATE_TO_STR(WINED3DRS_TRANSLUCENTSORTINDEPENDENT);
+        D3DSTATE_TO_STR(WINED3DRS_STENCILENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_STENCILFAIL);
+        D3DSTATE_TO_STR(WINED3DRS_STENCILZFAIL);
+        D3DSTATE_TO_STR(WINED3DRS_STENCILPASS);
+        D3DSTATE_TO_STR(WINED3DRS_STENCILFUNC);
+        D3DSTATE_TO_STR(WINED3DRS_STENCILREF);
+        D3DSTATE_TO_STR(WINED3DRS_STENCILMASK);
+        D3DSTATE_TO_STR(WINED3DRS_STENCILWRITEMASK);
+        D3DSTATE_TO_STR(WINED3DRS_TEXTUREFACTOR);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP0);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP1);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP2);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP3);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP4);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP5);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP6);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP7);
+        D3DSTATE_TO_STR(WINED3DRS_CLIPPING);
+        D3DSTATE_TO_STR(WINED3DRS_LIGHTING);
+        D3DSTATE_TO_STR(WINED3DRS_EXTENTS);
+        D3DSTATE_TO_STR(WINED3DRS_AMBIENT);
+        D3DSTATE_TO_STR(WINED3DRS_FOGVERTEXMODE);
+        D3DSTATE_TO_STR(WINED3DRS_COLORVERTEX);
+        D3DSTATE_TO_STR(WINED3DRS_LOCALVIEWER);
+        D3DSTATE_TO_STR(WINED3DRS_NORMALIZENORMALS);
+        D3DSTATE_TO_STR(WINED3DRS_COLORKEYBLENDENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_DIFFUSEMATERIALSOURCE);
+        D3DSTATE_TO_STR(WINED3DRS_SPECULARMATERIALSOURCE);
+        D3DSTATE_TO_STR(WINED3DRS_AMBIENTMATERIALSOURCE);
+        D3DSTATE_TO_STR(WINED3DRS_EMISSIVEMATERIALSOURCE);
+        D3DSTATE_TO_STR(WINED3DRS_VERTEXBLEND);
+        D3DSTATE_TO_STR(WINED3DRS_CLIPPLANEENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_SOFTWAREVERTEXPROCESSING);
+        D3DSTATE_TO_STR(WINED3DRS_POINTSIZE);
+        D3DSTATE_TO_STR(WINED3DRS_POINTSIZE_MIN);
+        D3DSTATE_TO_STR(WINED3DRS_POINTSPRITEENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_POINTSCALEENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_A);
+        D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_B);
+        D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_C);
+        D3DSTATE_TO_STR(WINED3DRS_MULTISAMPLEANTIALIAS);
+        D3DSTATE_TO_STR(WINED3DRS_MULTISAMPLEMASK);
+        D3DSTATE_TO_STR(WINED3DRS_PATCHEDGESTYLE);
+        D3DSTATE_TO_STR(WINED3DRS_PATCHSEGMENTS);
+        D3DSTATE_TO_STR(WINED3DRS_DEBUGMONITORTOKEN);
+        D3DSTATE_TO_STR(WINED3DRS_POINTSIZE_MAX);
+        D3DSTATE_TO_STR(WINED3DRS_INDEXEDVERTEXBLENDENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_TWEENFACTOR);
+        D3DSTATE_TO_STR(WINED3DRS_BLENDOP);
+        D3DSTATE_TO_STR(WINED3DRS_POSITIONDEGREE);
+        D3DSTATE_TO_STR(WINED3DRS_NORMALDEGREE);
+        D3DSTATE_TO_STR(WINED3DRS_SCISSORTESTENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_SLOPESCALEDEPTHBIAS);
+        D3DSTATE_TO_STR(WINED3DRS_ANTIALIASEDLINEENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_MINTESSELLATIONLEVEL);
+        D3DSTATE_TO_STR(WINED3DRS_MAXTESSELLATIONLEVEL);
+        D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_X);
+        D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_Y);
+        D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_Z);
+        D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_W);
+        D3DSTATE_TO_STR(WINED3DRS_ENABLEADAPTIVETESSELLATION);
+        D3DSTATE_TO_STR(WINED3DRS_TWOSIDEDSTENCILMODE);
+        D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILFAIL);
+        D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILZFAIL);
+        D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILPASS);
+        D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILFUNC);
+        D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE1);
+        D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE2);
+        D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE3);
+        D3DSTATE_TO_STR(WINED3DRS_BLENDFACTOR);
+        D3DSTATE_TO_STR(WINED3DRS_SRGBWRITEENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_DEPTHBIAS);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP8);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP9);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP10);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP11);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP12);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP13);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP14);
+        D3DSTATE_TO_STR(WINED3DRS_WRAP15);
+        D3DSTATE_TO_STR(WINED3DRS_SEPARATEALPHABLENDENABLE);
+        D3DSTATE_TO_STR(WINED3DRS_SRCBLENDALPHA);
+        D3DSTATE_TO_STR(WINED3DRS_DESTBLENDALPHA);
+        D3DSTATE_TO_STR(WINED3DRS_BLENDOPALPHA);
 #undef D3DSTATE_TO_STR
-  default:
-    FIXME("Unrecognized %u render state!\n", state);
-    return "unrecognized";
-  }
+        default:
+            FIXME("Unrecognized %u render state!\n", state);
+            return "unrecognized";
+    }
 }
 
-const char* debug_d3dsamplerstate(DWORD state) {
-  switch (state) {
+const char *debug_d3dsamplerstate(DWORD state)
+{
+    switch (state)
+    {
 #define D3DSTATE_TO_STR(u) case u: return #u
-    D3DSTATE_TO_STR(WINED3DSAMP_BORDERCOLOR  );
-    D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSU     );
-    D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSV     );
-    D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSW     );
-    D3DSTATE_TO_STR(WINED3DSAMP_MAGFILTER    );
-    D3DSTATE_TO_STR(WINED3DSAMP_MINFILTER    );
-    D3DSTATE_TO_STR(WINED3DSAMP_MIPFILTER    );
-    D3DSTATE_TO_STR(WINED3DSAMP_MIPMAPLODBIAS);
-    D3DSTATE_TO_STR(WINED3DSAMP_MAXMIPLEVEL  );
-    D3DSTATE_TO_STR(WINED3DSAMP_MAXANISOTROPY);
-    D3DSTATE_TO_STR(WINED3DSAMP_SRGBTEXTURE  );
-    D3DSTATE_TO_STR(WINED3DSAMP_ELEMENTINDEX );
-    D3DSTATE_TO_STR(WINED3DSAMP_DMAPOFFSET   );
+        D3DSTATE_TO_STR(WINED3DSAMP_BORDERCOLOR);
+        D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSU);
+        D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSV);
+        D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSW);
+        D3DSTATE_TO_STR(WINED3DSAMP_MAGFILTER);
+        D3DSTATE_TO_STR(WINED3DSAMP_MINFILTER);
+        D3DSTATE_TO_STR(WINED3DSAMP_MIPFILTER);
+        D3DSTATE_TO_STR(WINED3DSAMP_MIPMAPLODBIAS);
+        D3DSTATE_TO_STR(WINED3DSAMP_MAXMIPLEVEL);
+        D3DSTATE_TO_STR(WINED3DSAMP_MAXANISOTROPY);
+        D3DSTATE_TO_STR(WINED3DSAMP_SRGBTEXTURE);
+        D3DSTATE_TO_STR(WINED3DSAMP_ELEMENTINDEX);
+        D3DSTATE_TO_STR(WINED3DSAMP_DMAPOFFSET);
 #undef D3DSTATE_TO_STR
-  default:
-    FIXME("Unrecognized %u sampler state!\n", state);
-    return "unrecognized";
-  }
+        default:
+            FIXME("Unrecognized %u sampler state!\n", state);
+            return "unrecognized";
+    }
 }
 
 const char *debug_d3dtexturefiltertype(WINED3DTEXTUREFILTERTYPE filter_type) {
@@ -1992,32 +2061,34 @@ const char *debug_d3dtexturefiltertype(WINED3DTEXTUREFILTERTYPE filter_type) {
     }
 }
 
-const char* debug_d3dtexturestate(DWORD state) {
-  switch (state) {
+const char *debug_d3dtexturestate(DWORD state)
+{
+    switch (state)
+    {
 #define D3DSTATE_TO_STR(u) case u: return #u
-    D3DSTATE_TO_STR(WINED3DTSS_COLOROP               );
-    D3DSTATE_TO_STR(WINED3DTSS_COLORARG1             );
-    D3DSTATE_TO_STR(WINED3DTSS_COLORARG2             );
-    D3DSTATE_TO_STR(WINED3DTSS_ALPHAOP               );
-    D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG1             );
-    D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG2             );
-    D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT00          );
-    D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT01          );
-    D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT10          );
-    D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT11          );
-    D3DSTATE_TO_STR(WINED3DTSS_TEXCOORDINDEX         );
-    D3DSTATE_TO_STR(WINED3DTSS_BUMPENVLSCALE         );
-    D3DSTATE_TO_STR(WINED3DTSS_BUMPENVLOFFSET        );
-    D3DSTATE_TO_STR(WINED3DTSS_TEXTURETRANSFORMFLAGS );
-    D3DSTATE_TO_STR(WINED3DTSS_COLORARG0             );
-    D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG0             );
-    D3DSTATE_TO_STR(WINED3DTSS_RESULTARG             );
-    D3DSTATE_TO_STR(WINED3DTSS_CONSTANT              );
+        D3DSTATE_TO_STR(WINED3DTSS_COLOROP);
+        D3DSTATE_TO_STR(WINED3DTSS_COLORARG1);
+        D3DSTATE_TO_STR(WINED3DTSS_COLORARG2);
+        D3DSTATE_TO_STR(WINED3DTSS_ALPHAOP);
+        D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG1);
+        D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG2);
+        D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT00);
+        D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT01);
+        D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT10);
+        D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT11);
+        D3DSTATE_TO_STR(WINED3DTSS_TEXCOORDINDEX);
+        D3DSTATE_TO_STR(WINED3DTSS_BUMPENVLSCALE);
+        D3DSTATE_TO_STR(WINED3DTSS_BUMPENVLOFFSET);
+        D3DSTATE_TO_STR(WINED3DTSS_TEXTURETRANSFORMFLAGS);
+        D3DSTATE_TO_STR(WINED3DTSS_COLORARG0);
+        D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG0);
+        D3DSTATE_TO_STR(WINED3DTSS_RESULTARG);
+        D3DSTATE_TO_STR(WINED3DTSS_CONSTANT);
 #undef D3DSTATE_TO_STR
-  default:
-    FIXME("Unrecognized %u texture state!\n", state);
-    return "unrecognized";
-  }
+        default:
+            FIXME("Unrecognized %u texture state!\n", state);
+            return "unrecognized";
+    }
 }
 
 const char* debug_d3dtop(WINED3DTEXTUREOP d3dtop) {
@@ -2126,18 +2197,20 @@ const char *debug_d3dstate(DWORD state)
     return wine_dbg_sprintf("UNKNOWN_STATE(%#x)", state);
 }
 
-const char* debug_d3dpool(WINED3DPOOL Pool) {
-  switch (Pool) {
+const char *debug_d3dpool(WINED3DPOOL pool)
+{
+    switch (pool)
+    {
 #define POOL_TO_STR(p) case p: return #p
-    POOL_TO_STR(WINED3DPOOL_DEFAULT);
-    POOL_TO_STR(WINED3DPOOL_MANAGED);
-    POOL_TO_STR(WINED3DPOOL_SYSTEMMEM);
-    POOL_TO_STR(WINED3DPOOL_SCRATCH);
+        POOL_TO_STR(WINED3DPOOL_DEFAULT);
+        POOL_TO_STR(WINED3DPOOL_MANAGED);
+        POOL_TO_STR(WINED3DPOOL_SYSTEMMEM);
+        POOL_TO_STR(WINED3DPOOL_SCRATCH);
 #undef  POOL_TO_STR
-  default:
-    FIXME("Unrecognized %u WINED3DPOOL!\n", Pool);
-    return "unrecognized";
-  }
+        default:
+            FIXME("Unrecognized %u WINED3DPOOL!\n", pool);
+            return "unrecognized";
+    }
 }
 
 const char *debug_fbostatus(GLenum status) {
@@ -2293,9 +2366,11 @@ GLenum CompareFunc(DWORD func) {
     }
 }
 
-BOOL is_invalid_op(IWineD3DDeviceImpl *This, int stage, WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3) {
+BOOL is_invalid_op(const struct wined3d_state *state, int stage,
+        WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3)
+{
     if (op == WINED3DTOP_DISABLE) return FALSE;
-    if (This->stateBlock->textures[stage]) return FALSE;
+    if (state->textures[stage]) return FALSE;
 
     if ((arg1 & WINED3DTA_SELECTMASK) == WINED3DTA_TEXTURE
             && op != WINED3DTOP_SELECTARG2) return TRUE;
@@ -2310,7 +2385,7 @@ BOOL is_invalid_op(IWineD3DDeviceImpl *This, int stage, WINED3DTEXTUREOP op, DWO
 /* Setup this textures matrix according to the texture flags*/
 /* GL locking is done by the caller (state handler) */
 void set_texture_matrix(const float *smat, DWORD flags, BOOL calculatedCoords, BOOL transformed,
-        WINED3DFORMAT vtx_fmt, BOOL ffp_proj_control)
+        enum wined3d_format_id vtx_fmt, BOOL ffp_proj_control)
 {
     float mat[16];
 
@@ -2417,11 +2492,12 @@ unsigned int count_bits(unsigned int mask)
 
 /* Helper function for retrieving color info for ChoosePixelFormat and wglChoosePixelFormatARB.
  * The later function requires individual color components. */
-BOOL getColorBits(const struct wined3d_format_desc *format_desc,
+BOOL getColorBits(const struct wined3d_format *format,
         short *redSize, short *greenSize, short *blueSize, short *alphaSize, short *totalSize)
 {
-    TRACE("fmt: %s\n", debug_d3dformat(format_desc->format));
-    switch(format_desc->format)
+    TRACE("format %s.\n", debug_d3dformat(format->id));
+
+    switch (format->id)
     {
         case WINED3DFMT_B8G8R8X8_UNORM:
         case WINED3DFMT_B8G8R8_UNORM:
@@ -2438,26 +2514,27 @@ BOOL getColorBits(const struct wined3d_format_desc *format_desc,
         case WINED3DFMT_P8_UINT:
             break;
         default:
-            ERR("Unsupported format: %s\n", debug_d3dformat(format_desc->format));
+            FIXME("Unsupported format %s.\n", debug_d3dformat(format->id));
             return FALSE;
     }
 
-    *redSize = count_bits(format_desc->red_mask);
-    *greenSize = count_bits(format_desc->green_mask);
-    *blueSize = count_bits(format_desc->blue_mask);
-    *alphaSize = count_bits(format_desc->alpha_mask);
+    *redSize = count_bits(format->red_mask);
+    *greenSize = count_bits(format->green_mask);
+    *blueSize = count_bits(format->blue_mask);
+    *alphaSize = count_bits(format->alpha_mask);
     *totalSize = *redSize + *greenSize + *blueSize + *alphaSize;
 
-    TRACE("Returning red:  %d, green: %d, blue: %d, alpha: %d, total: %d for fmt=%s\n",
-            *redSize, *greenSize, *blueSize, *alphaSize, *totalSize, debug_d3dformat(format_desc->format));
+    TRACE("Returning red: %d, green: %d, blue: %d, alpha: %d, total: %d for format %s.\n",
+            *redSize, *greenSize, *blueSize, *alphaSize, *totalSize, debug_d3dformat(format->id));
     return TRUE;
 }
 
 /* Helper function for retrieving depth/stencil info for ChoosePixelFormat and wglChoosePixelFormatARB */
-BOOL getDepthStencilBits(const struct wined3d_format_desc *format_desc, short *depthSize, short *stencilSize)
+BOOL getDepthStencilBits(const struct wined3d_format *format, short *depthSize, short *stencilSize)
 {
-    TRACE("fmt: %s\n", debug_d3dformat(format_desc->format));
-    switch(format_desc->format)
+    TRACE("format %s.\n", debug_d3dformat(format->id));
+
+    switch (format->id)
     {
         case WINED3DFMT_D16_LOCKABLE:
         case WINED3DFMT_D16_UNORM:
@@ -2470,130 +2547,83 @@ BOOL getDepthStencilBits(const struct wined3d_format_desc *format_desc, short *d
         case WINED3DFMT_D32_FLOAT:
             break;
         default:
-            FIXME("Unsupported stencil format: %s\n", debug_d3dformat(format_desc->format));
+            FIXME("Unsupported depth/stencil format %s.\n", debug_d3dformat(format->id));
             return FALSE;
     }
 
-    *depthSize = format_desc->depth_size;
-    *stencilSize = format_desc->stencil_size;
+    *depthSize = format->depth_size;
+    *stencilSize = format->stencil_size;
 
-    TRACE("Returning depthSize: %d and stencilSize: %d for fmt=%s\n",
-            *depthSize, *stencilSize, debug_d3dformat(format_desc->format));
+    TRACE("Returning depthSize: %d and stencilSize: %d for format %s.\n",
+            *depthSize, *stencilSize, debug_d3dformat(format->id));
     return TRUE;
 }
 
-DWORD color_convert_argb_to_fmt(DWORD color, WINED3DFORMAT destfmt)
+/* Note: It's the caller's responsibility to ensure values can be expressed
+ * in the requested format. UNORM formats for example can only express values
+ * in the range 0.0f -> 1.0f. */
+DWORD wined3d_format_convert_from_float(const struct wined3d_format *format, const WINED3DCOLORVALUE *color)
 {
-    unsigned int r, g, b, a;
-    DWORD ret;
-
-    if (destfmt == WINED3DFMT_B8G8R8A8_UNORM
-            || destfmt == WINED3DFMT_B8G8R8X8_UNORM
-            || destfmt == WINED3DFMT_B8G8R8_UNORM)
-        return color;
-
-    TRACE("Converting color %08x to format %s\n", color, debug_d3dformat(destfmt));
+    static const struct
+    {
+        enum wined3d_format_id format_id;
+        float r_mul;
+        float g_mul;
+        float b_mul;
+        float a_mul;
+        BYTE r_shift;
+        BYTE g_shift;
+        BYTE b_shift;
+        BYTE a_shift;
+    }
+    conv[] =
+    {
+        {WINED3DFMT_B8G8R8A8_UNORM,     255.0f,  255.0f,  255.0f,  255.0f, 16,  8,  0, 24},
+        {WINED3DFMT_B8G8R8X8_UNORM,     255.0f,  255.0f,  255.0f,  255.0f, 16,  8,  0, 24},
+        {WINED3DFMT_B8G8R8_UNORM,       255.0f,  255.0f,  255.0f,  255.0f, 16,  8,  0, 24},
+        {WINED3DFMT_B5G6R5_UNORM,        31.0f,   63.0f,   31.0f,    0.0f, 11,  5,  0,  0},
+        {WINED3DFMT_B5G5R5A1_UNORM,      31.0f,   31.0f,   31.0f,    1.0f, 10,  5,  0, 15},
+        {WINED3DFMT_B5G5R5X1_UNORM,      31.0f,   31.0f,   31.0f,    1.0f, 10,  5,  0, 15},
+        {WINED3DFMT_A8_UNORM,             0.0f,    0.0f,    0.0f,  255.0f,  0,  0,  0,  0},
+        {WINED3DFMT_B4G4R4A4_UNORM,      15.0f,   15.0f,   15.0f,   15.0f,  8,  4,  0, 12},
+        {WINED3DFMT_B4G4R4X4_UNORM,      15.0f,   15.0f,   15.0f,   15.0f,  8,  4,  0, 12},
+        {WINED3DFMT_B2G3R3_UNORM,         7.0f,    7.0f,    3.0f,    0.0f,  5,  2,  0,  0},
+        {WINED3DFMT_R8G8B8A8_UNORM,     255.0f,  255.0f,  255.0f,  255.0f,  0,  8, 16, 24},
+        {WINED3DFMT_R8G8B8X8_UNORM,     255.0f,  255.0f,  255.0f,  255.0f,  0,  8, 16, 24},
+        {WINED3DFMT_B10G10R10A2_UNORM, 1023.0f, 1023.0f, 1023.0f,    3.0f, 20, 10,  0, 30},
+        {WINED3DFMT_R10G10B10A2_UNORM, 1023.0f, 1023.0f, 1023.0f,    3.0f,  0, 10, 20, 30},
+    };
+    unsigned int i;
 
-    a = (color & 0xff000000) >> 24;
-    r = (color & 0x00ff0000) >> 16;
-    g = (color & 0x0000ff00) >>  8;
-    b = (color & 0x000000ff) >>  0;
+    TRACE("Converting color {%.8e %.8e %.8e %.8e} to format %s.\n",
+            color->r, color->g, color->b, color->a, debug_d3dformat(format->id));
 
-    switch(destfmt)
+    for (i = 0; i < sizeof(conv) / sizeof(*conv); ++i)
     {
-        case WINED3DFMT_B5G6R5_UNORM:
-            if(r == 0xff && g == 0xff && b == 0xff) return 0xffff;
-            r = (r * 32) / 256;
-            g = (g * 64) / 256;
-            b = (b * 32) / 256;
-            ret  = r << 11;
-            ret |= g << 5;
-            ret |= b;
-            TRACE("Returning %08x\n", ret);
-            return ret;
-
-        case WINED3DFMT_B5G5R5X1_UNORM:
-        case WINED3DFMT_B5G5R5A1_UNORM:
-            a = (a *  2) / 256;
-            r = (r * 32) / 256;
-            g = (g * 32) / 256;
-            b = (b * 32) / 256;
-            ret  = a << 15;
-            ret |= r << 10;
-            ret |= g <<  5;
-            ret |= b <<  0;
-            TRACE("Returning %08x\n", ret);
-            return ret;
-
-        case WINED3DFMT_A8_UNORM:
-            TRACE("Returning %08x\n", a);
-            return a;
+        DWORD ret;
 
-        case WINED3DFMT_B4G4R4X4_UNORM:
-        case WINED3DFMT_B4G4R4A4_UNORM:
-            a = (a * 16) / 256;
-            r = (r * 16) / 256;
-            g = (g * 16) / 256;
-            b = (b * 16) / 256;
-            ret  = a << 12;
-            ret |= r <<  8;
-            ret |= g <<  4;
-            ret |= b <<  0;
-            TRACE("Returning %08x\n", ret);
-            return ret;
+        if (format->id != conv[i].format_id) continue;
 
-        case WINED3DFMT_B2G3R3_UNORM:
-            r = (r * 8) / 256;
-            g = (g * 8) / 256;
-            b = (b * 4) / 256;
-            ret  = r <<  5;
-            ret |= g <<  2;
-            ret |= b <<  0;
-            TRACE("Returning %08x\n", ret);
-            return ret;
-
-        case WINED3DFMT_R8G8B8X8_UNORM:
-        case WINED3DFMT_R8G8B8A8_UNORM:
-            ret  = a << 24;
-            ret |= b << 16;
-            ret |= g <<  8;
-            ret |= r <<  0;
-            TRACE("Returning %08x\n", ret);
-            return ret;
+        ret = ((DWORD)((color->r * conv[i].r_mul) + 0.5f)) << conv[i].r_shift;
+        ret |= ((DWORD)((color->g * conv[i].g_mul) + 0.5f)) << conv[i].g_shift;
+        ret |= ((DWORD)((color->b * conv[i].b_mul) + 0.5f)) << conv[i].b_shift;
+        ret |= ((DWORD)((color->a * conv[i].a_mul) + 0.5f)) << conv[i].a_shift;
 
-        case WINED3DFMT_B10G10R10A2_UNORM:
-            a = (a *    4) / 256;
-            r = (r * 1024) / 256;
-            g = (g * 1024) / 256;
-            b = (b * 1024) / 256;
-            ret  = a << 30;
-            ret |= r << 20;
-            ret |= g << 10;
-            ret |= b <<  0;
-            TRACE("Returning %08x\n", ret);
-            return ret;
-
-        case WINED3DFMT_R10G10B10A2_UNORM:
-            a = (a *    4) / 256;
-            r = (r * 1024) / 256;
-            g = (g * 1024) / 256;
-            b = (b * 1024) / 256;
-            ret  = a << 30;
-            ret |= b << 20;
-            ret |= g << 10;
-            ret |= r <<  0;
-            TRACE("Returning %08x\n", ret);
-            return ret;
+        TRACE("Returning 0x%08x.\n", ret);
 
-        default:
-            FIXME("Add a COLORFILL conversion for format %s\n", debug_d3dformat(destfmt));
-            return 0;
+        return ret;
     }
+
+    FIXME("Conversion for format %s not implemented.\n", debug_d3dformat(format->id));
+
+    return 0;
 }
 
 /* DirectDraw stuff */
-WINED3DFORMAT pixelformat_for_depth(DWORD depth) {
-    switch(depth) {
+enum wined3d_format_id pixelformat_for_depth(DWORD depth)
+{
+    switch (depth)
+    {
         case 8:  return WINED3DFMT_P8_UINT;
         case 15: return WINED3DFMT_B5G5R5X1_UNORM;
         case 16: return WINED3DFMT_B5G6R5_UNORM;
@@ -2696,13 +2726,15 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
     DWORD ttff;
     DWORD cop, aop, carg0, carg1, carg2, aarg0, aarg1, aarg2;
     IWineD3DDeviceImpl *device = stateblock->device;
+    IWineD3DSurfaceImpl *rt = device->render_targets[0];
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
 
     for (i = 0; i < gl_info->limits.texture_stages; ++i)
     {
         IWineD3DBaseTextureImpl *texture;
         settings->op[i].padding = 0;
-        if(stateblock->textureState[i][WINED3DTSS_COLOROP] == WINED3DTOP_DISABLE) {
+        if (stateblock->state.texture_states[i][WINED3DTSS_COLOROP] == WINED3DTOP_DISABLE)
+        {
             settings->op[i].cop = WINED3DTOP_DISABLE;
             settings->op[i].aop = WINED3DTOP_DISABLE;
             settings->op[i].carg0 = settings->op[i].carg1 = settings->op[i].carg2 = ARG_UNUSED;
@@ -2715,13 +2747,17 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
             break;
         }
 
-        texture = (IWineD3DBaseTextureImpl *) stateblock->textures[i];
-        if(texture) {
-            settings->op[i].color_fixup = texture->resource.format_desc->color_fixup;
-            if(ignore_textype) {
+        if ((texture = stateblock->state.textures[i]))
+        {
+            settings->op[i].color_fixup = texture->resource.format->color_fixup;
+            if (ignore_textype)
+            {
                 settings->op[i].tex_type = tex_1d;
-            } else {
-                switch (IWineD3DBaseTexture_GetTextureDimensions((IWineD3DBaseTexture *)texture)) {
+            }
+            else
+            {
+                switch (texture->baseTexture.target)
+                {
                     case GL_TEXTURE_1D:
                         settings->op[i].tex_type = tex_1d;
                         break;
@@ -2744,14 +2780,15 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
             settings->op[i].tex_type = tex_1d;
         }
 
-        cop = stateblock->textureState[i][WINED3DTSS_COLOROP];
-        aop = stateblock->textureState[i][WINED3DTSS_ALPHAOP];
+        cop = stateblock->state.texture_states[i][WINED3DTSS_COLOROP];
+        aop = stateblock->state.texture_states[i][WINED3DTSS_ALPHAOP];
 
-        carg1 = (args[cop] & ARG1) ? stateblock->textureState[i][WINED3DTSS_COLORARG1] : ARG_UNUSED;
-        carg2 = (args[cop] & ARG2) ? stateblock->textureState[i][WINED3DTSS_COLORARG2] : ARG_UNUSED;
-        carg0 = (args[cop] & ARG0) ? stateblock->textureState[i][WINED3DTSS_COLORARG0] : ARG_UNUSED;
+        carg1 = (args[cop] & ARG1) ? stateblock->state.texture_states[i][WINED3DTSS_COLORARG1] : ARG_UNUSED;
+        carg2 = (args[cop] & ARG2) ? stateblock->state.texture_states[i][WINED3DTSS_COLORARG2] : ARG_UNUSED;
+        carg0 = (args[cop] & ARG0) ? stateblock->state.texture_states[i][WINED3DTSS_COLORARG0] : ARG_UNUSED;
 
-        if(is_invalid_op(device, i, cop, carg1, carg2, carg0)) {
+        if (is_invalid_op(&stateblock->state, i, cop, carg1, carg2, carg0))
+        {
             carg0 = ARG_UNUSED;
             carg2 = ARG_UNUSED;
             carg1 = WINED3DTA_CURRENT;
@@ -2766,22 +2803,24 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
             aarg1 = carg1;
             aarg2 = carg2;
             aarg0 = carg0;
-        } else {
-            aarg1 = (args[aop] & ARG1) ? stateblock->textureState[i][WINED3DTSS_ALPHAARG1] : ARG_UNUSED;
-            aarg2 = (args[aop] & ARG2) ? stateblock->textureState[i][WINED3DTSS_ALPHAARG2] : ARG_UNUSED;
-            aarg0 = (args[aop] & ARG0) ? stateblock->textureState[i][WINED3DTSS_ALPHAARG0] : ARG_UNUSED;
+        }
+        else
+        {
+            aarg1 = (args[aop] & ARG1) ? stateblock->state.texture_states[i][WINED3DTSS_ALPHAARG1] : ARG_UNUSED;
+            aarg2 = (args[aop] & ARG2) ? stateblock->state.texture_states[i][WINED3DTSS_ALPHAARG2] : ARG_UNUSED;
+            aarg0 = (args[aop] & ARG0) ? stateblock->state.texture_states[i][WINED3DTSS_ALPHAARG0] : ARG_UNUSED;
         }
 
-        if (i == 0 && stateblock->textures[0] && stateblock->renderState[WINED3DRS_COLORKEYENABLE])
+        if (!i && stateblock->state.textures[0] && stateblock->state.render_states[WINED3DRS_COLORKEYENABLE])
         {
-            UINT texture_dimensions = IWineD3DBaseTexture_GetTextureDimensions(stateblock->textures[0]);
+            IWineD3DBaseTextureImpl *texture = stateblock->state.textures[0];
+            GLenum texture_dimensions = texture->baseTexture.target;
 
             if (texture_dimensions == GL_TEXTURE_2D || texture_dimensions == GL_TEXTURE_RECTANGLE_ARB)
             {
-                IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)stateblock->textures[0];
                 IWineD3DSurfaceImpl *surf = (IWineD3DSurfaceImpl *)texture->baseTexture.sub_resources[0];
 
-                if (surf->CKeyFlags & WINEDDSD_CKSRCBLT && !surf->resource.format_desc->alpha_mask)
+                if (surf->CKeyFlags & WINEDDSD_CKSRCBLT && !surf->resource.format->alpha_mask)
                 {
                     if (aop == WINED3DTOP_DISABLE)
                     {
@@ -2790,7 +2829,7 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
                     }
                     else if (aop == WINED3DTOP_SELECTARG1 && aarg1 != WINED3DTA_TEXTURE)
                     {
-                        if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE])
+                        if (stateblock->state.render_states[WINED3DRS_ALPHABLENDENABLE])
                         {
                             aarg2 = WINED3DTA_TEXTURE;
                             aop = WINED3DTOP_MODULATE;
@@ -2799,7 +2838,7 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
                     }
                     else if (aop == WINED3DTOP_SELECTARG2 && aarg2 != WINED3DTA_TEXTURE)
                     {
-                        if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE])
+                        if (stateblock->state.render_states[WINED3DRS_ALPHABLENDENABLE])
                         {
                             aarg1 = WINED3DTA_TEXTURE;
                             aop = WINED3DTOP_MODULATE;
@@ -2810,17 +2849,20 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
             }
         }
 
-        if(is_invalid_op(device, i, aop, aarg1, aarg2, aarg0)) {
+        if (is_invalid_op(&stateblock->state, i, aop, aarg1, aarg2, aarg0))
+        {
                aarg0 = ARG_UNUSED;
                aarg2 = ARG_UNUSED;
                aarg1 = WINED3DTA_CURRENT;
                aop = WINED3DTOP_SELECTARG1;
         }
 
-        if(carg1 == WINED3DTA_TEXTURE || carg2 == WINED3DTA_TEXTURE || carg0 == WINED3DTA_TEXTURE ||
-           aarg1 == WINED3DTA_TEXTURE || aarg2 == WINED3DTA_TEXTURE || aarg0 == WINED3DTA_TEXTURE) {
-            ttff = stateblock->textureState[i][WINED3DTSS_TEXTURETRANSFORMFLAGS];
-            if(ttff == (WINED3DTTFF_PROJECTED | WINED3DTTFF_COUNT3)) {
+        if (carg1 == WINED3DTA_TEXTURE || carg2 == WINED3DTA_TEXTURE || carg0 == WINED3DTA_TEXTURE
+                || aarg1 == WINED3DTA_TEXTURE || aarg2 == WINED3DTA_TEXTURE || aarg0 == WINED3DTA_TEXTURE)
+        {
+            ttff = stateblock->state.texture_states[i][WINED3DTSS_TEXTURETRANSFORMFLAGS];
+            if (ttff == (WINED3DTTFF_PROJECTED | WINED3DTTFF_COUNT3))
+            {
                 settings->op[i].projected = proj_count3;
             } else if(ttff == (WINED3DTTFF_PROJECTED | WINED3DTTFF_COUNT4)) {
                 settings->op[i].projected = proj_count4;
@@ -2840,7 +2882,8 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
         settings->op[i].aarg1 = aarg1;
         settings->op[i].aarg2 = aarg2;
 
-        if(stateblock->textureState[i][WINED3DTSS_RESULTARG] == WINED3DTA_TEMP) {
+        if (stateblock->state.texture_states[i][WINED3DTSS_RESULTARG] == WINED3DTA_TEMP)
+        {
             settings->op[i].dst = tempreg;
         } else {
             settings->op[i].dst = resultreg;
@@ -2852,13 +2895,20 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
         memset(&settings->op[i], 0xff, sizeof(settings->op[i]));
     }
 
-    if(stateblock->renderState[WINED3DRS_FOGENABLE] == FALSE) {
+    if (!stateblock->state.render_states[WINED3DRS_FOGENABLE])
+    {
         settings->fog = FOG_OFF;
-    } else if(stateblock->renderState[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE) {
-        if(use_vs(stateblock) || ((IWineD3DVertexDeclarationImpl *) stateblock->vertexDecl)->position_transformed) {
+    }
+    else if (stateblock->state.render_states[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE)
+    {
+        if (use_vs(&stateblock->state) || stateblock->state.vertex_declaration->position_transformed)
+        {
             settings->fog = FOG_LINEAR;
-        } else {
-            switch(stateblock->renderState[WINED3DRS_FOGVERTEXMODE]) {
+        }
+        else
+        {
+            switch (stateblock->state.render_states[WINED3DRS_FOGVERTEXMODE])
+            {
                 case WINED3DFOG_NONE:
                 case WINED3DFOG_LINEAR:
                     settings->fog = FOG_LINEAR;
@@ -2871,8 +2921,11 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
                     break;
             }
         }
-    } else {
-        switch(stateblock->renderState[WINED3DRS_FOGTABLEMODE]) {
+    }
+    else
+    {
+        switch (stateblock->state.render_states[WINED3DRS_FOGTABLEMODE])
+        {
             case WINED3DFOG_LINEAR:
                 settings->fog = FOG_LINEAR;
                 break;
@@ -2884,13 +2937,16 @@ void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_setting
                 break;
         }
     }
-    if(stateblock->renderState[WINED3DRS_SRGBWRITEENABLE]) {
+    if (stateblock->state.render_states[WINED3DRS_SRGBWRITEENABLE]
+            && rt->resource.format->Flags & WINED3DFMT_FLAG_SRGB_WRITE)
+    {
         settings->sRGB_write = 1;
     } else {
         settings->sRGB_write = 0;
     }
-    if(device->vs_clipping || !use_vs(stateblock) || !stateblock->renderState[WINED3DRS_CLIPPING] ||
-       !stateblock->renderState[WINED3DRS_CLIPPLANEENABLE]) {
+    if (device->vs_clipping || !use_vs(&stateblock->state) || !stateblock->state.render_states[WINED3DRS_CLIPPING]
+            || !stateblock->state.render_states[WINED3DRS_CLIPPLANEENABLE])
+    {
         /* No need to emulate clipplanes if GL supports native vertex shader clipping or if
          * the fixed function vertex pipeline is used(which always supports clipplanes), or
          * if no clipplane is enabled
@@ -2923,13 +2979,12 @@ void add_ffp_frag_shader(struct wine_rb_tree *shaders, struct ffp_frag_desc *des
  * Requires the caller to activate the correct unit before
  */
 /* GL locking is done by the caller (state handler) */
-void texture_activate_dimensions(DWORD stage, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
+void texture_activate_dimensions(IWineD3DBaseTextureImpl *texture, const struct wined3d_gl_info *gl_info)
 {
-    const struct wined3d_gl_info *gl_info = context->gl_info;
-
-    if (stateblock->textures[stage])
+    if (texture)
     {
-        switch (IWineD3DBaseTexture_GetTextureDimensions(stateblock->textures[stage])) {
+        switch (texture->baseTexture.target)
+        {
             case GL_TEXTURE_2D:
                 glDisable(GL_TEXTURE_3D);
                 checkGLcall("glDisable(GL_TEXTURE_3D)");
@@ -3019,10 +3074,10 @@ void sampler_texdim(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wine
     * will take care of this business
     */
     if (mapped_stage == WINED3D_UNMAPPED_STAGE || mapped_stage >= context->gl_info->limits.textures) return;
-    if(sampler >= stateblock->lowest_disabled_stage) return;
-    if(isStateDirty(context, STATE_TEXTURESTAGE(sampler, WINED3DTSS_COLOROP))) return;
+    if (sampler >= stateblock->state.lowest_disabled_stage) return;
+    if (isStateDirty(context, STATE_TEXTURESTAGE(sampler, WINED3DTSS_COLOROP))) return;
 
-    texture_activate_dimensions(sampler, stateblock, context);
+    texture_activate_dimensions(stateblock->state.textures[sampler], context->gl_info);
 }
 
 void *wined3d_rb_alloc(size_t size)
@@ -3106,3 +3161,26 @@ void select_shader_mode(const struct wined3d_gl_info *gl_info, int *ps_selected,
     else if (gl_info->supported[ATI_FRAGMENT_SHADER]) *ps_selected = SHADER_ATI;
     else *ps_selected = SHADER_NONE;
 }
+
+const struct blit_shader *wined3d_select_blitter(const struct wined3d_gl_info *gl_info, enum blit_operation blit_op,
+        const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool, const struct wined3d_format *src_format,
+        const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool, const struct wined3d_format *dst_format)
+{
+    static const struct blit_shader * const blitters[] =
+    {
+        &arbfp_blit,
+        &ffp_blit,
+        &cpu_blit,
+    };
+    unsigned int i;
+
+    for (i = 0; i < sizeof(blitters) / sizeof(*blitters); ++i)
+    {
+        if (blitters[i]->blit_supported(gl_info, blit_op,
+                src_rect, src_usage, src_pool, src_format,
+                dst_rect, dst_usage, dst_pool, dst_format))
+            return blitters[i];
+    }
+
+    return NULL;
+}
index 0bc141a..59219f0 100644 (file)
@@ -79,13 +79,11 @@ static ULONG WINAPI IWineD3DVertexDeclarationImpl_Release(IWineD3DVertexDeclarat
    IWineD3DVertexDeclaration parts follow
    ******************************************* */
 
-static HRESULT WINAPI IWineD3DVertexDeclarationImpl_GetParent(IWineD3DVertexDeclaration *iface, IUnknown** parent){
-    IWineD3DVertexDeclarationImpl *This = (IWineD3DVertexDeclarationImpl *)iface;
+static void * WINAPI IWineD3DVertexDeclarationImpl_GetParent(IWineD3DVertexDeclaration *iface)
+{
+    TRACE("iface %p.\n", iface);
 
-    *parent= This->parent;
-    IUnknown_AddRef(*parent);
-    TRACE("(%p) : returning %p\n", This, *parent);
-    return WINED3D_OK;
+    return ((IWineD3DVertexDeclarationImpl *)iface)->parent;
 }
 
 static BOOL declaration_element_valid_ffp(const WINED3DVERTEXELEMENT *element)
@@ -188,7 +186,7 @@ static const IWineD3DVertexDeclarationVtbl IWineD3DVertexDeclaration_Vtbl =
 
 HRESULT vertexdeclaration_init(IWineD3DVertexDeclarationImpl *declaration, IWineD3DDeviceImpl *device,
         const WINED3DVERTEXELEMENT *elements, UINT element_count,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
     WORD preloaded = 0; /* MAX_STREAMS, 16 */
@@ -221,7 +219,7 @@ HRESULT vertexdeclaration_init(IWineD3DVertexDeclarationImpl *declaration, IWine
     {
         struct wined3d_vertex_declaration_element *e = &declaration->elements[i];
 
-        e->format_desc = getFormatDescEntry(elements[i].format, gl_info);
+        e->format = wined3d_get_format(gl_info, elements[i].format);
         e->ffp_valid = declaration_element_valid_ffp(&elements[i]);
         e->input_slot = elements[i].input_slot;
         e->offset = elements[i].offset;
@@ -236,7 +234,7 @@ HRESULT vertexdeclaration_init(IWineD3DVertexDeclarationImpl *declaration, IWine
          * to be loaded when drawing, but filter tesselation pseudo streams. */
         if (e->input_slot >= MAX_STREAMS) continue;
 
-        if (!e->format_desc->gl_vtx_format)
+        if (!e->format->gl_vtx_format)
         {
             FIXME("The application tries to use an unsupported format (%s), returning E_FAIL.\n",
                     debug_d3dformat(elements[i].format));
index 0c9919d..e4e40fc 100644 (file)
@@ -74,14 +74,11 @@ static ULONG STDMETHODCALLTYPE rendertarget_view_Release(IWineD3DRendertargetVie
 
 /* IWineD3DBase methods */
 
-static HRESULT STDMETHODCALLTYPE rendertarget_view_GetParent(IWineD3DRendertargetView *iface, IUnknown **parent)
+static void * STDMETHODCALLTYPE rendertarget_view_GetParent(IWineD3DRendertargetView *iface)
 {
-    struct wined3d_rendertarget_view *This = (struct wined3d_rendertarget_view *)iface;
-
-    IUnknown_AddRef(This->parent);
-    *parent = This->parent;
+    TRACE("iface %p.\n", iface);
 
-    return WINED3D_OK;
+    return ((struct wined3d_rendertarget_view *)iface)->parent;
 }
 
 /* IWineD3DRendertargetView methods */
@@ -110,7 +107,7 @@ static const struct IWineD3DRendertargetViewVtbl wined3d_rendertarget_view_vtbl
 };
 
 void wined3d_rendertarget_view_init(struct wined3d_rendertarget_view *view,
-        IWineD3DResource *resource, IUnknown *parent)
+        IWineD3DResource *resource, void *parent)
 {
     view->vtbl = &wined3d_rendertarget_view_vtbl;
     view->refcount = 1;
index 42e61e6..8d42d54 100644 (file)
@@ -30,7 +30,6 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d_surface);
 static void volume_bind_and_dirtify(IWineD3DVolume *iface) {
     IWineD3DVolumeImpl *This = (IWineD3DVolumeImpl *)iface;
     const struct wined3d_gl_info *gl_info = &This->resource.device->adapter->gl_info;
-    IWineD3DVolumeTexture *texture;
     DWORD active_sampler;
 
     /* We don't need a specific texture unit, but after binding the texture the current unit is dirty.
@@ -60,12 +59,7 @@ static void volume_bind_and_dirtify(IWineD3DVolume *iface) {
         IWineD3DDeviceImpl_MarkStateDirty(This->resource.device, STATE_SAMPLER(active_sampler));
     }
 
-    if (SUCCEEDED(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DVolumeTexture, (void **)&texture))) {
-        IWineD3DVolumeTexture_BindTexture(texture, FALSE);
-        IWineD3DVolumeTexture_Release(texture);
-    } else {
-        ERR("Volume should be part of a volume texture\n");
-    }
+    IWineD3DVolumeTexture_BindTexture((IWineD3DVolumeTexture *)This->container, FALSE);
 }
 
 void volume_add_dirty_box(IWineD3DVolume *iface, const WINED3DBOX *dirty_box)
@@ -93,6 +87,13 @@ void volume_add_dirty_box(IWineD3DVolume *iface, const WINED3DBOX *dirty_box)
     }
 }
 
+void volume_set_container(IWineD3DVolumeImpl *volume, struct IWineD3DVolumeTextureImpl *container)
+{
+    TRACE("volume %p, container %p.\n", volume, container);
+
+    volume->container = container;
+}
+
 /* *******************************************
    IWineD3DVolume IUnknown parts follow
    ******************************************* */
@@ -122,12 +123,15 @@ static ULONG WINAPI IWineD3DVolumeImpl_AddRef(IWineD3DVolume *iface) {
     return InterlockedIncrement(&This->resource.ref);
 }
 
+/* Do not call while under the GL lock. */
 static ULONG WINAPI IWineD3DVolumeImpl_Release(IWineD3DVolume *iface) {
     IWineD3DVolumeImpl *This = (IWineD3DVolumeImpl *)iface;
     ULONG ref;
     TRACE("(%p) : Releasing from %d\n", This, This->resource.ref);
     ref = InterlockedDecrement(&This->resource.ref);
-    if (ref == 0) {
+
+    if (!ref)
+    {
         resource_cleanup((IWineD3DResource *)iface);
         This->resource.parent_ops->wined3d_object_destroyed(This->resource.parent);
         HeapFree(GetProcessHeap(), 0, This);
@@ -138,8 +142,11 @@ static ULONG WINAPI IWineD3DVolumeImpl_Release(IWineD3DVolume *iface) {
 /* ****************************************************
    IWineD3DVolume IWineD3DResource parts follow
    **************************************************** */
-static HRESULT WINAPI IWineD3DVolumeImpl_GetParent(IWineD3DVolume *iface, IUnknown **pParent) {
-    return resource_get_parent((IWineD3DResource *)iface, pParent);
+static void * WINAPI IWineD3DVolumeImpl_GetParent(IWineD3DVolume *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    return ((IWineD3DVolumeImpl *)iface)->resource.parent;
 }
 
 static HRESULT WINAPI IWineD3DVolumeImpl_SetPrivateData(IWineD3DVolume *iface, REFGUID refguid, CONST void* pData, DWORD SizeOfData, DWORD Flags) {
@@ -162,58 +169,40 @@ static DWORD WINAPI IWineD3DVolumeImpl_GetPriority(IWineD3DVolume *iface) {
     return resource_get_priority((IWineD3DResource *)iface);
 }
 
+/* Do not call while under the GL lock. */
 static void WINAPI IWineD3DVolumeImpl_PreLoad(IWineD3DVolume *iface) {
     FIXME("iface %p stub!\n", iface);
 }
 
-static void WINAPI IWineD3DVolumeImpl_UnLoad(IWineD3DVolume *iface) {
-    /* The whole content is shadowed on This->resource.allocatedMemory, and the
-     * texture name is managed by the VolumeTexture container
-     */
-    TRACE("(%p): Nothing to do\n", iface);
+/* Do not call while under the GL lock. */
+static void WINAPI IWineD3DVolumeImpl_UnLoad(IWineD3DVolume *iface)
+{
+    TRACE("iface %p.\n", iface);
+
+    /* The whole content is shadowed on This->resource.allocatedMemory, and
+     * the texture name is managed by the VolumeTexture container. */
+
+    resource_unload((IWineD3DResourceImpl *)iface);
 }
 
 static WINED3DRESOURCETYPE WINAPI IWineD3DVolumeImpl_GetType(IWineD3DVolume *iface) {
     return resource_get_type((IWineD3DResource *)iface);
 }
 
-/* *******************************************
-   IWineD3DVolume parts follow
-   ******************************************* */
-static HRESULT WINAPI IWineD3DVolumeImpl_GetContainer(IWineD3DVolume *iface, REFIID riid, void** ppContainer) {
-    IWineD3DVolumeImpl *This = (IWineD3DVolumeImpl *)iface;
-
-    TRACE("(This %p, riid %s, ppContainer %p)\n", This, debugstr_guid(riid), ppContainer);
-
-    if (!ppContainer) {
-        ERR("Called without a valid ppContainer.\n");
-        return E_FAIL;
-    }
-
-    /* Although surfaces can be standalone, volumes can't */
-    if (!This->container) {
-        ERR("Volume without an container. Should not happen.\n");
-        return E_FAIL;
-    }
-
-    TRACE("Relaying to QueryInterface\n");
-    return IUnknown_QueryInterface(This->container, riid, ppContainer);
-}
-
-static HRESULT WINAPI IWineD3DVolumeImpl_GetDesc(IWineD3DVolume *iface, WINED3DVOLUME_DESC* pDesc) {
-    IWineD3DVolumeImpl *This = (IWineD3DVolumeImpl *)iface;
-    TRACE("(%p) : copying into %p\n", This, pDesc);
-
-    pDesc->Format = This->resource.format_desc->format;
-    pDesc->Type = This->resource.resourceType;
-    pDesc->Usage = This->resource.usage;
-    pDesc->Pool = This->resource.pool;
-    pDesc->Size = This->resource.size; /* dx8 only */
-    pDesc->Width = This->currentDesc.Width;
-    pDesc->Height = This->currentDesc.Height;
-    pDesc->Depth = This->currentDesc.Depth;
-
-    return WINED3D_OK;
+static void WINAPI IWineD3DVolumeImpl_GetDesc(IWineD3DVolume *iface, WINED3DVOLUME_DESC *desc)
+{
+    IWineD3DVolumeImpl *volume = (IWineD3DVolumeImpl *)iface;
+
+    TRACE("iface %p, desc %p.\n", iface, desc);
+
+    desc->Format = volume->resource.format->id;
+    desc->Type = volume->resource.resourceType;
+    desc->Usage = volume->resource.usage;
+    desc->Pool = volume->resource.pool;
+    desc->Size = volume->resource.size; /* dx8 only */
+    desc->Width = volume->currentDesc.Width;
+    desc->Height = volume->currentDesc.Height;
+    desc->Depth = volume->currentDesc.Depth;
 }
 
 static HRESULT WINAPI IWineD3DVolumeImpl_LockBox(IWineD3DVolume *iface, WINED3DLOCKED_BOX* pLockedVolume, CONST WINED3DBOX* pBox, DWORD Flags) {
@@ -227,8 +216,8 @@ static HRESULT WINAPI IWineD3DVolumeImpl_LockBox(IWineD3DVolume *iface, WINED3DL
     /* fixme: should we really lock as such? */
     TRACE("(%p) : box=%p, output pbox=%p, allMem=%p\n", This, pBox, pLockedVolume, This->resource.allocatedMemory);
 
-    pLockedVolume->RowPitch = This->resource.format_desc->byte_count * This->currentDesc.Width; /* Bytes / row   */
-    pLockedVolume->SlicePitch = This->resource.format_desc->byte_count
+    pLockedVolume->RowPitch = This->resource.format->byte_count * This->currentDesc.Width; /* Bytes / row   */
+    pLockedVolume->SlicePitch = This->resource.format->byte_count
             * This->currentDesc.Width * This->currentDesc.Height;                               /* Bytes / slice */
     if (!pBox) {
         TRACE("No box supplied - all is ok\n");
@@ -244,7 +233,7 @@ static HRESULT WINAPI IWineD3DVolumeImpl_LockBox(IWineD3DVolume *iface, WINED3DL
         pLockedVolume->pBits = This->resource.allocatedMemory
                 + (pLockedVolume->SlicePitch * pBox->Front)     /* FIXME: is front < back or vica versa? */
                 + (pLockedVolume->RowPitch * pBox->Top)
-                + (pBox->Left * This->resource.format_desc->byte_count);
+                + (pBox->Left * This->resource.format->byte_count);
         This->lockedBox.Left   = pBox->Left;
         This->lockedBox.Top    = pBox->Top;
         This->lockedBox.Front  = pBox->Front;
@@ -255,27 +244,12 @@ static HRESULT WINAPI IWineD3DVolumeImpl_LockBox(IWineD3DVolume *iface, WINED3DL
 
     if (Flags & (WINED3DLOCK_NO_DIRTY_UPDATE | WINED3DLOCK_READONLY)) {
       /* Don't dirtify */
-    } else {
-      /**
-       * Dirtify on lock
-       * as seen in msdn docs
-       */
-      volume_add_dirty_box(iface, &This->lockedBox);
-
-      /**  Dirtify Container if needed */
-      if (NULL != This->container) {
-
-        IWineD3DVolumeTexture *cont = (IWineD3DVolumeTexture*) This->container;
-        WINED3DRESOURCETYPE containerType = IWineD3DBaseTexture_GetType((IWineD3DBaseTexture *) cont);
-
-        if (containerType == WINED3DRTYPE_VOLUMETEXTURE) {
-          IWineD3DBaseTextureImpl* pTexture = (IWineD3DBaseTextureImpl*) cont;
-          pTexture->baseTexture.texture_rgb.dirty = TRUE;
-          pTexture->baseTexture.texture_srgb.dirty = TRUE;
-        } else {
-          FIXME("Set dirty on container type %d\n", containerType);
-        }
-      }
+    }
+    else
+    {
+        volume_add_dirty_box(iface, &This->lockedBox);
+        This->container->baseTexture.texture_rgb.dirty = TRUE;
+        This->container->baseTexture.texture_srgb.dirty = TRUE;
     }
 
     This->locked = TRUE;
@@ -298,53 +272,26 @@ static HRESULT WINAPI IWineD3DVolumeImpl_UnlockBox(IWineD3DVolume *iface) {
 
 /* Internal use functions follow : */
 
-static HRESULT WINAPI IWineD3DVolumeImpl_SetContainer(IWineD3DVolume *iface, IWineD3DBase* container) {
-    IWineD3DVolumeImpl *This = (IWineD3DVolumeImpl *)iface;
-
-    TRACE("This %p, container %p\n", This, container);
-
-    /* We can't keep a reference to the container, since the container already keeps a reference to us. */
-
-    TRACE("Setting container to %p from %p\n", container, This->container);
-    This->container = container;
-
-    return WINED3D_OK;
-}
-
 /* Context activation is done by the caller. */
 static HRESULT WINAPI IWineD3DVolumeImpl_LoadTexture(IWineD3DVolume *iface, int gl_level, BOOL srgb_mode)
 {
     IWineD3DVolumeImpl *This = (IWineD3DVolumeImpl *)iface;
     const struct wined3d_gl_info *gl_info = &This->resource.device->adapter->gl_info;
-    const struct wined3d_format_desc *glDesc = This->resource.format_desc;
+    const struct wined3d_format *format = This->resource.format;
 
-    TRACE("(%p) : level %u, format %s (0x%08x)\n", This, gl_level, debug_d3dformat(glDesc->format), glDesc->format);
+    TRACE("iface %p, level %u, srgb %#x, format %s (%#x).\n",
+            iface, gl_level, srgb_mode, debug_d3dformat(format->id), format->id);
 
     volume_bind_and_dirtify(iface);
 
     TRACE("Calling glTexImage3D %x level=%d, intfmt=%x, w=%d, h=%d,d=%d, 0=%d, glFmt=%x, glType=%x, Mem=%p\n",
-            GL_TEXTURE_3D,
-            gl_level,
-            glDesc->glInternal,
-            This->currentDesc.Width,
-            This->currentDesc.Height,
-            This->currentDesc.Depth,
-            0,
-            glDesc->glFormat,
-            glDesc->glType,
-            This->resource.allocatedMemory);
+            GL_TEXTURE_3D, gl_level, format->glInternal, This->currentDesc.Width, This->currentDesc.Height,
+            This->currentDesc.Depth, 0, format->glFormat, format->glType, This->resource.allocatedMemory);
 
     ENTER_GL();
-    GL_EXTCALL(glTexImage3DEXT(GL_TEXTURE_3D,
-                gl_level,
-                glDesc->glInternal,
-                This->currentDesc.Width,
-                This->currentDesc.Height,
-                This->currentDesc.Depth,
-                0,
-                glDesc->glFormat,
-                glDesc->glType,
-                This->resource.allocatedMemory));
+    GL_EXTCALL(glTexImage3DEXT(GL_TEXTURE_3D, gl_level, format->glInternal,
+            This->currentDesc.Width, This->currentDesc.Height, This->currentDesc.Depth,
+            0, format->glFormat, format->glType, This->resource.allocatedMemory));
     checkGLcall("glTexImage3D");
     LEAVE_GL();
 
@@ -373,21 +320,19 @@ static const IWineD3DVolumeVtbl IWineD3DVolume_Vtbl =
     IWineD3DVolumeImpl_UnLoad,
     IWineD3DVolumeImpl_GetType,
     /* IWineD3DVolume */
-    IWineD3DVolumeImpl_GetContainer,
     IWineD3DVolumeImpl_GetDesc,
     IWineD3DVolumeImpl_LockBox,
     IWineD3DVolumeImpl_UnlockBox,
     /* Internal interface */
     IWineD3DVolumeImpl_LoadTexture,
-    IWineD3DVolumeImpl_SetContainer
 };
 
 HRESULT volume_init(IWineD3DVolumeImpl *volume, IWineD3DDeviceImpl *device, UINT width,
-        UINT height, UINT depth, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        UINT height, UINT depth, DWORD usage, enum wined3d_format_id format_id, WINED3DPOOL pool,
+        void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, gl_info);
+    const struct wined3d_format *format = wined3d_get_format(gl_info, format_id);
     HRESULT hr;
 
     if (!gl_info->supported[EXT_TEXTURE3D])
@@ -399,7 +344,7 @@ HRESULT volume_init(IWineD3DVolumeImpl *volume, IWineD3DDeviceImpl *device, UINT
     volume->lpVtbl = &IWineD3DVolume_Vtbl;
 
     hr = resource_init((IWineD3DResource *)volume, WINED3DRTYPE_VOLUME, device,
-            width * height * depth * format_desc->byte_count, usage, format_desc, pool, parent, parent_ops);
+            width * height * depth * format->byte_count, usage, format, pool, parent, parent_ops);
     if (FAILED(hr))
     {
         WARN("Failed to initialize resource, returning %#x.\n", hr);
index 9fccb2b..a2c0c6d 100644 (file)
@@ -26,6 +26,7 @@
 
 WINE_DEFAULT_DEBUG_CHANNEL(d3d_texture);
 
+/* Do not call while under the GL lock. */
 static void volumetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3DSRGB srgb)
 {
     /* Override the IWineD3DResource Preload method. */
@@ -42,7 +43,7 @@ static void volumetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINE
     if (!device->isInDraw) context = context_acquire(device, NULL);
     else if (gl_info->supported[EXT_TEXTURE_SRGB] && This->baseTexture.bindCount > 0)
     {
-        srgb_mode = device->stateBlock->samplerState[This->baseTexture.sampler][WINED3DSAMP_SRGBTEXTURE];
+        srgb_mode = device->stateBlock->state.sampler_states[This->baseTexture.sampler][WINED3DSAMP_SRGBTEXTURE];
         srgb_was_toggled = This->baseTexture.is_srgb != srgb_mode;
         This->baseTexture.is_srgb = srgb_mode;
     }
@@ -85,13 +86,13 @@ static void volumetexture_cleanup(IWineD3DVolumeTextureImpl *This)
 
     for (i = 0; i < This->baseTexture.level_count; ++i)
     {
-        IWineD3DVolume *volume = (IWineD3DVolume *)This->baseTexture.sub_resources[i];
+        IWineD3DVolumeImpl *volume = (IWineD3DVolumeImpl *)This->baseTexture.sub_resources[i];
 
         if (volume)
         {
             /* Cleanup the container. */
-            IWineD3DVolume_SetContainer(volume, NULL);
-            IWineD3DVolume_Release(volume);
+            volume_set_container(volume, NULL);
+            IWineD3DVolume_Release((IWineD3DVolume *)volume);
         }
     }
     basetexture_cleanup((IWineD3DBaseTexture *)This);
@@ -124,6 +125,7 @@ static ULONG WINAPI IWineD3DVolumeTextureImpl_AddRef(IWineD3DVolumeTexture *ifac
     return InterlockedIncrement(&This->resource.ref);
 }
 
+/* Do not call while under the GL lock. */
 static ULONG WINAPI IWineD3DVolumeTextureImpl_Release(IWineD3DVolumeTexture *iface) {
     IWineD3DVolumeTextureImpl *This = (IWineD3DVolumeTextureImpl *)iface;
     ULONG ref;
@@ -165,6 +167,7 @@ static void WINAPI IWineD3DVolumeTextureImpl_PreLoad(IWineD3DVolumeTexture *ifac
     volumetexture_internal_preload((IWineD3DBaseTexture *) iface, SRGB_ANY);
 }
 
+/* Do not call while under the GL lock. */
 static void WINAPI IWineD3DVolumeTextureImpl_UnLoad(IWineD3DVolumeTexture *iface) {
     unsigned int i;
     IWineD3DVolumeTextureImpl *This = (IWineD3DVolumeTextureImpl *)iface;
@@ -186,8 +189,11 @@ static WINED3DRESOURCETYPE WINAPI IWineD3DVolumeTextureImpl_GetType(IWineD3DVolu
     return resource_get_type((IWineD3DResource *)iface);
 }
 
-static HRESULT WINAPI IWineD3DVolumeTextureImpl_GetParent(IWineD3DVolumeTexture *iface, IUnknown **pParent) {
-    return resource_get_parent((IWineD3DResource *)iface, pParent);
+static void * WINAPI IWineD3DVolumeTextureImpl_GetParent(IWineD3DVolumeTexture *iface)
+{
+    TRACE("iface %p\n", iface);
+
+    return ((IWineD3DVolumeTextureImpl *)iface)->resource.parent;
 }
 
 /* ******************************************************
@@ -236,13 +242,6 @@ static HRESULT WINAPI IWineD3DVolumeTextureImpl_BindTexture(IWineD3DVolumeTextur
     return basetexture_bind((IWineD3DBaseTexture *)iface, srgb, &dummy);
 }
 
-static UINT WINAPI IWineD3DVolumeTextureImpl_GetTextureDimensions(IWineD3DVolumeTexture *iface)
-{
-    TRACE("iface %p.\n", iface);
-
-    return GL_TEXTURE_3D;
-}
-
 static BOOL WINAPI IWineD3DVolumeTextureImpl_IsCondNP2(IWineD3DVolumeTexture *iface)
 {
     TRACE("iface %p.\n", iface);
@@ -267,7 +266,9 @@ static HRESULT WINAPI IWineD3DVolumeTextureImpl_GetLevelDesc(IWineD3DVolumeTextu
         return WINED3DERR_INVALIDCALL;
     }
 
-    return IWineD3DVolume_GetDesc(volume, desc);
+    IWineD3DVolume_GetDesc(volume, desc);
+
+    return WINED3D_OK;
 }
 
 static HRESULT WINAPI IWineD3DVolumeTextureImpl_GetVolumeLevel(IWineD3DVolumeTexture *iface,
@@ -373,7 +374,6 @@ static const IWineD3DVolumeTextureVtbl IWineD3DVolumeTexture_Vtbl =
     IWineD3DVolumeTextureImpl_GetDirty,
     /* not in d3d */
     IWineD3DVolumeTextureImpl_BindTexture,
-    IWineD3DVolumeTextureImpl_GetTextureDimensions,
     IWineD3DVolumeTextureImpl_IsCondNP2,
     /* volume texture */
     IWineD3DVolumeTextureImpl_GetLevelDesc,
@@ -384,18 +384,18 @@ static const IWineD3DVolumeTextureVtbl IWineD3DVolumeTexture_Vtbl =
 };
 
 HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT height,
-        UINT depth, UINT levels, IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format,
-        WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
+        UINT depth, UINT levels, IWineD3DDeviceImpl *device, DWORD usage, enum wined3d_format_id format_id,
+        WINED3DPOOL pool, void *parent, const struct wined3d_parent_ops *parent_ops)
 {
     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
-    const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, gl_info);
+    const struct wined3d_format *format = wined3d_get_format(gl_info, format_id);
     UINT tmp_w, tmp_h, tmp_d;
     unsigned int i;
     HRESULT hr;
 
     /* TODO: It should only be possible to create textures for formats
      * that are reported as supported. */
-    if (WINED3DFMT_UNKNOWN >= format)
+    if (WINED3DFMT_UNKNOWN >= format_id)
     {
         WARN("(%p) : Texture cannot be created with a format of WINED3DFMT_UNKNOWN.\n", texture);
         return WINED3DERR_INVALIDCALL;
@@ -433,7 +433,7 @@ HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT
     texture->lpVtbl = &IWineD3DVolumeTexture_Vtbl;
 
     hr = basetexture_init((IWineD3DBaseTextureImpl *)texture, 1, levels,
-            WINED3DRTYPE_VOLUMETEXTURE, device, 0, usage, format_desc, pool, parent, parent_ops);
+            WINED3DRTYPE_VOLUMETEXTURE, device, 0, usage, format, pool, parent, parent_ops);
     if (FAILED(hr))
     {
         WARN("Failed to initialize basetexture, returning %#x.\n", hr);
@@ -445,6 +445,7 @@ HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT
     texture->baseTexture.pow2Matrix[5] = 1.0f;
     texture->baseTexture.pow2Matrix[10] = 1.0f;
     texture->baseTexture.pow2Matrix[15] = 1.0f;
+    texture->baseTexture.target = GL_TEXTURE_3D;
 
     /* Generate all the surfaces. */
     tmp_w = width;
@@ -457,7 +458,7 @@ HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT
 
         /* Create the volume. */
         hr = IWineD3DDeviceParent_CreateVolume(device->device_parent, parent,
-                tmp_w, tmp_h, tmp_d, format, pool, usage, &volume);
+                tmp_w, tmp_h, tmp_d, format_id, pool, usage, &volume);
         if (FAILED(hr))
         {
             ERR("Creating a volume for the volume texture failed, hr %#x.\n", hr);
@@ -466,7 +467,7 @@ HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT
         }
 
         /* Set its container to this texture. */
-        IWineD3DVolume_SetContainer(volume, (IWineD3DBase *)texture);
+        volume_set_container((IWineD3DVolumeImpl *)volume, texture);
         texture->baseTexture.sub_resources[i] = (IWineD3DResourceImpl *)volume;
 
         /* Calculate the next mipmap level. */
index f65ee31..c375b38 100644 (file)
@@ -1,4 +1,4 @@
 @ stdcall WineDirect3DCreate(long ptr)
-@ stdcall WineDirect3DCreateClipper(ptr)
+@ stdcall WineDirect3DCreateClipper()
 @ stdcall wined3d_mutex_lock()
 @ stdcall wined3d_mutex_unlock()
index 4ece7e7..9c2c0c1 100644 (file)
@@ -1353,6 +1353,7 @@ void (WINE_GLAPI *glVertex4sv)(const GLshort *v) DECLSPEC_HIDDEN;
 void (WINE_GLAPI *glVertexPointer)(GLint size, GLenum type, GLsizei stride, const GLvoid *pointer) DECLSPEC_HIDDEN;
 void (WINE_GLAPI *glViewport)(GLint x, GLint y, GLsizei width, GLsizei height) DECLSPEC_HIDDEN;
 void (WINE_GLAPI *glPointParameterfv)(GLenum pname, const GLfloat *params) DECLSPEC_HIDDEN;
+void (WINE_GLAPI *glPointParameteri)(GLenum name, GLint value) DECLSPEC_HIDDEN;
 
 /* glFinish and glFlush are always loaded from opengl32.dll, thus they always have
  * __stdcall calling convention.
@@ -1708,6 +1709,7 @@ BOOL (WINAPI *pwglShareLists)(HGLRC, HGLRC) DECLSPEC_HIDDEN;
     USE_GL_FUNC(glVertexPointer) \
     USE_GL_FUNC(glViewport) \
     USE_GL_FUNC(glPointParameterfv) \
+    USE_GL_FUNC(glPointParameteri) \
 
 #define WGL_FUNCS_GEN \
     USE_WGL_FUNC(wglCreateContext) \
@@ -1758,6 +1760,7 @@ typedef enum wined3d_gl_extension
     ARB_SYNC,
     ARB_TEXTURE_BORDER_CLAMP,
     ARB_TEXTURE_COMPRESSION,
+    ARB_TEXTURE_COMPRESSION_RGTC,
     ARB_TEXTURE_CUBE_MAP,
     ARB_TEXTURE_ENV_ADD,
     ARB_TEXTURE_ENV_COMBINE,
@@ -1784,6 +1787,7 @@ typedef enum wined3d_gl_extension
     EXT_BLEND_FUNC_SEPARATE,
     EXT_BLEND_MINMAX,
     EXT_DRAW_BUFFERS2,
+    EXT_DEPTH_BOUNDS_TEST,
     EXT_FOG_COORD,
     EXT_FRAMEBUFFER_BLIT,
     EXT_FRAMEBUFFER_MULTISAMPLE,
@@ -1816,6 +1820,7 @@ typedef enum wined3d_gl_extension
     NV_FRAGMENT_PROGRAM_OPTION,
     NV_HALF_FLOAT,
     NV_LIGHT_MAX_EXPONENT,
+    NV_POINT_SPRITE,
     NV_REGISTER_COMBINERS,
     NV_REGISTER_COMBINERS2,
     NV_TEXGEN_REFLECTION,
@@ -1834,7 +1839,8 @@ typedef enum wined3d_gl_extension
     WGL_ARB_PIXEL_FORMAT,
     WGL_WINE_PIXEL_FORMAT_PASSTHROUGH,
     /* Internally used */
-    WINE_NORMALIZED_TEXRECT,
+    WINED3D_GL_NORMALIZED_TEXRECT,
+    WINED3D_GL_VERSION_2_0,
 
     WINED3D_GL_EXT_COUNT,
 } GL_SupportedExt;
@@ -2447,6 +2453,15 @@ typedef GLvoid (WINE_GLAPI *PGLFNGETSYNCIVPROC)(GLsync sync, GLenum pname, GLsiz
 #define GL_CLAMP_TO_BORDER_ARB                              0x812d
 #endif
 
+/* GL_ARB_texture_compression_rgtc */
+#ifndef GL_ARB_texture_compression_rgtc
+#define GL_ARB_texture_compression_rgtc 1
+#define GL_COMPRESSED_RED_RGTC1                             0x8dbb
+#define GL_COMPRESSED_SIGNED_RED_RGTC1                      0x8dbc
+#define GL_COMPRESSED_RED_GREEN_RGTC2                       0x8dbd
+#define GL_COMPRESSED_SIGNED_RED_GREEN_RGTC2                0x8dbe
+#endif
+
 /* GL_ARB_texture_cube_map */
 #ifndef GL_ARB_texture_cube_map
 #define GL_ARB_texture_cube_map 1
@@ -2968,6 +2983,14 @@ typedef void (WINE_GLAPI *PGLFNBLENDEQUATIONSEPARATEEXTPROC)(GLenum modeRGB, GLe
 typedef void (WINE_GLAPI *PGLFNBLENDFUNCSEPARATEEXTPROC)(GLenum sfactorRGB, GLenum dfactorRGB,
         GLenum sfactorAlpha, GLenum dfactorAlpha);
 
+/* GL_EXT_depth_bounds_test */
+#ifndef GL_EXT_depth_bounds_test
+#define GL_EXT_depth_bounds_test 1
+#define GL_DEPTH_BOUNDS_TEST_EXT                            0x8890
+#define GL_DEPTH_BOUNDS_EXT                                 0x8891
+#endif
+typedef void (WINE_GLAPI *PGLFNDEPTHBOUNDSEXTPROC)(GLclampd zmin, GLclampd zmax);
+
 /* GL_EXT_draw_buffers2 */
 typedef GLvoid (WINE_GLAPI *PGLFNCOLORMASKINDEXEDEXTPROC)(GLuint buffer_idx, GLboolean r, GLboolean g,
         GLboolean b, GLboolean a);
@@ -3479,6 +3502,16 @@ typedef void (WINE_GLAPI *PGLFNVERTEXATTRIBS4HVNVPROC)(GLuint index, GLsizei n,
 #define GL_MAX_SPOT_EXPONENT_NV                             0x8505
 #endif
 
+/* GL_NV_point_sprite */
+#ifndef GL_NV_point_sprite
+#define GL_NV_point_sprite 1
+#define GL_NV_POINT_SPRITE_NV                               0x8861
+#define GL_NV_COORD_REPLACE_NV                              0x8862
+#define GL_NV_POINT_SPRITE_R_MODE_NV                        0x8863
+#endif
+typedef void (WINE_GLAPI *PGLFNPOINTPARAMETERIVNVPROC)(GLenum pname, const GLint *params);
+typedef void (WINE_GLAPI *PGLFNPOINTPARAMETERINVPROC)(GLenum pname, GLint param);
+
 /* GL_NV_register_combiners */
 #ifndef GL_NV_register_combiners
 #define GL_NV_register_combiners 1
@@ -4197,6 +4230,9 @@ typedef BOOL (WINAPI *WINED3D_PFNWGLSETPIXELFORMATWINE)(HDC hdc, int iPixelForma
     /* GL_EXT_blend_func_separate */ \
     USE_GL_FUNC(PGLFNBLENDEQUATIONSEPARATEEXTPROC, \
             glBlendEquationSeparateEXT,                 EXT_BLEND_EQUATION_SEPARATE,    NULL) \
+    /* GL_EXT_depth_bounds_test */ \
+    USE_GL_FUNC(PGLFNDEPTHBOUNDSEXTPROC, \
+            glDepthBoundsEXT,                           EXT_DEPTH_BOUNDS_TEST,          NULL) \
     /* GL_EXT_draw_buffers2 */ \
     USE_GL_FUNC(PGLFNCOLORMASKINDEXEDEXTPROC, \
             glColorMaskIndexedEXT,                      EXT_DRAW_BUFFERS2,              NULL) \
@@ -4474,6 +4510,11 @@ typedef BOOL (WINAPI *WINED3D_PFNWGLSETPIXELFORMATWINE)(HDC hdc, int iPixelForma
             glVertexAttribs3hvNV,                       NV_HALF_FLOAT,                  NULL) \
     USE_GL_FUNC(PGLFNVERTEXATTRIBS4HVNVPROC, \
             glVertexAttribs4hvNV,                       NV_HALF_FLOAT,                  NULL) \
+    /* GL_NV_point_sprite */ \
+    USE_GL_FUNC(PGLFNPOINTPARAMETERIVNVPROC, \
+            glPointParameterivNV,                       NV_POINT_SPRITE,                NULL) \
+    USE_GL_FUNC(PGLFNPOINTPARAMETERINVPROC, \
+            glPointParameteriNV,                        NV_POINT_SPRITE,                NULL) \
     /* GL_NV_register_combiners */ \
     USE_GL_FUNC(PGLFNCOMBINERINPUTNVPROC, \
             glCombinerInputNV,                          NV_REGISTER_COMBINERS,          NULL) \
index 6330eba..26945ef 100644 (file)
@@ -46,8 +46,8 @@ struct wined3d_wndproc_table
 static struct wined3d_wndproc_table wndproc_table;
 
 int num_lock = 0;
-void (*CDECL wine_tsx11_lock_ptr)(void) = NULL;
-void (*CDECL wine_tsx11_unlock_ptr)(void) = NULL;
+void (CDECL *wine_tsx11_lock_ptr)(void) = NULL;
+void (CDECL *wine_tsx11_unlock_ptr)(void) = NULL;
 
 static CRITICAL_SECTION wined3d_cs;
 static CRITICAL_SECTION_DEBUG wined3d_cs_debug =
@@ -70,13 +70,14 @@ wined3d_settings_t wined3d_settings =
     RTL_READTEX,    /* Default render target locking method */
     PCI_VENDOR_NONE,/* PCI Vendor ID */
     PCI_DEVICE_NONE,/* PCI Device ID */
-    0,              /* The default of memory is set in FillGLCaps */
+    0,              /* The default of memory is set in init_driver_info */
     NULL,           /* No wine logo by default */
     FALSE,          /* Disable multisampling for now due to Nvidia driver bugs which happens for some users */
     FALSE,          /* No strict draw ordering. */
 };
 
-IWineD3D * WINAPI WineDirect3DCreate(UINT version, IUnknown *parent)
+/* Do not call while under the GL lock. */
+IWineD3D * WINAPI WineDirect3DCreate(UINT version, void *parent)
 {
     IWineD3DImpl *object;
     HRESULT hr;
@@ -101,19 +102,19 @@ IWineD3D * WINAPI WineDirect3DCreate(UINT version, IUnknown *parent)
     return (IWineD3D *)object;
 }
 
-static inline DWORD get_config_key(HKEY defkey, HKEY appkey, const char* name, char* buffer, DWORD size)
+static DWORD get_config_key(HKEY defkey, HKEY appkey, const char *name, char *buffer, DWORD size)
 {
-    if (0 != appkey && !RegQueryValueExA( appkey, name, 0, NULL, (LPBYTE) buffer, &size )) return 0;
-    if (0 != defkey && !RegQueryValueExA( defkey, name, 0, NULL, (LPBYTE) buffer, &size )) return 0;
+    if (appkey && !RegQueryValueExA(appkey, name, 0, NULL, (BYTE *)buffer, &size)) return 0;
+    if (defkey && !RegQueryValueExA(defkey, name, 0, NULL, (BYTE *)buffer, &size)) return 0;
     return ERROR_FILE_NOT_FOUND;
 }
 
-static inline DWORD get_config_key_dword(HKEY defkey, HKEY appkey, const char* name, DWORD *data)
+static DWORD get_config_key_dword(HKEY defkey, HKEY appkey, const char *name, DWORD *data)
 {
     DWORD type;
     DWORD size = sizeof(DWORD);
-    if (0 != appkey && !RegQueryValueExA( appkey, name, 0, &type, (LPBYTE) data, &size ) && (type == REG_DWORD)) return 0;
-    if (0 != defkey && !RegQueryValueExA( defkey, name, 0, &type, (LPBYTE) data, &size ) && (type == REG_DWORD)) return 0;
+    if (appkey && !RegQueryValueExA(appkey, name, 0, &type, (BYTE *)data, &size) && (type == REG_DWORD)) return 0;
+    if (defkey && !RegQueryValueExA(defkey, name, 0, &type, (BYTE *)data, &size) && (type == REG_DWORD)) return 0;
     return ERROR_FILE_NOT_FOUND;
 }
 
@@ -199,7 +200,7 @@ static BOOL wined3d_dll_init(HINSTANCE hInstDLL)
         }
     }
 
-    if ( 0 != hkey || 0 != appkey )
+    if (hkey || appkey)
     {
         if ( !get_config_key( hkey, appkey, "VertexShaderMode", buffer, size) )
         {
index 9a5c7c4..3651c32 100644 (file)
@@ -157,11 +157,11 @@ struct min_lookup
     GLenum mip[WINED3DTEXF_LINEAR + 1];
 };
 
-const struct min_lookup minMipLookup[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
-const struct min_lookup minMipLookup_noFilter[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
-const struct min_lookup minMipLookup_noMip[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
-const GLenum magLookup[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
-const GLenum magLookup_noFilter[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
+extern const struct min_lookup minMipLookup[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
+extern const struct min_lookup minMipLookup_noFilter[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
+extern const struct min_lookup minMipLookup_noMip[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
+extern const GLenum magLookup[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
+extern const GLenum magLookup_noFilter[WINED3DTEXF_LINEAR + 1] DECLSPEC_HIDDEN;
 
 static inline GLenum wined3d_gl_mag_filter(const GLenum mag_lookup[], WINED3DTEXTUREFILTERTYPE mag_filter)
 {
@@ -192,9 +192,9 @@ static inline float float_16_to_32(const unsigned short *in) {
 
     if(e == 0) {
         if(m == 0) return sgn * 0.0f; /* +0.0 or -0.0 */
-        else return sgn * pow(2, -14.0f) * ((float)m / 1024.0f);
+        else return sgn * powf(2, -14.0f) * ((float)m / 1024.0f);
     } else if(e < 31) {
-        return sgn * pow(2, (float)e - 15.0f) * (1.0f + ((float)m / 1024.0f));
+        return sgn * powf(2, (float)e - 15.0f) * (1.0f + ((float)m / 1024.0f));
     } else {
         if(m == 0) return sgn / 0.0f; /* +INF / -INF */
         else return 0.0f / 0.0f; /* NAN */
@@ -205,16 +205,16 @@ static inline float float_24_to_32(DWORD in)
 {
     const float sgn = in & 0x800000 ? -1.0f : 1.0f;
     const unsigned short e = (in & 0x780000) >> 19;
-    const unsigned short m = in & 0x7ffff;
+    const unsigned int m = in & 0x7ffff;
 
     if (e == 0)
     {
         if (m == 0) return sgn * 0.0f; /* +0.0 or -0.0 */
-        else return sgn * pow(2, -6.0f) * ((float)m / 524288.0f);
+        else return sgn * powf(2, -6.0f) * ((float)m / 524288.0f);
     }
     else if (e < 15)
     {
-        return sgn * pow(2, (float)e - 7.0f) * (1.0f + ((float)m / 524288.0f));
+        return sgn * powf(2, (float)e - 7.0f) * (1.0f + ((float)m / 524288.0f));
     }
     else
     {
@@ -308,12 +308,13 @@ typedef enum _WINED3DSHADER_PARAM_REGISTER_TYPE
     WINED3DSPR_PREDICATE = 19,
     WINED3DSPR_IMMCONST,
     WINED3DSPR_CONSTBUFFER,
+    WINED3DSPR_NULL,
 } WINED3DSHADER_PARAM_REGISTER_TYPE;
 
 enum wined3d_immconst_type
 {
-    WINED3D_IMMCONST_FLOAT,
-    WINED3D_IMMCONST_FLOAT4,
+    WINED3D_IMMCONST_SCALAR,
+    WINED3D_IMMCONST_VEC4,
 };
 
 #define WINED3DSP_NOSWIZZLE (0 | (1 << 2) | (2 << 4) | (3 << 6))
@@ -404,6 +405,7 @@ enum WINED3D_SHADER_INSTRUCTION_HANDLER
 {
     WINED3DSIH_ABS,
     WINED3DSIH_ADD,
+    WINED3DSIH_AND,
     WINED3DSIH_BEM,
     WINED3DSIH_BREAK,
     WINED3DSIH_BREAKC,
@@ -436,6 +438,7 @@ enum WINED3D_SHADER_INSTRUCTION_HANDLER
     WINED3DSIH_IF,
     WINED3DSIH_IFC,
     WINED3DSIH_IGE,
+    WINED3DSIH_IMUL,
     WINED3DSIH_LABEL,
     WINED3DSIH_LIT,
     WINED3DSIH_LOG,
@@ -453,6 +456,7 @@ enum WINED3D_SHADER_INSTRUCTION_HANDLER
     WINED3DSIH_MIN,
     WINED3DSIH_MOV,
     WINED3DSIH_MOVA,
+    WINED3DSIH_MOVC,
     WINED3DSIH_MUL,
     WINED3DSIH_NOP,
     WINED3DSIH_NRM,
@@ -677,13 +681,18 @@ enum fogmode {
 /* Stateblock dependent parameters which have to be hardcoded
  * into the shader code
  */
+
+#define WINED3D_PSARGS_PROJECTED (1 << 3)
+#define WINED3D_PSARGS_TEXTRANSFORM_SHIFT 4
+#define WINED3D_PSARGS_TEXTRANSFORM_MASK 0xf
+
 struct ps_compile_args {
     struct color_fixup_desc     color_fixup[MAX_FRAGMENT_SAMPLERS];
     enum vertexprocessing_mode  vp_mode;
     enum fogmode                fog;
-    /* Projected textures(ps 1.0-1.3) */
+    WORD                        tex_transform; /* ps 1.0-1.3, 4 textures */
     /* Texture types(2D, Cube, 3D) in ps 1.x */
-    BOOL                        srgb_correction;
+    WORD                        srgb_correction;
     WORD                        np2_fixup;
     /* Bitmap for NP2 texcoord fixups (16 samplers max currently).
        D3D9 has a limit of 16 samplers and the fixup is superfluous
@@ -728,8 +737,8 @@ extern const shader_backend_t none_shader_backend DECLSPEC_HIDDEN;
 
 /* X11 locking */
 
-extern void (* CDECL wine_tsx11_lock_ptr)(void) DECLSPEC_HIDDEN;
-extern void (* CDECL wine_tsx11_unlock_ptr)(void) DECLSPEC_HIDDEN;
+extern void (CDECL *wine_tsx11_lock_ptr)(void) DECLSPEC_HIDDEN;
+extern void (CDECL *wine_tsx11_unlock_ptr)(void) DECLSPEC_HIDDEN;
 
 /* As GLX relies on X, this is needed */
 extern int num_lock DECLSPEC_HIDDEN;
@@ -806,7 +815,7 @@ do {
 /* Trace vector and strided data information */
 #define TRACE_STRIDED(si, name) do { if (si->use_map & (1 << name)) \
         TRACE( #name "=(data:%p, stride:%d, format:%#x, vbo %d, stream %u)\n", \
-        si->elements[name].data, si->elements[name].stride, si->elements[name].format_desc->format, \
+        si->elements[name].data, si->elements[name].stride, si->elements[name].format->id, \
         si->elements[name].buffer_object, si->elements[name].stream_idx); } while(0)
 
 /* Advance declaration of structures to satisfy compiler */
@@ -819,40 +828,6 @@ typedef struct IWineD3DSwapChainImpl  IWineD3DSwapChainImpl;
 /* Global variables */
 extern const float identity[16] DECLSPEC_HIDDEN;
 
-/*****************************************************************************
- * Compilable extra diagnostics
- */
-
-/* TODO: Confirm each of these works when wined3d move completed */
-#if 0 /* NOTE: Must be 0 in cvs */
-  /* To avoid having to get gigabytes of trace, the following can be compiled in, and at the start
-     of each frame, a check is made for the existence of C:\D3DTRACE, and if it exists d3d trace
-     is enabled, and if it doesn't exist it is disabled. */
-# define FRAME_DEBUGGING
-  /*  Adding in the SINGLE_FRAME_DEBUGGING gives a trace of just what makes up a single frame, before
-      the file is deleted                                                                            */
-# if 1 /* NOTE: Must be 1 in cvs, as this is mostly more useful than a trace from program start */
-#  define SINGLE_FRAME_DEBUGGING
-# endif
-  /* The following, when enabled, lets you see the makeup of the frame, by drawprimitive calls.
-     It can only be enabled when FRAME_DEBUGGING is also enabled
-     The contents of the back buffer are written into /tmp/backbuffer_* after each primitive
-     array is drawn.                                                                            */
-# if 0 /* NOTE: Must be 0 in cvs, as this give a lot of ppm files when compiled in */
-#  define SHOW_FRAME_MAKEUP 1
-# endif
-  /* The following, when enabled, lets you see the makeup of the all the textures used during each
-     of the drawprimitive calls. It can only be enabled when SHOW_FRAME_MAKEUP is also enabled.
-     The contents of the textures assigned to each stage are written into
-     /tmp/texture_*_<Stage>.ppm after each primitive array is drawn.                            */
-# if 0 /* NOTE: Must be 0 in cvs, as this give a lot of ppm files when compiled in */
-#  define SHOW_TEXTURE_MAKEUP 0
-# endif
-extern BOOL isOn;
-extern BOOL isDumpingFrames;
-extern LONG primCounter;
-#endif
-
 enum wined3d_ffp_idx
 {
     WINED3D_FFP_POSITION = 0,
@@ -896,7 +871,7 @@ enum wined3d_ffp_emit_idx
 
 struct wined3d_stream_info_element
 {
-    const struct wined3d_format_desc *format_desc;
+    const struct wined3d_format *format;
     GLsizei stride;
     const BYTE *data;
     UINT stream_idx;
@@ -1094,6 +1069,7 @@ struct wined3d_context
     GLuint                  fbo_draw_binding;
     BOOL rebind_fbo;
     IWineD3DSurfaceImpl **blit_targets;
+    GLenum *draw_buffers;
 
     /* Queries */
     GLuint *free_occlusion_queries;
@@ -1166,7 +1142,8 @@ enum blit_operation
     BLIT_OP_COLOR_FILL
 };
 
-/* Shaders for color conversions in blits */
+/* Shaders for color conversions in blits. Do not do blit operations while
+ * already under the GL lock. */
 struct blit_shader
 {
     HRESULT (*alloc_private)(IWineD3DDevice *iface);
@@ -1174,15 +1151,21 @@ struct blit_shader
     HRESULT (*set_shader)(IWineD3DDevice *iface, IWineD3DSurfaceImpl *surface);
     void (*unset_shader)(IWineD3DDevice *iface);
     BOOL (*blit_supported)(const struct wined3d_gl_info *gl_info, enum blit_operation blit_op,
-                           const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool, const struct wined3d_format_desc *src_format_desc,
-                           const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool, const struct wined3d_format_desc *dst_format_desc);
-    HRESULT (*color_fill)(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *dst_surface, const RECT *dst_rect, DWORD fill_color);
+            const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool, const struct wined3d_format *src_format,
+            const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool, const struct wined3d_format *dst_format);
+    HRESULT (*color_fill)(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *dst_surface,
+            const RECT *dst_rect, const WINED3DCOLORVALUE *color);
 };
 
 extern const struct blit_shader ffp_blit DECLSPEC_HIDDEN;
 extern const struct blit_shader arbfp_blit DECLSPEC_HIDDEN;
 extern const struct blit_shader cpu_blit DECLSPEC_HIDDEN;
 
+const struct blit_shader *wined3d_select_blitter(const struct wined3d_gl_info *gl_info, enum blit_operation blit_op,
+        const RECT *src_rect, DWORD src_usage, WINED3DPOOL src_pool, const struct wined3d_format *src_format,
+        const RECT *dst_rect, DWORD dst_usage, WINED3DPOOL dst_pool, const struct wined3d_format *dst_format)
+        DECLSPEC_HIDDEN;
+
 /* Temporary blit_shader helper functions */
 HRESULT arbfp_blit_surface(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *src_surface, const RECT *src_rect,
                            IWineD3DSurfaceImpl *dst_surface, const RECT *dst_rect_in, enum blit_operation blit_op,
@@ -1195,22 +1178,24 @@ void context_alloc_occlusion_query(struct wined3d_context *context,
         struct wined3d_occlusion_query *query) DECLSPEC_HIDDEN;
 void context_apply_blit_state(struct wined3d_context *context, IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN;
 void context_apply_clear_state(struct wined3d_context *context, IWineD3DDeviceImpl *device,
-        IWineD3DSurfaceImpl *render_target, IWineD3DSurfaceImpl *depth_stencil) DECLSPEC_HIDDEN;
+        UINT rt_count, IWineD3DSurfaceImpl **rts, IWineD3DSurfaceImpl *depth_stencil) DECLSPEC_HIDDEN;
 void context_apply_draw_state(struct wined3d_context *context, IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN;
 void context_apply_fbo_state_blit(struct wined3d_context *context, GLenum target,
-        IWineD3DSurfaceImpl *render_target, IWineD3DSurfaceImpl *depth_stencil) DECLSPEC_HIDDEN;
+        IWineD3DSurfaceImpl *render_target, IWineD3DSurfaceImpl *depth_stencil, DWORD location) DECLSPEC_HIDDEN;
 void context_attach_depth_stencil_fbo(struct wined3d_context *context,
         GLenum fbo_target, IWineD3DSurfaceImpl *depth_stencil, BOOL use_render_buffer) DECLSPEC_HIDDEN;
 void context_bind_fbo(struct wined3d_context *context, GLenum target, GLuint *fbo) DECLSPEC_HIDDEN;
 struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3DSurfaceImpl *target,
-        const struct wined3d_format_desc *ds_format_desc) DECLSPEC_HIDDEN;
+        const struct wined3d_format *ds_format) DECLSPEC_HIDDEN;
 void context_destroy(IWineD3DDeviceImpl *This, struct wined3d_context *context) DECLSPEC_HIDDEN;
 void context_free_event_query(struct wined3d_event_query *query) DECLSPEC_HIDDEN;
 void context_free_occlusion_query(struct wined3d_occlusion_query *query) DECLSPEC_HIDDEN;
 struct wined3d_context *context_get_current(void) DECLSPEC_HIDDEN;
 DWORD context_get_tls_idx(void) DECLSPEC_HIDDEN;
 void context_release(struct wined3d_context *context) DECLSPEC_HIDDEN;
-void context_resource_released(IWineD3DDevice *iface,
+void context_resource_released(IWineD3DDeviceImpl *device,
+        IWineD3DResource *resource, WINED3DRESOURCETYPE type) DECLSPEC_HIDDEN;
+void context_resource_unloaded(IWineD3DDeviceImpl *device,
         IWineD3DResource *resource, WINED3DRESOURCETYPE type) DECLSPEC_HIDDEN;
 BOOL context_set_current(struct wined3d_context *ctx) DECLSPEC_HIDDEN;
 void context_set_draw_buffer(struct wined3d_context *context, GLenum buffer) DECLSPEC_HIDDEN;
@@ -1258,6 +1243,34 @@ typedef struct WineD3D_PixelFormat
     int numSamples;
 } WineD3D_PixelFormat;
 
+/* The driver names reflect the lowest GPU supported
+ * by a certain driver, so DRIVER_ATI_R300 supports
+ * R3xx, R4xx and R5xx GPUs. */
+enum wined3d_display_driver
+{
+    DRIVER_ATI_RAGE_128PRO,
+    DRIVER_ATI_R100,
+    DRIVER_ATI_R300,
+    DRIVER_ATI_R600,
+    DRIVER_INTEL_GMA800,
+    DRIVER_INTEL_GMA900,
+    DRIVER_INTEL_GMA950,
+    DRIVER_INTEL_GMA3000,
+    DRIVER_NVIDIA_TNT,
+    DRIVER_NVIDIA_GEFORCE2MX,
+    DRIVER_NVIDIA_GEFORCEFX,
+    DRIVER_NVIDIA_GEFORCE6,
+    DRIVER_UNKNOWN
+};
+
+enum wined3d_driver_model
+{
+    DRIVER_MODEL_WIN9X,
+    DRIVER_MODEL_NT40,
+    DRIVER_MODEL_NT5X,
+    DRIVER_MODEL_NT6X
+};
+
 enum wined3d_gl_vendor
 {
     GL_VENDOR_UNKNOWN,
@@ -1338,15 +1351,24 @@ enum wined3d_pci_device
     CARD_NVIDIA_GEFORCE_8600GT      = 0x0402,
     CARD_NVIDIA_GEFORCE_8600MGT     = 0x0407,
     CARD_NVIDIA_GEFORCE_8800GTS     = 0x0193,
+    CARD_NVIDIA_GEFORCE_8800GTX     = 0x0191,
     CARD_NVIDIA_GEFORCE_9200        = 0x086d,
     CARD_NVIDIA_GEFORCE_9400GT      = 0x042c,
     CARD_NVIDIA_GEFORCE_9500GT      = 0x0640,
     CARD_NVIDIA_GEFORCE_9600GT      = 0x0622,
     CARD_NVIDIA_GEFORCE_9800GT      = 0x0614,
+    CARD_NVIDIA_GEFORCE_210         = 0x0a23,
+    CARD_NVIDIA_GEFORCE_GT220       = 0x0a20,
+    CARD_NVIDIA_GEFORCE_GT240       = 0x0ca3,
     CARD_NVIDIA_GEFORCE_GTX260      = 0x05e2,
     CARD_NVIDIA_GEFORCE_GTX275      = 0x05e6,
     CARD_NVIDIA_GEFORCE_GTX280      = 0x05e1,
-    CARD_NVIDIA_GEFORCE_GT240       = 0x0ca3,
+    CARD_NVIDIA_GEFORCE_GT325M      = 0x0a35,
+    CARD_NVIDIA_GEFORCE_GTS350M     = 0x0cb0,
+    CARD_NVIDIA_GEFORCE_GTX460      = 0x0e22,
+    CARD_NVIDIA_GEFORCE_GTX465      = 0x06c4,
+    CARD_NVIDIA_GEFORCE_GTX470      = 0x06cd,
+    CARD_NVIDIA_GEFORCE_GTX480      = 0x06c0,
 
     CARD_INTEL_845G                 = 0x2562,
     CARD_INTEL_I830G                = 0x3577,
@@ -1355,7 +1377,7 @@ enum wined3d_pci_device
     CARD_INTEL_I915G                = 0x2582,
     CARD_INTEL_I915GM               = 0x2592,
     CARD_INTEL_I945GM               = 0x27a2, /* Same as GMA 950? */
-    CARD_INTEL_X3100                = 0x2a02, /* Found in Macs. Same as GMA 965? */
+    CARD_INTEL_X3100                = 0x2a02, /* Found in Macs. Same as GM965/GL960 */
 };
 
 struct wined3d_fbo_ops
@@ -1420,7 +1442,6 @@ struct wined3d_gl_limits
 struct wined3d_gl_info
 {
     DWORD glsl_version;
-    UINT vidmem;
     struct wined3d_gl_limits limits;
     DWORD reserved_glsl_constants;
     DWORD quirks;
@@ -1435,7 +1456,7 @@ struct wined3d_gl_info
     WGL_EXT_FUNCS_GEN
 #undef USE_GL_FUNC
 
-    struct wined3d_format_desc *gl_formats;
+    struct wined3d_format *formats;
 };
 
 struct wined3d_driver_info
@@ -1444,6 +1465,7 @@ struct wined3d_driver_info
     enum wined3d_pci_device device;
     const char *name;
     const char *description;
+    unsigned int vidmem;
     DWORD version_high;
     DWORD version_low;
 };
@@ -1559,14 +1581,14 @@ typedef struct IWineD3DImpl
     LONG                    ref;     /* Note: Ref counting not required */
 
     /* WineD3D Information */
-    IUnknown               *parent;
+    void *parent;
     UINT                    dxVersion;
 
     UINT adapter_count;
     struct wined3d_adapter adapters[1];
 } IWineD3DImpl;
 
-HRESULT wined3d_init(IWineD3DImpl *wined3d, UINT version, IUnknown *parent) DECLSPEC_HIDDEN;
+HRESULT wined3d_init(IWineD3DImpl *wined3d, UINT version, void *parent) DECLSPEC_HIDDEN;
 BOOL wined3d_register_window(HWND window, struct IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN;
 void wined3d_unregister_window(HWND window) DECLSPEC_HIDDEN;
 
@@ -1585,7 +1607,6 @@ struct IWineD3DDeviceImpl
     LONG                    ref;     /* Note: Ref counting not required */
 
     /* WineD3D Information  */
-    IUnknown               *parent;
     IWineD3DDeviceParent   *device_parent;
     IWineD3D *wined3d;
     struct wined3d_adapter *adapter;
@@ -1664,7 +1685,6 @@ struct IWineD3DDeviceImpl
     UINT                    currentPalette;
 
     /* For rendering to a texture using glCopyTexImage */
-    GLenum                  *draw_buffers;
     GLuint                  depth_blt_texture;
     GLuint                  depth_blt_rb;
     UINT                    depth_blt_rb_w;
@@ -1687,7 +1707,7 @@ struct IWineD3DDeviceImpl
 
     /* DirectDraw stuff */
     DWORD ddraw_width, ddraw_height;
-    WINED3DFORMAT ddraw_format;
+    enum wined3d_format_id ddraw_format;
 
     /* Final position fixup constant */
     float                       posFixup[4];
@@ -1713,12 +1733,15 @@ struct IWineD3DDeviceImpl
     struct WineD3DRectPatch *currentPatch;
 };
 
+HRESULT device_clear_render_targets(IWineD3DDeviceImpl *device, UINT rt_count, IWineD3DSurfaceImpl **rts,
+        UINT rect_count, const RECT *rects, const RECT *draw_rect, DWORD flags,
+        const WINED3DCOLORVALUE *color, float depth, DWORD stencil) DECLSPEC_HIDDEN;
 BOOL device_context_add(IWineD3DDeviceImpl *device, struct wined3d_context *context) DECLSPEC_HIDDEN;
 void device_context_remove(IWineD3DDeviceImpl *device, struct wined3d_context *context) DECLSPEC_HIDDEN;
 void device_get_draw_rect(IWineD3DDeviceImpl *device, RECT *rect) DECLSPEC_HIDDEN;
 HRESULT device_init(IWineD3DDeviceImpl *device, IWineD3DImpl *wined3d,
         UINT adapter_idx, WINED3DDEVTYPE device_type, HWND focus_window, DWORD flags,
-        IUnknown *parent, IWineD3DDeviceParent *device_parent) DECLSPEC_HIDDEN;
+        IWineD3DDeviceParent *device_parent) DECLSPEC_HIDDEN;
 void device_preload_textures(IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN;
 LRESULT device_process_message(IWineD3DDeviceImpl *device, HWND window,
         UINT message, WPARAM wparam, LPARAM lparam, WNDPROC proc) DECLSPEC_HIDDEN;
@@ -1729,8 +1752,6 @@ void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
 void device_switch_onscreen_ds(IWineD3DDeviceImpl *device, struct wined3d_context *context,
         IWineD3DSurfaceImpl *depth_stencil) DECLSPEC_HIDDEN;
 void device_update_stream_info(IWineD3DDeviceImpl *device, const struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN;
-HRESULT IWineD3DDeviceImpl_ClearSurface(IWineD3DDeviceImpl *This, IWineD3DSurfaceImpl *target, DWORD Count,
-        const WINED3DRECT *pRects, DWORD Flags, WINED3DCOLOR Color, float Z, DWORD Stencil) DECLSPEC_HIDDEN;
 void IWineD3DDeviceImpl_FindTexUnitMap(IWineD3DDeviceImpl *This) DECLSPEC_HIDDEN;
 void IWineD3DDeviceImpl_MarkStateDirty(IWineD3DDeviceImpl *This, DWORD state) DECLSPEC_HIDDEN;
 
@@ -1767,18 +1788,19 @@ typedef struct IWineD3DResourceClass
     LONG                    ref;     /* Note: Ref counting not required */
 
     /* WineD3DResource Information */
-    IUnknown               *parent;
     WINED3DRESOURCETYPE     resourceType;
     IWineD3DDeviceImpl *device;
     WINED3DPOOL             pool;
     UINT                    size;
     DWORD                   usage;
-    const struct wined3d_format_desc *format_desc;
+    const struct wined3d_format *format;
     DWORD                   priority;
     BYTE                   *allocatedMemory; /* Pointer to the real data location */
     BYTE                   *heapMemory; /* Pointer to the HeapAlloced block of memory */
     struct list             privateData;
     struct list             resource_list_entry;
+
+    void *parent;
     const struct wined3d_parent_ops *parent_ops;
 } IWineD3DResourceClass;
 
@@ -1791,17 +1813,17 @@ typedef struct IWineD3DResourceImpl
 
 void resource_cleanup(IWineD3DResource *iface) DECLSPEC_HIDDEN;
 HRESULT resource_free_private_data(IWineD3DResource *iface, REFGUID guid) DECLSPEC_HIDDEN;
-HRESULT resource_get_parent(IWineD3DResource *iface, IUnknown **parent) DECLSPEC_HIDDEN;
 DWORD resource_get_priority(IWineD3DResource *iface) DECLSPEC_HIDDEN;
 HRESULT resource_get_private_data(IWineD3DResource *iface, REFGUID guid,
         void *data, DWORD *data_size) DECLSPEC_HIDDEN;
 HRESULT resource_init(IWineD3DResource *iface, WINED3DRESOURCETYPE resource_type,
-        IWineD3DDeviceImpl *device, UINT size, DWORD usage, const struct wined3d_format_desc *format_desc,
-        WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        IWineD3DDeviceImpl *device, UINT size, DWORD usage, const struct wined3d_format *format,
+        WINED3DPOOL pool, void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 WINED3DRESOURCETYPE resource_get_type(IWineD3DResource *iface) DECLSPEC_HIDDEN;
 DWORD resource_set_priority(IWineD3DResource *iface, DWORD new_priority) DECLSPEC_HIDDEN;
 HRESULT resource_set_private_data(IWineD3DResource *iface, REFGUID guid,
         const void *data, DWORD data_size, DWORD flags) DECLSPEC_HIDDEN;
+void resource_unload(IWineD3DResourceImpl *resource) DECLSPEC_HIDDEN;
 
 /* Tests show that the start address of resources is 32 byte aligned */
 #define RESOURCE_ALIGNMENT 16
@@ -1858,15 +1880,10 @@ typedef struct IWineD3DBaseTextureClass
     BOOL                    pow2Matrix_identity;
     const struct min_lookup *minMipLookup;
     const GLenum            *magLookup;
+    GLenum target;
     void                    (*internal_preload)(IWineD3DBaseTexture *iface, enum WINED3DSRGB srgb);
 } IWineD3DBaseTextureClass;
 
-void surface_internal_preload(IWineD3DSurfaceImpl *surface, enum WINED3DSRGB srgb) DECLSPEC_HIDDEN;
-BOOL surface_init_sysmem(IWineD3DSurfaceImpl *surface) DECLSPEC_HIDDEN;
-BOOL surface_is_offscreen(IWineD3DSurfaceImpl *iface) DECLSPEC_HIDDEN;
-void surface_prepare_texture(IWineD3DSurfaceImpl *surface,
-        const struct wined3d_gl_info *gl_info, BOOL srgb) DECLSPEC_HIDDEN;
-
 typedef struct IWineD3DBaseTextureImpl
 {
     /* IUnknown & WineD3DResource Information     */
@@ -1891,7 +1908,7 @@ IWineD3DResourceImpl *basetexture_get_sub_resource(IWineD3DBaseTextureImpl *text
         UINT layer, UINT level) DECLSPEC_HIDDEN;
 HRESULT basetexture_init(IWineD3DBaseTextureImpl *texture, UINT layer_count, UINT level_count,
         WINED3DRESOURCETYPE resource_type, IWineD3DDeviceImpl *device, UINT size, DWORD usage,
-        const struct wined3d_format_desc *format_desc, WINED3DPOOL pool, IUnknown *parent,
+        const struct wined3d_format *format, WINED3DPOOL pool, void *parent,
         const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 HRESULT basetexture_set_autogen_filter_type(IWineD3DBaseTexture *iface,
         WINED3DTEXTUREFILTERTYPE filter_type) DECLSPEC_HIDDEN;
@@ -1910,14 +1927,13 @@ typedef struct IWineD3DTextureImpl
     IWineD3DBaseTextureClass  baseTexture;
 
     /* IWineD3DTexture */
-    UINT                      target;
     BOOL                      cond_np2;
 
 } IWineD3DTextureImpl;
 
 HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT levels,
-        IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        IWineD3DDeviceImpl *device, DWORD usage, enum wined3d_format_id format_id, WINED3DPOOL pool,
+        void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * IWineD3DCubeTexture implementation structure (extends IWineD3DBaseTextureImpl)
@@ -1931,8 +1947,8 @@ typedef struct IWineD3DCubeTextureImpl
 } IWineD3DCubeTextureImpl;
 
 HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UINT levels,
-        IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        IWineD3DDeviceImpl *device, DWORD usage, enum wined3d_format_id format_id, WINED3DPOOL pool,
+        void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 
 typedef struct _WINED3DVOLUMET_DESC
 {
@@ -1952,7 +1968,7 @@ typedef struct IWineD3DVolumeImpl
 
     /* WineD3DVolume Information */
     WINED3DVOLUMET_DESC      currentDesc;
-    IWineD3DBase            *container;
+    struct IWineD3DVolumeTextureImpl *container;
     BOOL                    lockable;
     BOOL                    locked;
     WINED3DBOX              lockedBox;
@@ -1962,8 +1978,9 @@ typedef struct IWineD3DVolumeImpl
 
 void volume_add_dirty_box(IWineD3DVolume *iface, const WINED3DBOX *dirty_box) DECLSPEC_HIDDEN;
 HRESULT volume_init(IWineD3DVolumeImpl *volume, IWineD3DDeviceImpl *device, UINT width,
-        UINT height, UINT depth, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        UINT height, UINT depth, DWORD usage, enum wined3d_format_id format_id, WINED3DPOOL pool,
+        void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+void volume_set_container(IWineD3DVolumeImpl *volume, struct IWineD3DVolumeTextureImpl *container) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * IWineD3DVolumeTexture implementation structure (extends IWineD3DBaseTextureImpl)
@@ -1977,8 +1994,8 @@ typedef struct IWineD3DVolumeTextureImpl
 } IWineD3DVolumeTextureImpl;
 
 HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT height,
-        UINT depth, UINT levels, IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format,
-        WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        UINT depth, UINT levels, IWineD3DDeviceImpl *device, DWORD usage, enum wined3d_format_id format_id,
+        WINED3DPOOL pool, void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 
 typedef struct _WINED3DSURFACET_DESC
 {
@@ -2011,6 +2028,7 @@ struct fbo_entry
     struct list entry;
     IWineD3DSurfaceImpl **render_targets;
     IWineD3DSurfaceImpl *depth_stencil;
+    DWORD location;
     BOOL attached;
     GLuint id;
 };
@@ -2023,10 +2041,26 @@ typedef struct IWineD3DClipperImpl
     const IWineD3DClipperVtbl *lpVtbl;
     LONG ref;
 
-    IUnknown *Parent;
     HWND hWnd;
 } IWineD3DClipperImpl;
 
+enum wined3d_container_type
+{
+    WINED3D_CONTAINER_NONE = 0,
+    WINED3D_CONTAINER_SWAPCHAIN,
+    WINED3D_CONTAINER_TEXTURE,
+};
+
+struct wined3d_subresource_container
+{
+    enum wined3d_container_type type;
+    union
+    {
+        struct IWineD3DBase *base;
+        struct IWineD3DSwapChainImpl *swapchain;
+        struct IWineD3DBaseTextureImpl *texture;
+    } u;
+};
 
 /*****************************************************************************
  * IWineD3DSurface implementation structure
@@ -2038,7 +2072,7 @@ struct IWineD3DSurfaceImpl
     IWineD3DResourceClass     resource;
 
     /* IWineD3DSurface fields */
-    IWineD3DBase              *container;
+    struct wined3d_subresource_container container;
     WINED3DSURFACET_DESC      currentDesc;
     IWineD3DPaletteImpl       *palette; /* D3D7 style palette handling */
     PALETTEENTRY              *palette9; /* D3D8/9 style palette handling */
@@ -2095,20 +2129,37 @@ struct IWineD3DSurfaceImpl
 extern const IWineD3DSurfaceVtbl IWineD3DSurface_Vtbl DECLSPEC_HIDDEN;
 extern const IWineD3DSurfaceVtbl IWineGDISurface_Vtbl DECLSPEC_HIDDEN;
 
-UINT surface_calculate_size(const struct wined3d_format_desc *format_desc,
-        UINT alignment, UINT width, UINT height) DECLSPEC_HIDDEN;
+void surface_add_dirty_rect(IWineD3DSurfaceImpl *surface, const RECT *dirty_rect) DECLSPEC_HIDDEN;
+HRESULT surface_color_fill(IWineD3DSurfaceImpl *s, const RECT *rect, const WINED3DCOLORVALUE *color) DECLSPEC_HIDDEN;
 void surface_gdi_cleanup(IWineD3DSurfaceImpl *This) DECLSPEC_HIDDEN;
+GLenum surface_get_gl_buffer(IWineD3DSurfaceImpl *surface) DECLSPEC_HIDDEN;
 HRESULT surface_init(IWineD3DSurfaceImpl *surface, WINED3DSURFTYPE surface_type, UINT alignment,
         UINT width, UINT height, UINT level, BOOL lockable, BOOL discard, WINED3DMULTISAMPLE_TYPE multisample_type,
-        UINT multisample_quality, IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format,
-        WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        UINT multisample_quality, IWineD3DDeviceImpl *device, DWORD usage, enum wined3d_format_id format_id,
+        WINED3DPOOL pool, void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+BOOL surface_init_sysmem(IWineD3DSurfaceImpl *surface) DECLSPEC_HIDDEN;
+void surface_internal_preload(IWineD3DSurfaceImpl *surface, enum WINED3DSRGB srgb) DECLSPEC_HIDDEN;
+BOOL surface_is_offscreen(IWineD3DSurfaceImpl *iface) DECLSPEC_HIDDEN;
+void surface_load_ds_location(IWineD3DSurfaceImpl *surface,
+        struct wined3d_context *context, DWORD location) DECLSPEC_HIDDEN;
+HRESULT surface_load_location(IWineD3DSurfaceImpl *surface, DWORD flag, const RECT *rect) DECLSPEC_HIDDEN;
+void surface_modify_ds_location(IWineD3DSurfaceImpl *surface, DWORD location, UINT w, UINT h) DECLSPEC_HIDDEN;
+void surface_modify_location(IWineD3DSurfaceImpl *surface, DWORD flag, BOOL persistent) DECLSPEC_HIDDEN;
+void surface_prepare_texture(IWineD3DSurfaceImpl *surface,
+        const struct wined3d_gl_info *gl_info, BOOL srgb) DECLSPEC_HIDDEN;
+void surface_set_compatible_renderbuffer(IWineD3DSurfaceImpl *surface,
+        unsigned int width, unsigned int height) DECLSPEC_HIDDEN;
+void surface_set_container(IWineD3DSurfaceImpl *surface,
+        enum wined3d_container_type type, IWineD3DBase *container) DECLSPEC_HIDDEN;
+void surface_set_texture_name(IWineD3DSurfaceImpl *surface, GLuint name, BOOL srgb_name) DECLSPEC_HIDDEN;
+void surface_set_texture_target(IWineD3DSurfaceImpl *surface, GLenum target) DECLSPEC_HIDDEN;
 void surface_translate_frontbuffer_coords(IWineD3DSurfaceImpl *surface, HWND window, RECT *rect) DECLSPEC_HIDDEN;
 
 /* Predeclare the shared Surface functions */
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_QueryInterface(IWineD3DSurface *iface,
         REFIID riid, LPVOID *ppobj) DECLSPEC_HIDDEN;
 ULONG WINAPI IWineD3DBaseSurfaceImpl_AddRef(IWineD3DSurface *iface) DECLSPEC_HIDDEN;
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetParent(IWineD3DSurface *iface, IUnknown **pParent) DECLSPEC_HIDDEN;
+void * WINAPI IWineD3DBaseSurfaceImpl_GetParent(IWineD3DSurface *iface) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetPrivateData(IWineD3DSurface *iface,
         REFGUID refguid, const void *pData, DWORD SizeOfData, DWORD Flags) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetPrivateData(IWineD3DSurface *iface,
@@ -2117,9 +2168,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_FreePrivateData(IWineD3DSurface *iface, R
 DWORD WINAPI IWineD3DBaseSurfaceImpl_SetPriority(IWineD3DSurface *iface, DWORD PriorityNew) DECLSPEC_HIDDEN;
 DWORD WINAPI IWineD3DBaseSurfaceImpl_GetPriority(IWineD3DSurface *iface) DECLSPEC_HIDDEN;
 WINED3DRESOURCETYPE WINAPI IWineD3DBaseSurfaceImpl_GetType(IWineD3DSurface *iface) DECLSPEC_HIDDEN;
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetContainer(IWineD3DSurface* iface,
-        REFIID riid, void **ppContainer) DECLSPEC_HIDDEN;
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetDesc(IWineD3DSurface *iface, WINED3DSURFACE_DESC *pDesc) DECLSPEC_HIDDEN;
+void WINAPI IWineD3DBaseSurfaceImpl_GetDesc(IWineD3DSurface *iface, WINED3DSURFACE_DESC *desc) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetBltStatus(IWineD3DSurface *iface, DWORD Flags) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetFlipStatus(IWineD3DSurface *iface, DWORD Flags) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_IsLost(IWineD3DSurface *iface) DECLSPEC_HIDDEN;
@@ -2128,9 +2177,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetPalette(IWineD3DSurface *iface, IWineD
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetPalette(IWineD3DSurface *iface, IWineD3DPalette *Pal) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetColorKey(IWineD3DSurface *iface,
         DWORD Flags, const WINEDDCOLORKEY *CKey) DECLSPEC_HIDDEN;
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetContainer(IWineD3DSurface *iface, IWineD3DBase *container) DECLSPEC_HIDDEN;
 DWORD WINAPI IWineD3DBaseSurfaceImpl_GetPitch(IWineD3DSurface *iface) DECLSPEC_HIDDEN;
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_RealizePalette(IWineD3DSurface *iface) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetOverlayPosition(IWineD3DSurface *iface, LONG X, LONG Y) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetOverlayPosition(IWineD3DSurface *iface, LONG *X, LONG *Y) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_UpdateOverlayZOrder(IWineD3DSurface *iface,
@@ -2139,15 +2186,15 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_UpdateOverlay(IWineD3DSurface *iface, con
         IWineD3DSurface *DstSurface, const RECT *DstRect, DWORD Flags, const WINEDDOVERLAYFX *FX) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetClipper(IWineD3DSurface *iface, IWineD3DClipper *clipper) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetClipper(IWineD3DSurface *iface, IWineD3DClipper **clipper) DECLSPEC_HIDDEN;
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetFormat(IWineD3DSurface *iface, WINED3DFORMAT format) DECLSPEC_HIDDEN;
+HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetFormat(IWineD3DSurface *iface,
+        enum wined3d_format_id format_id) DECLSPEC_HIDDEN;
 HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) DECLSPEC_HIDDEN;
-HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *DestRect, IWineD3DSurface *SrcSurface,
-        const RECT *SrcRect, DWORD Flags, const WINEDDBLTFX *DDBltFx, WINED3DTEXTUREFILTERTYPE Filter) DECLSPEC_HIDDEN;
+HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *dst_rect, IWineD3DSurface *src_surface,
+        const RECT *src_rect, DWORD flags, const WINEDDBLTFX *fx, WINED3DTEXTUREFILTERTYPE filter) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dstx, DWORD dsty,
         IWineD3DSurface *Source, const RECT *rsrc, DWORD trans) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSurfaceImpl_LockRect(IWineD3DSurface *iface, WINED3DLOCKED_RECT *pLockedRect,
         const RECT *pRect, DWORD Flags) DECLSPEC_HIDDEN;
-void WINAPI IWineD3DBaseSurfaceImpl_BindTexture(IWineD3DSurface *iface, BOOL srgb) DECLSPEC_HIDDEN;
 const void *WINAPI IWineD3DBaseSurfaceImpl_GetData(IWineD3DSurface *iface) DECLSPEC_HIDDEN;
 
 void get_drawable_size_swapchain(struct wined3d_context *context, UINT *width, UINT *height) DECLSPEC_HIDDEN;
@@ -2182,7 +2229,6 @@ void flip_surface(IWineD3DSurfaceImpl *front, IWineD3DSurfaceImpl *back) DECLSPE
 #define SFLAG_DS_ONSCREEN   0x00200000 /* Is a depth stencil, last modified onscreen */
 #define SFLAG_DS_OFFSCREEN  0x00400000 /* Is a depth stencil, last modified offscreen */
 #define SFLAG_INOVERLAYDRAW 0x00800000 /* Overlay drawing is in progress. Recursion prevention */
-#define SFLAG_SWAPCHAIN     0x01000000 /* The surface is part of a swapchain */
 
 /* In some conditions the surface memory must not be freed:
  * SFLAG_CONVERTED: Converting the data back would take too long
@@ -2219,9 +2265,9 @@ typedef enum {
     CONVERT_RGB32_888
 } CONVERT_TYPES;
 
-HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *This, BOOL need_alpha_ck, BOOL use_texturing,
-                        struct wined3d_format_desc *desc, CONVERT_TYPES *convert) DECLSPEC_HIDDEN;
-void d3dfmt_p8_init_palette(IWineD3DSurfaceImpl *This, BYTE table[256][4], BOOL colorkey) DECLSPEC_HIDDEN;
+HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *surface, BOOL need_alpha_ck, BOOL use_texturing,
+        struct wined3d_format *format, CONVERT_TYPES *convert) DECLSPEC_HIDDEN;
+void d3dfmt_p8_init_palette(IWineD3DSurfaceImpl *surface, BYTE table[256][4], BOOL colorkey) DECLSPEC_HIDDEN;
 
 BOOL palette9_changed(IWineD3DSurfaceImpl *This) DECLSPEC_HIDDEN;
 
@@ -2231,7 +2277,7 @@ BOOL palette9_changed(IWineD3DSurfaceImpl *This) DECLSPEC_HIDDEN;
 
 struct wined3d_vertex_declaration_element
 {
-    const struct wined3d_format_desc *format_desc;
+    const struct wined3d_format *format;
     BOOL ffp_valid;
     WORD input_slot;
     WORD offset;
@@ -2246,7 +2292,7 @@ typedef struct IWineD3DVertexDeclarationImpl {
     const IWineD3DVertexDeclarationVtbl *lpVtbl;
     LONG                    ref;
 
-    IUnknown                *parent;
+    void *parent;
     const struct wined3d_parent_ops *parent_ops;
     IWineD3DDeviceImpl *device;
 
@@ -2261,7 +2307,7 @@ typedef struct IWineD3DVertexDeclarationImpl {
 
 HRESULT vertexdeclaration_init(IWineD3DVertexDeclarationImpl *declaration, IWineD3DDeviceImpl *device,
         const WINED3DVERTEXELEMENT *elements, UINT element_count,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * IWineD3DStateBlock implementation structure
@@ -2301,87 +2347,70 @@ struct StageState {
     DWORD state;
 };
 
-struct IWineD3DStateBlockImpl
+struct wined3d_stream_state
 {
-    /* IUnknown fields */
-    const IWineD3DStateBlockVtbl *lpVtbl;
-    LONG                      ref;     /* Note: Ref counting not required */
-
-    /* IWineD3DStateBlock information */
-    IWineD3DDeviceImpl *device;
-    WINED3DSTATEBLOCKTYPE     blockType;
-
-    /* Array indicating whether things have been set or changed */
-    SAVEDSTATES               changed;
-
-    /* Vertex Shader Declaration */
-    IWineD3DVertexDeclaration *vertexDecl;
-
-    IWineD3DVertexShader      *vertexShader;
-
-    /* Vertex Shader Constants */
-    BOOL                       vertexShaderConstantB[MAX_CONST_B];
-    INT                        vertexShaderConstantI[MAX_CONST_I * 4];
-    float                     *vertexShaderConstantF;
+    struct wined3d_buffer *buffer;
+    UINT offset;
+    UINT stride;
+    UINT frequency;
+    UINT flags;
+};
 
-    /* primitive type */
+struct wined3d_state
+{
+    IWineD3DVertexDeclarationImpl *vertex_declaration;
+    struct wined3d_stream_state streams[MAX_STREAMS + 1 /* tesselated pseudo-stream */];
+    BOOL user_stream;
+    struct wined3d_buffer *index_buffer;
+    enum wined3d_format_id index_format;
+    INT base_vertex_index;
+    INT load_base_vertex_index; /* Non-indexed drawing needs 0 here, indexed needs base_vertex_index. */
     GLenum gl_primitive_type;
 
-    /* Stream Source */
-    BOOL                      streamIsUP;
-    UINT                      streamStride[MAX_STREAMS];
-    UINT                      streamOffset[MAX_STREAMS + 1 /* tesselated pseudo-stream */ ];
-    IWineD3DBuffer           *streamSource[MAX_STREAMS];
-    UINT                      streamFreq[MAX_STREAMS + 1];
-    UINT                      streamFlags[MAX_STREAMS + 1];     /*0 | WINED3DSTREAMSOURCE_INSTANCEDATA | WINED3DSTREAMSOURCE_INDEXEDDATA  */
+    struct IWineD3DVertexShaderImpl *vertex_shader;
+    BOOL vs_consts_b[MAX_CONST_B];
+    INT vs_consts_i[MAX_CONST_I * 4];
+    float *vs_consts_f;
+
+    struct IWineD3DPixelShaderImpl *pixel_shader;
+    BOOL ps_consts_b[MAX_CONST_B];
+    INT ps_consts_i[MAX_CONST_I * 4];
+    float *ps_consts_f;
 
-    /* Indices */
-    IWineD3DBuffer*           pIndexData;
-    WINED3DFORMAT             IndexFmt;
-    INT                       baseVertexIndex;
-    INT                       loadBaseVertexIndex; /* non-indexed drawing needs 0 here, indexed baseVertexIndex */
+    IWineD3DBaseTextureImpl *textures[MAX_COMBINED_SAMPLERS];
+    DWORD sampler_states[MAX_COMBINED_SAMPLERS][WINED3D_HIGHEST_SAMPLER_STATE + 1];
+    DWORD texture_states[MAX_TEXTURES][WINED3D_HIGHEST_TEXTURE_STATE + 1];
+    DWORD lowest_disabled_stage;
 
-    /* Transform */
-    WINED3DMATRIX             transforms[HIGHEST_TRANSFORMSTATE + 1];
+    WINED3DMATRIX transforms[HIGHEST_TRANSFORMSTATE + 1];
+    double clip_planes[MAX_CLIPPLANES][4];
+    WINED3DCLIPSTATUS clip_status;
+    WINED3DMATERIAL material;
+    WINED3DVIEWPORT viewport;
+    RECT scissor_rect;
 
     /* Light hashmap . Collisions are handled using standard wine double linked lists */
 #define LIGHTMAP_SIZE 43 /* Use of a prime number recommended. Set to 1 for a linked list! */
 #define LIGHTMAP_HASHFUNC(x) ((x) % LIGHTMAP_SIZE) /* Primitive and simple function */
-    struct list               lightMap[LIGHTMAP_SIZE]; /* Hash map containing the lights */
-    const struct wined3d_light_info *activeLights[MAX_ACTIVE_LIGHTS]; /* Map of opengl lights to d3d lights */
+    struct list light_map[LIGHTMAP_SIZE]; /* Hash map containing the lights */
+    const struct wined3d_light_info *lights[MAX_ACTIVE_LIGHTS]; /* Map of opengl lights to d3d lights */
 
-    /* Clipping */
-    double                    clipplane[MAX_CLIPPLANES][4];
-    WINED3DCLIPSTATUS         clip_status;
-
-    /* ViewPort */
-    WINED3DVIEWPORT           viewport;
-
-    /* Material */
-    WINED3DMATERIAL           material;
-
-    /* Pixel Shader */
-    IWineD3DPixelShader      *pixelShader;
-
-    /* Pixel Shader Constants */
-    BOOL                       pixelShaderConstantB[MAX_CONST_B];
-    INT                        pixelShaderConstantI[MAX_CONST_I * 4];
-    float                     *pixelShaderConstantF;
-
-    /* RenderState */
-    DWORD                     renderState[WINEHIGHEST_RENDER_STATE + 1];
+    DWORD render_states[WINEHIGHEST_RENDER_STATE + 1];
+};
 
-    /* Texture */
-    IWineD3DBaseTexture      *textures[MAX_COMBINED_SAMPLERS];
+struct IWineD3DStateBlockImpl
+{
+    /* IUnknown fields */
+    const IWineD3DStateBlockVtbl *lpVtbl;
+    LONG                      ref;     /* Note: Ref counting not required */
 
-    /* Texture State Stage */
-    DWORD                     textureState[MAX_TEXTURES][WINED3D_HIGHEST_TEXTURE_STATE + 1];
-    DWORD                     lowest_disabled_stage;
-    /* Sampler States */
-    DWORD                     samplerState[MAX_COMBINED_SAMPLERS][WINED3D_HIGHEST_SAMPLER_STATE + 1];
+    /* IWineD3DStateBlock information */
+    IWineD3DDeviceImpl *device;
+    WINED3DSTATEBLOCKTYPE     blockType;
 
-    /* Scissor test rectangle */
-    RECT                      scissorRect;
+    /* Array indicating whether things have been set or changed */
+    SAVEDSTATES               changed;
+    struct wined3d_state state;
 
     /* Contained state management */
     DWORD                     contained_render_states[WINEHIGHEST_RENDER_STATE + 1];
@@ -2409,6 +2438,7 @@ struct IWineD3DStateBlockImpl
 HRESULT stateblock_init(IWineD3DStateBlockImpl *stateblock,
         IWineD3DDeviceImpl *device, WINED3DSTATEBLOCKTYPE type) DECLSPEC_HIDDEN;
 void stateblock_init_contained_states(IWineD3DStateBlockImpl *object) DECLSPEC_HIDDEN;
+void stateblock_init_default_state(IWineD3DStateBlockImpl *stateblock) DECLSPEC_HIDDEN;
 
 static inline void stateblock_apply_state(DWORD state, IWineD3DStateBlockImpl *stateblock,
         struct wined3d_context *context)
@@ -2435,7 +2465,6 @@ typedef struct IWineD3DQueryImpl
     const IWineD3DQueryVtbl  *lpVtbl;
     LONG                      ref;     /* Note: Ref counting not required */
 
-    IUnknown                 *parent;
     IWineD3DDeviceImpl *device;
 
     /* IWineD3DQuery fields */
@@ -2445,8 +2474,7 @@ typedef struct IWineD3DQueryImpl
     void                     *extendedData;
 } IWineD3DQueryImpl;
 
-HRESULT query_init(IWineD3DQueryImpl *query, IWineD3DDeviceImpl *device,
-        WINED3DQUERYTYPE type, IUnknown *parent) DECLSPEC_HIDDEN;
+HRESULT query_init(IWineD3DQueryImpl *query, IWineD3DDeviceImpl *device, WINED3DQUERYTYPE type) DECLSPEC_HIDDEN;
 
 /* IWineD3DBuffer */
 
@@ -2508,8 +2536,8 @@ const BYTE *buffer_get_memory(IWineD3DBuffer *iface, const struct wined3d_gl_inf
         GLuint *buffer_object) DECLSPEC_HIDDEN;
 BYTE *buffer_get_sysmem(struct wined3d_buffer *This, const struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN;
 HRESULT buffer_init(struct wined3d_buffer *buffer, IWineD3DDeviceImpl *device,
-        UINT size, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool, GLenum bind_hint,
-        const char *data, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        UINT size, DWORD usage, enum wined3d_format_id format_id, WINED3DPOOL pool, GLenum bind_hint,
+        const char *data, void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 
 /* IWineD3DRendertargetView */
 struct wined3d_rendertarget_view
@@ -2518,11 +2546,11 @@ struct wined3d_rendertarget_view
     LONG refcount;
 
     IWineD3DResource *resource;
-    IUnknown *parent;
+    void *parent;
 };
 
 void wined3d_rendertarget_view_init(struct wined3d_rendertarget_view *view,
-        IWineD3DResource *resource, IUnknown *parent) DECLSPEC_HIDDEN;
+        IWineD3DResource *resource, void *parent) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * IWineD3DSwapChainImpl implementation structure (extends IUnknown)
@@ -2534,7 +2562,7 @@ struct IWineD3DSwapChainImpl
     const IWineD3DSwapChainVtbl *lpVtbl;
     LONG                      ref;     /* Note: Ref counting not required */
 
-    IUnknown                 *parent;
+    void *parent;
     IWineD3DDeviceImpl *device;
 
     /* IWineD3DSwapChain fields */
@@ -2542,10 +2570,10 @@ struct IWineD3DSwapChainImpl
     IWineD3DSurfaceImpl *front_buffer;
     WINED3DPRESENT_PARAMETERS presentParms;
     DWORD                     orig_width, orig_height;
-    WINED3DFORMAT             orig_fmt;
+    enum wined3d_format_id orig_fmt;
     WINED3DGAMMARAMP          orig_gamma;
     BOOL                      render_to_fbo;
-    const struct wined3d_format_desc *ds_format;
+    const struct wined3d_format *ds_format;
 
     LONG prev_time, frames;   /* Performance tracking */
     unsigned int vSyncCounter;
@@ -2557,16 +2585,16 @@ struct IWineD3DSwapChainImpl
     HWND device_window;
 };
 
-const IWineD3DSwapChainVtbl IWineGDISwapChain_Vtbl DECLSPEC_HIDDEN;
+extern const IWineD3DSwapChainVtbl IWineGDISwapChain_Vtbl DECLSPEC_HIDDEN;
 void x11_copy_to_screen(IWineD3DSwapChainImpl *This, const RECT *rc) DECLSPEC_HIDDEN;
 
 HRESULT WINAPI IWineD3DBaseSwapChainImpl_QueryInterface(IWineD3DSwapChain *iface,
         REFIID riid, LPVOID *ppobj) DECLSPEC_HIDDEN;
 ULONG WINAPI IWineD3DBaseSwapChainImpl_AddRef(IWineD3DSwapChain *iface) DECLSPEC_HIDDEN;
 ULONG WINAPI IWineD3DBaseSwapChainImpl_Release(IWineD3DSwapChain *iface) DECLSPEC_HIDDEN;
-HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetParent(IWineD3DSwapChain *iface, IUnknown **ppParent) DECLSPEC_HIDDEN;
+void * WINAPI IWineD3DBaseSwapChainImpl_GetParent(IWineD3DSwapChain *iface) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetFrontBufferData(IWineD3DSwapChain *iface,
-        IWineD3DSurface *pDestSurface) DECLSPEC_HIDDEN;
+        IWineD3DSurface *dst_surface) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetBackBuffer(IWineD3DSwapChain *iface, UINT iBackBuffer,
         WINED3DBACKBUFFER_TYPE Type, IWineD3DSurface **ppBackBuffer) DECLSPEC_HIDDEN;
 HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetRasterStatus(IWineD3DSwapChain *iface,
@@ -2584,7 +2612,7 @@ HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetGammaRamp(IWineD3DSwapChain *iface,
 
 struct wined3d_context *swapchain_create_context_for_thread(IWineD3DSwapChain *iface) DECLSPEC_HIDDEN;
 HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface_type,
-        IWineD3DDeviceImpl *device, WINED3DPRESENT_PARAMETERS *present_parameters, IUnknown *parent) DECLSPEC_HIDDEN;
+        IWineD3DDeviceImpl *device, WINED3DPRESENT_PARAMETERS *present_parameters, void *parent) DECLSPEC_HIDDEN;
 void swapchain_restore_fullscreen_window(IWineD3DSwapChainImpl *swapchain) DECLSPEC_HIDDEN;
 void swapchain_setup_fullscreen_window(IWineD3DSwapChainImpl *swapchain, UINT w, UINT h) DECLSPEC_HIDDEN;
 
@@ -2595,7 +2623,7 @@ void swapchain_setup_fullscreen_window(IWineD3DSwapChainImpl *swapchain, UINT w,
  */
 
 /* Trace routines */
-const char *debug_d3dformat(WINED3DFORMAT fmt) DECLSPEC_HIDDEN;
+const char *debug_d3dformat(enum wined3d_format_id format_id) DECLSPEC_HIDDEN;
 const char *debug_d3ddevicetype(WINED3DDEVTYPE devtype) DECLSPEC_HIDDEN;
 const char *debug_d3dresourcetype(WINED3DRESOURCETYPE res) DECLSPEC_HIDDEN;
 const char *debug_d3dusage(DWORD usage) DECLSPEC_HIDDEN;
@@ -2618,20 +2646,18 @@ const char *debug_d3dtop(WINED3DTEXTUREOP d3dtop) DECLSPEC_HIDDEN;
 void dump_color_fixup_desc(struct color_fixup_desc fixup) DECLSPEC_HIDDEN;
 const char *debug_surflocation(DWORD flag) DECLSPEC_HIDDEN;
 
-/* Color conversion routines */
-DWORD color_convert_argb_to_fmt(DWORD color, WINED3DFORMAT destfmt) DECLSPEC_HIDDEN;
-
 /* Routines for GL <-> D3D values */
 GLenum StencilOp(DWORD op) DECLSPEC_HIDDEN;
 GLenum CompareFunc(DWORD func) DECLSPEC_HIDDEN;
-BOOL is_invalid_op(IWineD3DDeviceImpl *This, int stage, WINED3DTEXTUREOP op,
-        DWORD arg1, DWORD arg2, DWORD arg3) DECLSPEC_HIDDEN;
-void set_tex_op_nvrc(IWineD3DDevice *iface, BOOL is_alpha, int stage, WINED3DTEXTUREOP op,
-        DWORD arg1, DWORD arg2, DWORD arg3, INT texture_idx, DWORD dst) DECLSPEC_HIDDEN;
+BOOL is_invalid_op(const struct wined3d_state *state, int stage,
+        WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3) DECLSPEC_HIDDEN;
+void set_tex_op_nvrc(const struct wined3d_gl_info *gl_info, const struct wined3d_state *state,
+        BOOL is_alpha, int stage, WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3,
+        INT texture_idx, DWORD dst) DECLSPEC_HIDDEN;
 void set_texture_matrix(const float *smat, DWORD flags, BOOL calculatedCoords,
-        BOOL transformed, WINED3DFORMAT coordtype, BOOL ffp_can_disable_proj) DECLSPEC_HIDDEN;
-void texture_activate_dimensions(DWORD stage, IWineD3DStateBlockImpl *stateblock,
-        struct wined3d_context *context) DECLSPEC_HIDDEN;
+        BOOL transformed, enum wined3d_format_id coordtype, BOOL ffp_can_disable_proj) DECLSPEC_HIDDEN;
+void texture_activate_dimensions(IWineD3DBaseTextureImpl *texture,
+        const struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN;
 void sampler_texdim(DWORD state, IWineD3DStateBlockImpl *stateblock,
         struct wined3d_context *context) DECLSPEC_HIDDEN;
 void tex_alphaop(DWORD state, IWineD3DStateBlockImpl *stateblock,
@@ -2647,19 +2673,9 @@ void state_fogstartend(DWORD state, IWineD3DStateBlockImpl *stateblock,
 void state_fog_fragpart(DWORD state, IWineD3DStateBlockImpl *stateblock,
         struct wined3d_context *context) DECLSPEC_HIDDEN;
 
-void surface_add_dirty_rect(IWineD3DSurfaceImpl *surface, const RECT *dirty_rect) DECLSPEC_HIDDEN;
-GLenum surface_get_gl_buffer(IWineD3DSurfaceImpl *surface) DECLSPEC_HIDDEN;
-void surface_load_ds_location(IWineD3DSurfaceImpl *surface,
-        struct wined3d_context *context, DWORD location) DECLSPEC_HIDDEN;
-void surface_modify_ds_location(IWineD3DSurfaceImpl *surface, DWORD location, UINT w, UINT h) DECLSPEC_HIDDEN;
-void surface_set_compatible_renderbuffer(IWineD3DSurfaceImpl *surface,
-        unsigned int width, unsigned int height) DECLSPEC_HIDDEN;
-void surface_set_texture_name(IWineD3DSurfaceImpl *surface, GLuint name, BOOL srgb_name) DECLSPEC_HIDDEN;
-void surface_set_texture_target(IWineD3DSurfaceImpl *surface, GLenum target) DECLSPEC_HIDDEN;
-
-BOOL getColorBits(const struct wined3d_format_desc *format_desc,
+BOOL getColorBits(const struct wined3d_format *format,
         short *redSize, short *greenSize, short *blueSize, short *alphaSize, short *totalSize) DECLSPEC_HIDDEN;
-BOOL getDepthStencilBits(const struct wined3d_format_desc *format_desc,
+BOOL getDepthStencilBits(const struct wined3d_format *format,
         short *depthSize, short *stencilSize) DECLSPEC_HIDDEN;
 
 /* Math utils */
@@ -2707,7 +2723,7 @@ int shader_addline(struct wined3d_shader_buffer *buffer, const char *fmt, ...) P
 int shader_vaddline(struct wined3d_shader_buffer *buffer, const char *fmt, va_list args) DECLSPEC_HIDDEN;
 
 /* Vertex shader utility functions */
-extern BOOL vshader_get_input(IWineD3DVertexShader *iface,
+extern BOOL vshader_get_input(struct IWineD3DVertexShaderImpl *shader,
         BYTE usage_req, BYTE usage_idx_req, unsigned int *regnum) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
@@ -2726,7 +2742,7 @@ typedef struct IWineD3DBaseShaderClass
     void *frontend_data;
     void *backend_data;
 
-    IUnknown *parent;
+    void *parent;
     const struct wined3d_parent_ops *parent_ops;
 
     /* Programs this shader is linked with */
@@ -2783,7 +2799,7 @@ static inline BOOL shader_is_scalar(const struct wined3d_shader_register *reg)
     {
         case WINED3DSPR_RASTOUT:
             /* oFog & oPts */
-            if (reg->idx != 0) return TRUE;
+            if (reg->idx) return TRUE;
             /* oPos */
             return FALSE;
 
@@ -2805,13 +2821,7 @@ static inline BOOL shader_is_scalar(const struct wined3d_shader_register *reg)
             }
 
         case WINED3DSPR_IMMCONST:
-            switch(reg->immconst_type)
-            {
-                case WINED3D_IMMCONST_FLOAT:
-                    return TRUE;
-                default:
-                    return FALSE;
-            }
+            return reg->immconst_type == WINED3D_IMMCONST_SCALAR;
 
         default:
             return FALSE;
@@ -2846,11 +2856,11 @@ typedef struct IWineD3DVertexShaderImpl {
     UINT                       rel_offset;
 } IWineD3DVertexShaderImpl;
 
-void find_vs_compile_args(IWineD3DVertexShaderImpl *shader, IWineD3DStateBlockImpl *stateblock,
-        struct vs_compile_args *args) DECLSPEC_HIDDEN;
+void find_vs_compile_args(const struct wined3d_state *state,
+        IWineD3DVertexShaderImpl *shader, struct vs_compile_args *args) DECLSPEC_HIDDEN;
 HRESULT vertexshader_init(IWineD3DVertexShaderImpl *shader, IWineD3DDeviceImpl *device,
         const DWORD *byte_code, const struct wined3d_shader_signature *output_signature,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 
 struct wined3d_geometryshader
 {
@@ -2860,7 +2870,7 @@ struct wined3d_geometryshader
 
 HRESULT geometryshader_init(struct wined3d_geometryshader *shader, IWineD3DDeviceImpl *device,
         const DWORD *byte_code, const struct wined3d_shader_signature *output_signature,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * IDirect3DPixelShader implementation structure
@@ -2905,11 +2915,11 @@ typedef struct IWineD3DPixelShaderImpl {
 
 HRESULT pixelshader_init(IWineD3DPixelShaderImpl *shader, IWineD3DDeviceImpl *device,
         const DWORD *byte_code, const struct wined3d_shader_signature *output_signature,
-        IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
+        void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
 void pixelshader_update_samplers(struct shader_reg_maps *reg_maps,
         IWineD3DBaseTexture * const *textures) DECLSPEC_HIDDEN;
-void find_ps_compile_args(IWineD3DPixelShaderImpl *shader, IWineD3DStateBlockImpl *stateblock,
-        struct ps_compile_args *args) DECLSPEC_HIDDEN;
+void find_ps_compile_args(const struct wined3d_state *state,
+        IWineD3DPixelShaderImpl *shader, struct ps_compile_args *args) DECLSPEC_HIDDEN;
 
 /* sRGB correction constants */
 static const float srgb_cmp = 0.0031308f;
@@ -2926,7 +2936,7 @@ struct IWineD3DPaletteImpl {
     const IWineD3DPaletteVtbl  *lpVtbl;
     LONG                       ref;
 
-    IUnknown                   *parent;
+    void *parent;
     IWineD3DDeviceImpl *device;
 
     /* IWineD3DPalette */
@@ -2940,10 +2950,10 @@ struct IWineD3DPaletteImpl {
 };
 
 HRESULT wined3d_palette_init(IWineD3DPaletteImpl *palette, IWineD3DDeviceImpl *device,
-        DWORD flags, const PALETTEENTRY *entries, IUnknown *parent) DECLSPEC_HIDDEN;
+        DWORD flags, const PALETTEENTRY *entries, void *parent) DECLSPEC_HIDDEN;
 
 /* DirectDraw utility functions */
-extern WINED3DFORMAT pixelformat_for_depth(DWORD depth) DECLSPEC_HIDDEN;
+extern enum wined3d_format_id pixelformat_for_depth(DWORD depth) DECLSPEC_HIDDEN;
 
 /*****************************************************************************
  * Pixel format management
@@ -2957,7 +2967,7 @@ extern WINED3DFORMAT pixelformat_for_depth(DWORD depth) DECLSPEC_HIDDEN;
 #define WINED3DFMT_FLAG_RENDERTARGET                0x00000010
 #define WINED3DFMT_FLAG_FOURCC                      0x00000020
 #define WINED3DFMT_FLAG_FBO_ATTACHABLE              0x00000040
-#define WINED3DFMT_FLAG_COMPRESSED                  0x00000080
+#define WINED3DFMT_FLAG_FBO_ATTACHABLE_SRGB         0x00000080
 #define WINED3DFMT_FLAG_GETDC                       0x00000100
 #define WINED3DFMT_FLAG_FLOAT                       0x00000200
 #define WINED3DFMT_FLAG_BUMPMAP                     0x00000400
@@ -2965,10 +2975,13 @@ extern WINED3DFORMAT pixelformat_for_depth(DWORD depth) DECLSPEC_HIDDEN;
 #define WINED3DFMT_FLAG_SRGB_WRITE                  0x00001000
 #define WINED3DFMT_FLAG_VTF                         0x00002000
 #define WINED3DFMT_FLAG_SHADOW                      0x00004000
+#define WINED3DFMT_FLAG_COMPRESSED                  0x00008000
+#define WINED3DFMT_FLAG_BROKEN_PITCH                0x00010000
 
-struct wined3d_format_desc
+struct wined3d_format
 {
-    WINED3DFORMAT format;
+    enum wined3d_format_id id;
+
     DWORD red_mask;
     DWORD green_mask;
     DWORD blue_mask;
@@ -3000,29 +3013,27 @@ struct wined3d_format_desc
     void (*convert)(const BYTE *src, BYTE *dst, UINT pitch, UINT width, UINT height);
 };
 
-const struct wined3d_format_desc *getFormatDescEntry(WINED3DFORMAT fmt,
-        const struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN;
+const struct wined3d_format *wined3d_get_format(const struct wined3d_gl_info *gl_info,
+        enum wined3d_format_id format_id) DECLSPEC_HIDDEN;
+UINT wined3d_format_calculate_size(const struct wined3d_format *format,
+        UINT alignment, UINT width, UINT height) DECLSPEC_HIDDEN;
+DWORD wined3d_format_convert_from_float(const struct wined3d_format *format,
+        const WINED3DCOLORVALUE *color) DECLSPEC_HIDDEN;
 
-static inline BOOL use_vs(IWineD3DStateBlockImpl *stateblock)
+static inline BOOL use_vs(const struct wined3d_state *state)
 {
     /* Check stateblock->vertexDecl to allow this to be used from
      * IWineD3DDeviceImpl_FindTexUnitMap(). This is safe because
      * stateblock->vertexShader implies a vertex declaration instead of ddraw
      * style strided data. */
-    return (stateblock->vertexShader
-            && !((IWineD3DVertexDeclarationImpl *)stateblock->vertexDecl)->position_transformed
-            && stateblock->device->vs_selected_mode != SHADER_NONE);
+    return state->vertex_shader && !state->vertex_declaration->position_transformed;
 }
 
-static inline BOOL use_ps(IWineD3DStateBlockImpl *stateblock)
+static inline BOOL use_ps(const struct wined3d_state *state)
 {
-    return (stateblock->pixelShader && stateblock->device->ps_selected_mode != SHADER_NONE);
+    return !!state->pixel_shader;
 }
 
-void stretch_rect_fbo(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *src_surface,
-        const RECT *src_rect, IWineD3DSurfaceImpl *dst_surface, const RECT *dst_rect,
-        const WINED3DTEXTUREFILTERTYPE filter) DECLSPEC_HIDDEN;
-
 /* The WNDCLASS-Name for the fake window which we use to retrieve the GL capabilities */
 #define WINED3D_OPENGL_WINDOW_CLASS_NAME "WineD3D_OpenGL"
 
index 1da7d44..83e2bae 100644 (file)
@@ -135,7 +135,7 @@ typedef enum _WINED3DDEGREETYPE
     WINED3DDEGREE_FORCE_DWORD               = 0x7fffffff
 } WINED3DDEGREETYPE;
 
-typedef enum _WINED3DFORMAT
+enum wined3d_format_id
 {
     WINED3DFMT_UNKNOWN,
     WINED3DFMT_B8G8R8_UNORM,
@@ -267,11 +267,12 @@ typedef enum _WINED3DFORMAT
     WINED3DFMT_R8G8_B8G8                    = 0x47424752, /* RGBG */
     WINED3DFMT_ATI2N                        = 0x32495441, /* ATI2 */
     WINED3DFMT_INST                         = 0x54534e49, /* INST */
+    WINED3DFMT_NVDB                         = 0x4244564e, /* NVDB */
     WINED3DFMT_NVHU                         = 0x5548564e, /* NVHU */
     WINED3DFMT_NVHS                         = 0x5348564e, /* NVHS */
 
     WINED3DFMT_FORCE_DWORD = 0xffffffff
-} WINED3DFORMAT;
+};
 
 typedef enum _WINED3DRENDERSTATETYPE
 {
@@ -1536,7 +1537,7 @@ typedef struct _WINED3DDISPLAYMODE
     UINT Width;
     UINT Height;
     UINT RefreshRate;
-    WINED3DFORMAT Format;
+    enum wined3d_format_id Format;
 } WINED3DDISPLAYMODE;
 
 typedef struct _WINED3DCOLORVALUE
@@ -1569,14 +1570,6 @@ typedef struct _WINED3DMATRIX
     } DUMMYUNIONNAME;
 } WINED3DMATRIX;
 
-typedef struct _WINED3DRECT
-{
-    LONG x1;
-    LONG y1;
-    LONG x2;
-    LONG y2;
-} WINED3DRECT;
-
 typedef struct _WINED3DLIGHT
 {
     WINED3DLIGHTTYPE Type;
@@ -1668,7 +1661,7 @@ typedef struct _WINED3DPRESENT_PARAMETERS
 {
     UINT BackBufferWidth;
     UINT BackBufferHeight;
-    WINED3DFORMAT BackBufferFormat;
+    enum wined3d_format_id BackBufferFormat;
     UINT BackBufferCount;
     WINED3DMULTISAMPLE_TYPE MultiSampleType;
     DWORD MultiSampleQuality;
@@ -1676,7 +1669,7 @@ typedef struct _WINED3DPRESENT_PARAMETERS
     HWND hDeviceWindow;
     BOOL Windowed;
     BOOL EnableAutoDepthStencil;
-    WINED3DFORMAT AutoDepthStencilFormat;
+    enum wined3d_format_id AutoDepthStencilFormat;
     DWORD Flags;
     UINT FullScreen_RefreshRateInHz;
     UINT PresentationInterval;
@@ -1685,7 +1678,7 @@ typedef struct _WINED3DPRESENT_PARAMETERS
 
 typedef struct _WINED3DSURFACE_DESC
 {
-    WINED3DFORMAT format;
+    enum wined3d_format_id format;
     WINED3DRESOURCETYPE resource_type;
     DWORD usage;
     WINED3DPOOL pool;
@@ -1698,7 +1691,7 @@ typedef struct _WINED3DSURFACE_DESC
 
 typedef struct _WINED3DVOLUME_DESC
 {
-    WINED3DFORMAT Format;
+    enum wined3d_format_id Format;
     WINED3DRESOURCETYPE Type;
     DWORD Usage;
     WINED3DPOOL Pool;
@@ -1716,7 +1709,7 @@ typedef struct _WINED3DCLIPSTATUS
 
 typedef struct _WINED3DVERTEXELEMENT
 {
-    WINED3DFORMAT format;
+    enum wined3d_format_id format;
     WORD input_slot;
     WORD offset;
     UINT output_slot; /* D3D 8 & 10 */
@@ -1846,7 +1839,7 @@ typedef struct _WINED3DBUFFER_DESC
 
 typedef struct WineDirect3DStridedData
 {
-    WINED3DFORMAT format;   /* Format of the data */
+    enum wined3d_format_id format;   /* Format of the data */
     const BYTE *lpData;     /* Pointer to start of data */
     DWORD dwStride;         /* Stride between occurrences of this data */
 } WineDirect3DStridedData;
@@ -2103,7 +2096,7 @@ struct wined3d_shader_signature
 
 struct wined3d_parent_ops
 {
-    void (*wined3d_object_destroyed)(void *parent);
+    void (__stdcall *wined3d_object_destroyed)(void *parent);
 };
 
 interface IWineD3DResource;
@@ -2127,7 +2120,7 @@ interface IWineD3DDeviceParent : IUnknown
         [in] IUnknown *superior,
         [in] UINT width,
         [in] UINT height,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] DWORD usage,
         [in] WINED3DPOOL pool,
         [in] UINT level,
@@ -2139,7 +2132,7 @@ interface IWineD3DDeviceParent : IUnknown
         [in] IUnknown *superior,
         [in] UINT width,
         [in] UINT height,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] WINED3DMULTISAMPLE_TYPE multisample_type,
         [in] DWORD multisample_quality,
         [in] BOOL lockable,
@@ -2147,10 +2140,9 @@ interface IWineD3DDeviceParent : IUnknown
     );
 
     HRESULT CreateDepthStencilSurface(
-        [in] IUnknown *superior,
         [in] UINT width,
         [in] UINT height,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] WINED3DMULTISAMPLE_TYPE multisample_type,
         [in] DWORD multisample_quality,
         [in] BOOL discard,
@@ -2162,7 +2154,7 @@ interface IWineD3DDeviceParent : IUnknown
         [in] UINT width,
         [in] UINT height,
         [in] UINT depth,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] WINED3DPOOL pool,
         [in] DWORD usage,
         [out] IWineD3DVolume **volume
@@ -2173,8 +2165,8 @@ interface IWineD3DDeviceParent : IUnknown
         [out] IWineD3DSwapChain **swapchain
     );
 }
-typedef ULONG (*D3DCB_DESTROYSWAPCHAINFN)(IWineD3DSwapChain *pSwapChain);
-typedef HRESULT (*D3DCB_ENUMRESOURCES)(IWineD3DResource *resource, void *pData);
+typedef ULONG (__stdcall *D3DCB_DESTROYSWAPCHAINFN)(IWineD3DSwapChain *pSwapChain);
+typedef HRESULT (__stdcall *D3DCB_ENUMRESOURCES)(IWineD3DResource *resource, void *pData);
 
 [
     object,
@@ -2183,8 +2175,7 @@ typedef HRESULT (*D3DCB_ENUMRESOURCES)(IWineD3DResource *resource, void *pData);
 ]
 interface IWineD3DBase : IUnknown
 {
-    HRESULT GetParent(
-        [out] IUnknown **parent
+    void *GetParent(
     );
 }
 
@@ -2205,11 +2196,11 @@ interface IWineD3D : IWineD3DBase
     );
     UINT GetAdapterModeCount(
         [in] UINT adapter_idx,
-        [in] WINED3DFORMAT format
+        [in] enum wined3d_format_id format_id
     );
     HRESULT EnumAdapterModes(
         [in] UINT adapter_idx,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] UINT mode_idx,
         [out] WINED3DDISPLAYMODE *mode
     );
@@ -2225,7 +2216,7 @@ interface IWineD3D : IWineD3DBase
     HRESULT CheckDeviceMultiSampleType(
         [in] UINT adapter_idx,
         [in] WINED3DDEVTYPE device_type,
-        [in] WINED3DFORMAT surface_format,
+        [in] enum wined3d_format_id surface_format_id,
         [in] BOOL windowed,
         [in] WINED3DMULTISAMPLE_TYPE multisample_type,
         [out] DWORD *quality_levels
@@ -2233,31 +2224,31 @@ interface IWineD3D : IWineD3DBase
     HRESULT CheckDepthStencilMatch(
         [in] UINT adapter_idx,
         [in] WINED3DDEVTYPE device_type,
-        [in] WINED3DFORMAT adapter_format,
-        [in] WINED3DFORMAT render_target_format,
-        [in] WINED3DFORMAT depth_stencil_format
+        [in] enum wined3d_format_id adapter_format_id,
+        [in] enum wined3d_format_id render_target_format_id,
+        [in] enum wined3d_format_id depth_stencil_format_id
     );
     HRESULT CheckDeviceType(
         [in] UINT adapter_idx,
         [in] WINED3DDEVTYPE device_type,
-        [in] WINED3DFORMAT display_format,
-        [in] WINED3DFORMAT backbuffer_format,
+        [in] enum wined3d_format_id display_format_id,
+        [in] enum wined3d_format_id backbuffer_format_id,
         [in] BOOL windowed
     );
     HRESULT CheckDeviceFormat(
         [in] UINT adaper_idx,
         [in] WINED3DDEVTYPE device_type,
-        [in] WINED3DFORMAT adapter_format,
+        [in] enum wined3d_format_id adapter_format_id,
         [in] DWORD usage,
         [in] WINED3DRESOURCETYPE resource_type,
-        [in] WINED3DFORMAT check_format,
+        [in] enum wined3d_format_id check_format,
         [in] WINED3DSURFTYPE surface_type
     );
     HRESULT CheckDeviceFormatConversion(
         [in] UINT adapter_idx,
         [in] WINED3DDEVTYPE device_type,
-        [in] WINED3DFORMAT source_format,
-        [in] WINED3DFORMAT target_format
+        [in] enum wined3d_format_id source_format_id,
+        [in] enum wined3d_format_id target_format_id
     );
     HRESULT GetDeviceCaps(
         [in] UINT adapter_idx,
@@ -2269,7 +2260,6 @@ interface IWineD3D : IWineD3DBase
         [in] WINED3DDEVTYPE device_type,
         [in] HWND focus_window,
         [in] DWORD behaviour_flags,
-        [in] IUnknown *parent,
         [in] IWineD3DDeviceParent *device_parent,
         [out] IWineD3DDevice **device
     );
@@ -2350,7 +2340,7 @@ interface IWineD3DPalette : IWineD3DBase
     local,
     uuid(8f2bceb1-d338-488c-ab7f-0ec980bf5d2d)
 ]
-interface IWineD3DClipper : IWineD3DBase
+interface IWineD3DClipper : IUnknown
 {
     HRESULT GetClipList(
         [in] const RECT *rect,
@@ -2380,11 +2370,7 @@ interface IWineD3DClipper : IWineD3DBase
 ]
 interface IWineD3DSurface : IWineD3DResource
 {
-    HRESULT GetContainer(
-        [in] REFIID riid,
-        [out] void **container
-    );
-    HRESULT GetDesc(
+    void GetDesc(
         [out] WINED3DSURFACE_DESC *desc
     );
     HRESULT LockRect(
@@ -2477,27 +2463,13 @@ interface IWineD3DSurface : IWineD3DResource
     void BindTexture(
         [in] BOOL srgb
     );
-    HRESULT SaveSnapshot(
-        [in] const char *filename
-    );
-    HRESULT SetContainer(
-        [in] IWineD3DBase *container
-    );
     const void *GetData(
     );
     HRESULT SetFormat(
-        [in] WINED3DFORMAT format
+        [in] enum wined3d_format_id format_id
     );
     HRESULT PrivateSetup(
     );
-    void ModifyLocation(
-        [in] DWORD location,
-        [in] BOOL persistent
-    );
-    HRESULT LoadLocation(
-        [in] DWORD location,
-        [in] const RECT *rect
-    );
     WINED3DSURFTYPE GetImplType(
     );
     HRESULT DrawOverlay(
@@ -2511,11 +2483,7 @@ interface IWineD3DSurface : IWineD3DResource
 ]
 interface IWineD3DVolume : IWineD3DResource
 {
-    HRESULT GetContainer(
-        [in] REFIID riid,
-        [out] void **container
-    );
-    HRESULT GetDesc(
+    void GetDesc(
         [out] WINED3DVOLUME_DESC *desc
     );
     HRESULT LockBox(
@@ -2529,9 +2497,6 @@ interface IWineD3DVolume : IWineD3DResource
         [in] int gl_level,
         [in] BOOL srgb_mode
     );
-    HRESULT SetContainer(
-        [in] IWineD3DBase *container
-    );
 }
 
 [
@@ -2563,8 +2528,6 @@ interface IWineD3DBaseTexture : IWineD3DResource
     HRESULT BindTexture(
         [in] BOOL srgb
     );
-    UINT GetTextureDimensions(
-    );
     BOOL IsCondNP2(
     );
 }
@@ -2680,8 +2643,6 @@ interface IWineD3DStateBlock : IUnknown
     );
     HRESULT Apply(
     );
-    HRESULT InitStartupStateBlock(
-    );
 }
 
 [
@@ -2689,7 +2650,7 @@ interface IWineD3DStateBlock : IUnknown
     local,
     uuid(905ddbac-6f30-11d9-c687-00046142c14f)
 ]
-interface IWineD3DQuery : IWineD3DBase
+interface IWineD3DQuery : IUnknown
 {
     HRESULT GetData(
         [out] void *data,
@@ -2768,7 +2729,7 @@ interface IWineD3DBuffer : IWineD3DResource
     );
     HRESULT Unmap(
     );
-    HRESULT GetDesc(
+    void GetDesc(
         [out] WINED3DBUFFER_DESC *desc
     );
 }
@@ -2823,12 +2784,12 @@ interface IWineD3DPixelShader : IWineD3DBaseShader
     local,
     uuid(6d10a2ce-09d0-4a53-a427-11388f9f8ca5)
 ]
-interface IWineD3DDevice : IWineD3DBase
+interface IWineD3DDevice : IUnknown
 {
     HRESULT CreateBuffer(
         [in] struct wined3d_buffer_desc *desc,
         [in] const void *data,
-        [in] IUnknown *parent,
+        [in] void *parent,
         [in] const struct wined3d_parent_ops *parent_ops,
         [out] IWineD3DBuffer **buffer
     );
@@ -2836,42 +2797,41 @@ interface IWineD3DDevice : IWineD3DBase
         [in] UINT length,
         [in] DWORD usage,
         [in] WINED3DPOOL pool,
-        [out] IWineD3DBuffer **vertex_buffer,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DBuffer **vertex_buffer
     );
     HRESULT CreateIndexBuffer(
         [in] UINT length,
         [in] DWORD usage,
         [in] WINED3DPOOL pool,
-        [out] IWineD3DBuffer **index_buffer,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DBuffer **index_buffer
     );
     HRESULT CreateStateBlock(
         [in] WINED3DSTATEBLOCKTYPE type,
-        [out] IWineD3DStateBlock **stateblock,
-        [in] IUnknown *parent
+        [out] IWineD3DStateBlock **stateblock
     );
     HRESULT CreateSurface(
         [in] UINT width,
         [in] UINT height,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] BOOL lockable,
         [in] BOOL discard,
         [in] UINT level,
-        [out] IWineD3DSurface **surface,
         [in] DWORD usage,
         [in] WINED3DPOOL pool,
         [in] WINED3DMULTISAMPLE_TYPE multisample_type,
         [in] DWORD multisample_quality,
         [in] WINED3DSURFTYPE surface_type,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DSurface **surface
     );
     HRESULT CreateRendertargetView(
         [in] IWineD3DResource *resource,
-        [in] IUnknown *parent,
+        [in] void *parent,
         [out] IWineD3DRendertargetView **rendertarget_view
     );
     HRESULT CreateTexture(
@@ -2879,11 +2839,11 @@ interface IWineD3DDevice : IWineD3DBase
         [in] UINT height,
         [in] UINT levels,
         [in] DWORD usage,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] WINED3DPOOL pool,
-        [out] IWineD3DTexture **texture,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DTexture **texture
     );
     HRESULT CreateVolumeTexture(
         [in] UINT width,
@@ -2891,83 +2851,82 @@ interface IWineD3DDevice : IWineD3DBase
         [in] UINT depth,
         [in] UINT levels,
         [in] DWORD usage,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] WINED3DPOOL pool,
-        [out] IWineD3DVolumeTexture **texture,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DVolumeTexture **texture
     );
     HRESULT CreateVolume(
         [in] UINT width,
         [in] UINT height,
         [in] UINT depth,
         [in] DWORD usage,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] WINED3DPOOL pool,
-        [out] IWineD3DVolume **volume,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DVolume **volume
     );
     HRESULT CreateCubeTexture(
         [in] UINT edge_length,
         [in] UINT levels,
         [in] DWORD usage,
-        [in] WINED3DFORMAT format,
+        [in] enum wined3d_format_id format_id,
         [in] WINED3DPOOL pool,
-        [out] IWineD3DCubeTexture **texture,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DCubeTexture **texture
     );
     HRESULT CreateQuery(
         [in] WINED3DQUERYTYPE type,
-        [out] IWineD3DQuery **query,
-        [in] IUnknown *parent
+        [out] IWineD3DQuery **query
     );
     HRESULT CreateSwapChain(
         [in] WINED3DPRESENT_PARAMETERS *present_parameters,
-        [out] IWineD3DSwapChain **swapchain,
-        [in] IUnknown *parent,
-        [in] WINED3DSURFTYPE surface_type
+        [in] WINED3DSURFTYPE surface_type,
+        [in] void *parent,
+        [out] IWineD3DSwapChain **swapchain
     );
     HRESULT CreateVertexDeclaration(
-        [out] IWineD3DVertexDeclaration **declaration,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops,
         [in] const WINED3DVERTEXELEMENT *elements,
-        [in] UINT element_count
+        [in] UINT element_count,
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DVertexDeclaration **declaration
     );
     HRESULT CreateVertexDeclarationFromFVF(
-        [out] IWineD3DVertexDeclaration **declaration,
-        [in] IUnknown *parent,
+        [in] DWORD fvf,
+        [in] void *parent,
         [in] const struct wined3d_parent_ops *parent_ops,
-        [in] DWORD fvf
+        [out] IWineD3DVertexDeclaration **declaration
     );
     HRESULT CreateVertexShader(
         [in] const DWORD *function,
         [in] const struct wined3d_shader_signature *output_signature,
-        [out] IWineD3DVertexShader **shader,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DVertexShader **shader
     );
     HRESULT CreateGeometryShader(
         [in] const DWORD *byte_code,
         [in] const struct wined3d_shader_signature *output_signature,
-        [out] IWineD3DGeometryShader **shader,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DGeometryShader **shader
     );
     HRESULT CreatePixelShader(
         [in] const DWORD *function,
         [in] const struct wined3d_shader_signature *output_signature,
-        [out] IWineD3DPixelShader **shader,
-        [in] IUnknown *parent,
-        [in] const struct wined3d_parent_ops *parent_ops
+        [in] void *parent,
+        [in] const struct wined3d_parent_ops *parent_ops,
+        [out] IWineD3DPixelShader **shader
     );
     HRESULT CreatePalette(
         [in] DWORD flags,
         [in] const PALETTEENTRY *palette_entry,
-        [out] IWineD3DPalette **palette,
-        [in] IUnknown *parent
+        [in] void *parent,
+        [out] IWineD3DPalette **palette
     );
     HRESULT Init3D(
         [in] WINED3DPRESENT_PARAMETERS *present_parameters
@@ -3076,7 +3035,7 @@ interface IWineD3DDevice : IWineD3DBase
     );
     HRESULT SetIndexBuffer(
         [in] IWineD3DBuffer *index_buffer,
-        [in] WINED3DFORMAT format
+        [in] enum wined3d_format_id format_id
     );
     HRESULT GetIndexBuffer(
         [out] IWineD3DBuffer **index_buffer
@@ -3125,8 +3084,7 @@ interface IWineD3DDevice : IWineD3DBase
     HRESULT SetPixelShader(
         [in] IWineD3DPixelShader *shader
     );
-    HRESULT GetPixelShader(
-        [out] IWineD3DPixelShader **shader
+    IWineD3DPixelShader *GetPixelShader(
     );
     HRESULT SetPixelShaderConstantB(
         [in] UINT start_register,
@@ -3175,10 +3133,6 @@ interface IWineD3DDevice : IWineD3DBase
         [in] DWORD render_target_idx,
         [out] IWineD3DSurface **render_target
     );
-    HRESULT SetFrontBackBuffers(
-        [in] IWineD3DSurface *front,
-        [in] IWineD3DSurface *back
-    );
     HRESULT SetSamplerState(
         [in] DWORD sampler_idx,
         [in] WINED3DSAMPLERSTATETYPE state,
@@ -3255,8 +3209,7 @@ interface IWineD3DDevice : IWineD3DBase
     HRESULT SetVertexShader(
         [in] IWineD3DVertexShader *shader
     );
-    HRESULT GetVertexShader(
-        [out] IWineD3DVertexShader **shader
+    IWineD3DVertexShader *GetVertexShader(
     );
     HRESULT SetVertexShaderConstantB(
         [in] UINT start_register,
@@ -3327,7 +3280,7 @@ interface IWineD3DDevice : IWineD3DBase
     );
     HRESULT Clear(
         [in] DWORD rect_count,
-        [in] const WINED3DRECT *rects,
+        [in] const RECT *rects,
         [in] DWORD flags,
         [in] WINED3DCOLOR color,
         [in] float z,
@@ -3335,7 +3288,7 @@ interface IWineD3DDevice : IWineD3DBase
     );
     void ClearRendertargetView(
         [in] IWineD3DRendertargetView *rendertarget_view,
-        [in] const float color[4]
+        [in] const WINED3DCOLORVALUE *color
     );
     void SetPrimitiveType(
         [in] WINED3DPRIMITIVETYPE primitive_topology
@@ -3359,7 +3312,7 @@ interface IWineD3DDevice : IWineD3DBase
     HRESULT DrawIndexedPrimitiveUP(
         [in] UINT index_count,
         [in] const void *index_data,
-        [in] WINED3DFORMAT index_data_format,
+        [in] enum wined3d_format_id index_data_format_id,
         [in] const void *stream_data,
         [in] UINT stream_stride
     );
@@ -3372,7 +3325,7 @@ interface IWineD3DDevice : IWineD3DBase
         [in] const WineDirect3DVertexStridedData *strided_data,
         [in] UINT vertex_count,
         [in] const void *index_data,
-        [in] WINED3DFORMAT index_data_format
+        [in] enum wined3d_format_id index_data_format_id
     );
     HRESULT DrawRectPatch(
         [in] UINT handle,
@@ -3389,8 +3342,8 @@ interface IWineD3DDevice : IWineD3DBase
     );
     HRESULT ColorFill(
         [in] IWineD3DSurface *surface,
-        [in] const WINED3DRECT *rect,
-        [in] WINED3DCOLOR color
+        [in] const RECT *rect,
+        [in] const WINED3DCOLORVALUE *color
     );
     HRESULT UpdateTexture(
         [in] IWineD3DBaseTexture *src_texture,
@@ -3421,7 +3374,7 @@ interface IWineD3DDevice : IWineD3DBase
     );
 }
 
-IWineD3D *WineDirect3DCreate(UINT dxVersion, IUnknown *parent);
-IWineD3DClipper *WineDirect3DCreateClipper(IUnknown *parent);
+IWineD3D *WineDirect3DCreate(UINT dxVersion, void *parent);
+IWineD3DClipper *WineDirect3DCreateClipper(void);
 void wined3d_mutex_lock(void);
 void wined3d_mutex_unlock(void);