- Sync wined3d, ddraw, d3d8, d3d9 with Wine

svn path=/trunk/; revision=47371
This commit is contained in:
Kamil Hornicek 2010-05-27 10:25:14 +00:00
parent 7c79933df4
commit 5989fa66dd
42 changed files with 7375 additions and 6167 deletions

View file

@ -171,18 +171,19 @@ static DWORD d3d8_allocate_handle(struct d3d8_handle_table *t, void *object, enu
if (t->free_entries) if (t->free_entries)
{ {
DWORD index = t->free_entries - t->entries;
/* Use a free handle */ /* Use a free handle */
entry = t->free_entries; entry = t->free_entries;
if (entry->type != D3D8_HANDLE_FREE) if (entry->type != D3D8_HANDLE_FREE)
{ {
ERR("Handle %u(%p) is in the free list, but has type %#x.\n", (entry - t->entries), entry, entry->type); ERR("Handle %u(%p) is in the free list, but has type %#x.\n", index, entry, entry->type);
return D3D8_INVALID_HANDLE; return D3D8_INVALID_HANDLE;
} }
t->free_entries = entry->object; t->free_entries = entry->object;
entry->object = object; entry->object = object;
entry->type = type; entry->type = type;
return entry - t->entries; return index;
} }
if (!(t->entry_count < t->table_size)) if (!(t->entry_count < t->table_size))
@ -324,6 +325,7 @@ static ULONG WINAPI IDirect3DDevice8Impl_Release(LPDIRECT3DDEVICE8 iface) {
HeapFree(GetProcessHeap(), 0, This->decls); HeapFree(GetProcessHeap(), 0, This->decls);
IWineD3DDevice_Uninit3D(This->WineD3DDevice, D3D8CB_DestroySwapChain); IWineD3DDevice_Uninit3D(This->WineD3DDevice, D3D8CB_DestroySwapChain);
IWineD3DDevice_ReleaseFocusWindow(This->WineD3DDevice);
IWineD3DDevice_Release(This->WineD3DDevice); IWineD3DDevice_Release(This->WineD3DDevice);
HeapFree(GetProcessHeap(), 0, This->handle_table.entries); HeapFree(GetProcessHeap(), 0, This->handle_table.entries);
HeapFree(GetProcessHeap(), 0, This); HeapFree(GetProcessHeap(), 0, This);
@ -2762,6 +2764,19 @@ static const IWineD3DDeviceParentVtbl d3d8_wined3d_device_parent_vtbl =
device_parent_CreateSwapChain, device_parent_CreateSwapChain,
}; };
static void setup_fpu(void)
{
WORD cw;
#if defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__))
__asm__ volatile ("fnstcw %0" : "=m" (cw));
cw = (cw & ~0xf3f) | 0x3f;
__asm__ volatile ("fldcw %0" : : "m" (cw));
#else
FIXME("FPU setup not implemented for this platform.\n");
#endif
}
HRESULT device_init(IDirect3DDevice8Impl *device, IWineD3D *wined3d, UINT adapter, HRESULT device_init(IDirect3DDevice8Impl *device, IWineD3D *wined3d, UINT adapter,
D3DDEVTYPE device_type, HWND focus_window, DWORD flags, D3DPRESENT_PARAMETERS *parameters) D3DDEVTYPE device_type, HWND focus_window, DWORD flags, D3DPRESENT_PARAMETERS *parameters)
{ {
@ -2780,6 +2795,8 @@ HRESULT device_init(IDirect3DDevice8Impl *device, IWineD3D *wined3d, UINT adapte
} }
device->handle_table.table_size = D3D8_INITIAL_HANDLE_TABLE_SIZE; device->handle_table.table_size = D3D8_INITIAL_HANDLE_TABLE_SIZE;
if (!(flags & D3DCREATE_FPU_PRESERVE)) setup_fpu();
wined3d_mutex_lock(); 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, (IUnknown *)device,
(IWineD3DDeviceParent *)&device->device_parent_vtbl, &device->WineD3DDevice); (IWineD3DDeviceParent *)&device->device_parent_vtbl, &device->WineD3DDevice);
@ -2791,6 +2808,19 @@ HRESULT device_init(IDirect3DDevice8Impl *device, IWineD3D *wined3d, UINT adapte
return hr; return hr;
} }
if (!parameters->Windowed)
{
if (!focus_window) focus_window = parameters->hDeviceWindow;
if (FAILED(hr = IWineD3DDevice_AcquireFocusWindow(device->WineD3DDevice, focus_window)))
{
ERR("Failed to acquire focus window, hr %#x.\n", hr);
IWineD3DDevice_Release(device->WineD3DDevice);
wined3d_mutex_unlock();
HeapFree(GetProcessHeap(), 0, device->handle_table.entries);
return hr;
}
}
if (flags & D3DCREATE_MULTITHREADED) IWineD3DDevice_SetMultithreaded(device->WineD3DDevice); if (flags & D3DCREATE_MULTITHREADED) IWineD3DDevice_SetMultithreaded(device->WineD3DDevice);
wined3d_parameters.BackBufferWidth = parameters->BackBufferWidth; wined3d_parameters.BackBufferWidth = parameters->BackBufferWidth;
@ -2813,6 +2843,7 @@ HRESULT device_init(IDirect3DDevice8Impl *device, IWineD3D *wined3d, UINT adapte
if (FAILED(hr)) if (FAILED(hr))
{ {
WARN("Failed to initialize 3D, hr %#x.\n", hr); WARN("Failed to initialize 3D, hr %#x.\n", hr);
IWineD3DDevice_ReleaseFocusWindow(device->WineD3DDevice);
IWineD3DDevice_Release(device->WineD3DDevice); IWineD3DDevice_Release(device->WineD3DDevice);
wined3d_mutex_unlock(); wined3d_mutex_unlock();
HeapFree(GetProcessHeap(), 0, device->handle_table.entries); HeapFree(GetProcessHeap(), 0, device->handle_table.entries);
@ -2855,6 +2886,7 @@ HRESULT device_init(IDirect3DDevice8Impl *device, IWineD3D *wined3d, UINT adapte
err: err:
wined3d_mutex_lock(); wined3d_mutex_lock();
IWineD3DDevice_Uninit3D(device->WineD3DDevice, D3D8CB_DestroySwapChain); IWineD3DDevice_Uninit3D(device->WineD3DDevice, D3D8CB_DestroySwapChain);
IWineD3DDevice_ReleaseFocusWindow(device->WineD3DDevice);
IWineD3DDevice_Release(device->WineD3DDevice); IWineD3DDevice_Release(device->WineD3DDevice);
wined3d_mutex_unlock(); wined3d_mutex_unlock();
HeapFree(GetProcessHeap(), 0, device->handle_table.entries); HeapFree(GetProcessHeap(), 0, device->handle_table.entries);

View file

@ -271,6 +271,7 @@ static ULONG WINAPI DECLSPEC_HOTPATCH IDirect3DDevice9Impl_Release(LPDIRECT3DDEV
HeapFree(GetProcessHeap(), 0, This->convertedDecls); HeapFree(GetProcessHeap(), 0, This->convertedDecls);
IWineD3DDevice_Uninit3D(This->WineD3DDevice, D3D9CB_DestroySwapChain); IWineD3DDevice_Uninit3D(This->WineD3DDevice, D3D9CB_DestroySwapChain);
IWineD3DDevice_ReleaseFocusWindow(This->WineD3DDevice);
IWineD3DDevice_Release(This->WineD3DDevice); IWineD3DDevice_Release(This->WineD3DDevice);
wined3d_mutex_unlock(); wined3d_mutex_unlock();
@ -2821,6 +2822,19 @@ static const IWineD3DDeviceParentVtbl d3d9_wined3d_device_parent_vtbl =
device_parent_CreateSwapChain, device_parent_CreateSwapChain,
}; };
static void setup_fpu(void)
{
WORD cw;
#if defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__))
__asm__ volatile ("fnstcw %0" : "=m" (cw));
cw = (cw & ~0xf3f) | 0x3f;
__asm__ volatile ("fldcw %0" : : "m" (cw));
#else
FIXME("FPU setup not implemented for this platform.\n");
#endif
}
HRESULT device_init(IDirect3DDevice9Impl *device, IWineD3D *wined3d, UINT adapter, D3DDEVTYPE device_type, HRESULT device_init(IDirect3DDevice9Impl *device, IWineD3D *wined3d, UINT adapter, D3DDEVTYPE device_type,
HWND focus_window, DWORD flags, D3DPRESENT_PARAMETERS *parameters) HWND focus_window, DWORD flags, D3DPRESENT_PARAMETERS *parameters)
{ {
@ -2832,6 +2846,8 @@ HRESULT device_init(IDirect3DDevice9Impl *device, IWineD3D *wined3d, UINT adapte
device->device_parent_vtbl = &d3d9_wined3d_device_parent_vtbl; device->device_parent_vtbl = &d3d9_wined3d_device_parent_vtbl;
device->ref = 1; device->ref = 1;
if (!(flags & D3DCREATE_FPU_PRESERVE)) setup_fpu();
wined3d_mutex_lock(); 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, (IUnknown *)device,
(IWineD3DDeviceParent *)&device->device_parent_vtbl, &device->WineD3DDevice); (IWineD3DDeviceParent *)&device->device_parent_vtbl, &device->WineD3DDevice);
@ -2842,6 +2858,18 @@ HRESULT device_init(IDirect3DDevice9Impl *device, IWineD3D *wined3d, UINT adapte
return hr; return hr;
} }
if (!parameters->Windowed)
{
if (!focus_window) focus_window = parameters->hDeviceWindow;
if (FAILED(hr = IWineD3DDevice_AcquireFocusWindow(device->WineD3DDevice, focus_window)))
{
ERR("Failed to acquire focus window, hr %#x.\n", hr);
IWineD3DDevice_Release(device->WineD3DDevice);
wined3d_mutex_unlock();
return hr;
}
}
if (flags & D3DCREATE_ADAPTERGROUP_DEVICE) if (flags & D3DCREATE_ADAPTERGROUP_DEVICE)
{ {
WINED3DCAPS caps; WINED3DCAPS caps;
@ -2885,6 +2913,7 @@ HRESULT device_init(IDirect3DDevice9Impl *device, IWineD3D *wined3d, UINT adapte
if (FAILED(hr)) if (FAILED(hr))
{ {
WARN("Failed to initialize 3D, hr %#x.\n", hr); WARN("Failed to initialize 3D, hr %#x.\n", hr);
IWineD3DDevice_ReleaseFocusWindow(device->WineD3DDevice);
HeapFree(GetProcessHeap(), 0, wined3d_parameters); HeapFree(GetProcessHeap(), 0, wined3d_parameters);
IWineD3DDevice_Release(device->WineD3DDevice); IWineD3DDevice_Release(device->WineD3DDevice);
wined3d_mutex_unlock(); wined3d_mutex_unlock();
@ -2921,6 +2950,7 @@ HRESULT device_init(IDirect3DDevice9Impl *device, IWineD3D *wined3d, UINT adapte
ERR("Failed to allocate FVF vertex declaration map memory.\n"); ERR("Failed to allocate FVF vertex declaration map memory.\n");
wined3d_mutex_lock(); wined3d_mutex_lock();
IWineD3DDevice_Uninit3D(device->WineD3DDevice, D3D9CB_DestroySwapChain); IWineD3DDevice_Uninit3D(device->WineD3DDevice, D3D9CB_DestroySwapChain);
IWineD3DDevice_ReleaseFocusWindow(device->WineD3DDevice);
IWineD3DDevice_Release(device->WineD3DDevice); IWineD3DDevice_Release(device->WineD3DDevice);
wined3d_mutex_unlock(); wined3d_mutex_unlock();
return E_OUTOFMEMORY; return E_OUTOFMEMORY;

View file

@ -264,8 +264,8 @@ IDirectDrawImpl_AddRef(IDirectDraw7 *iface)
void void
IDirectDrawImpl_Destroy(IDirectDrawImpl *This) IDirectDrawImpl_Destroy(IDirectDrawImpl *This)
{ {
/* Clear the cooplevel to restore window and display mode */
IDirectDraw7_SetCooperativeLevel((IDirectDraw7 *)This, NULL, DDSCL_NORMAL); IDirectDraw7_SetCooperativeLevel((IDirectDraw7 *)This, NULL, DDSCL_NORMAL);
IDirectDraw7_RestoreDisplayMode((IDirectDraw7 *)This);
/* Destroy the device window if we created one */ /* Destroy the device window if we created one */
if(This->devicewindow != 0) if(This->devicewindow != 0)
@ -441,12 +441,11 @@ IDirectDrawImpl_SetCooperativeLevel(IDirectDraw7 *iface,
/* Switching from fullscreen? */ /* Switching from fullscreen? */
if(This->cooperative_level & DDSCL_FULLSCREEN) if(This->cooperative_level & DDSCL_FULLSCREEN)
{ {
/* Restore the display mode */
IDirectDraw7_RestoreDisplayMode(iface);
This->cooperative_level &= ~DDSCL_FULLSCREEN; This->cooperative_level &= ~DDSCL_FULLSCREEN;
This->cooperative_level &= ~DDSCL_EXCLUSIVE; This->cooperative_level &= ~DDSCL_EXCLUSIVE;
This->cooperative_level &= ~DDSCL_ALLOWMODEX; This->cooperative_level &= ~DDSCL_ALLOWMODEX;
IWineD3DDevice_ReleaseFocusWindow(This->wineD3DDevice);
} }
/* Don't override focus windows or private device windows */ /* Don't override focus windows or private device windows */
@ -483,6 +482,13 @@ IDirectDrawImpl_SetCooperativeLevel(IDirectDraw7 *iface,
!(This->devicewindow) && !(This->devicewindow) &&
(hwnd != window) ) (hwnd != window) )
{ {
HRESULT hr = IWineD3DDevice_AcquireFocusWindow(This->wineD3DDevice, hwnd);
if (FAILED(hr))
{
ERR("Failed to acquire focus window, hr %#x.\n", hr);
LeaveCriticalSection(&ddraw_cs);
return hr;
}
This->dest_window = hwnd; This->dest_window = hwnd;
} }
} }
@ -1514,11 +1520,24 @@ IDirectDrawImpl_GetSurfaceFromDC(IDirectDraw7 *iface,
IDirectDrawSurface7 **Surface) IDirectDrawSurface7 **Surface)
{ {
IDirectDrawImpl *This = (IDirectDrawImpl *)iface; IDirectDrawImpl *This = (IDirectDrawImpl *)iface;
FIXME("(%p)->(%p,%p): Stub!\n", This, hdc, Surface); IWineD3DSurface *wined3d_surface;
HRESULT hr;
/* Implementation idea if needed: Loop through all surfaces and compare TRACE("iface %p, dc %p, surface %p.\n", iface, hdc, Surface);
* their hdc with hdc. Implement it in WineD3D! */
return DDERR_NOTFOUND; if (!Surface) return E_INVALIDARG;
hr = IWineD3DDevice_GetSurfaceFromDC(This->wineD3DDevice, hdc, &wined3d_surface);
if (FAILED(hr))
{
TRACE("No surface found for dc %p.\n", hdc);
*Surface = NULL;
return DDERR_NOTFOUND;
}
IWineD3DSurface_GetParent(wined3d_surface, (IUnknown **)Surface);
TRACE("Returning surface %p.\n", Surface);
return DD_OK;
} }
/***************************************************************************** /*****************************************************************************

View file

@ -290,6 +290,7 @@ IDirectDrawImpl_CreateSurface(LPDIRECTDRAW This, LPDDSURFACEDESC pSDesc,
set_surf_version(impl, 1); set_surf_version(impl, 1);
IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw1(This)); IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw1(This));
impl->ifaceToRelease = NULL; impl->ifaceToRelease = NULL;
return hr; return hr;
} }
@ -309,11 +310,13 @@ IDirectDraw2Impl_CreateSurface(LPDIRECTDRAW2 This, LPDDSURFACEDESC pSDesc,
*ppSurface = NULL; *ppSurface = NULL;
return hr; return hr;
} }
impl = (IDirectDrawSurfaceImpl *)pSurface7; impl = (IDirectDrawSurfaceImpl *)pSurface7;
*ppSurface = (IDirectDrawSurface *)&impl->IDirectDrawSurface3_vtbl; *ppSurface = (IDirectDrawSurface *)&impl->IDirectDrawSurface3_vtbl;
set_surf_version(impl, 2); set_surf_version(impl, 2);
IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw2(This)); IDirectDraw7_Release((IDirectDraw7 *)ddraw_from_ddraw2(This));
impl->ifaceToRelease = NULL; impl->ifaceToRelease = NULL;
return hr; return hr;
} }

View file

@ -2409,22 +2409,60 @@ IDirect3DDeviceImpl_7_GetRenderState(IDirect3DDevice7 *iface,
case D3DRENDERSTATE_TEXTUREMIN: case D3DRENDERSTATE_TEXTUREMIN:
{ {
WINED3DTEXTUREFILTERTYPE tex_min; WINED3DTEXTUREFILTERTYPE tex_min;
WINED3DTEXTUREFILTERTYPE tex_mip;
hr = IWineD3DDevice_GetSamplerState(This->wineD3DDevice, hr = IWineD3DDevice_GetSamplerState(This->wineD3DDevice,
0, WINED3DSAMP_MINFILTER, 0, WINED3DSAMP_MINFILTER, &tex_min);
&tex_min); if (FAILED(hr))
{
LeaveCriticalSection(&ddraw_cs);
return hr;
}
hr = IWineD3DDevice_GetSamplerState(This->wineD3DDevice,
0, WINED3DSAMP_MIPFILTER, &tex_mip);
switch (tex_min) switch (tex_min)
{ {
case WINED3DTEXF_POINT: case WINED3DTEXF_POINT:
*Value = D3DFILTER_NEAREST; switch (tex_mip)
{
case WINED3DTEXF_NONE:
*Value = D3DFILTER_NEAREST;
break;
case WINED3DTEXF_POINT:
*Value = D3DFILTER_MIPNEAREST;
break;
case WINED3DTEXF_LINEAR:
*Value = D3DFILTER_LINEARMIPNEAREST;
break;
default:
ERR("Unhandled mip filter %#x.\n", tex_mip);
*Value = D3DFILTER_NEAREST;
break;
}
break; break;
case WINED3DTEXF_LINEAR: case WINED3DTEXF_LINEAR:
*Value = D3DFILTER_LINEAR; switch (tex_mip)
{
case WINED3DTEXF_NONE:
*Value = D3DFILTER_LINEAR;
break;
case WINED3DTEXF_POINT:
*Value = D3DFILTER_MIPLINEAR;
break;
case WINED3DTEXF_LINEAR:
*Value = D3DFILTER_LINEARMIPLINEAR;
break;
default:
ERR("Unhandled mip filter %#x.\n", tex_mip);
*Value = D3DFILTER_LINEAR;
break;
}
break; break;
default: default:
ERR("Unhandled texture mag %d !\n",tex_min); ERR("Unhandled texture min filter %#x.\n",tex_min);
*Value = 0; *Value = D3DFILTER_NEAREST;
break;
} }
break; break;
} }
@ -2441,8 +2479,20 @@ IDirect3DDeviceImpl_7_GetRenderState(IDirect3DDevice7 *iface,
Value); Value);
break; break;
case D3DRENDERSTATE_BORDERCOLOR:
FIXME("Unhandled render state D3DRENDERSTATE_BORDERCOLOR.\n");
hr = E_NOTIMPL;
break;
default: default:
/* FIXME: Unhandled: D3DRENDERSTATE_STIPPLEPATTERN00 - 31 */ if (RenderStateType >= D3DRENDERSTATE_STIPPLEPATTERN00
&& RenderStateType <= D3DRENDERSTATE_STIPPLEPATTERN31)
{
FIXME("Unhandled stipple pattern render state (%#x).\n",
RenderStateType);
hr = E_NOTIMPL;
break;
}
hr = IWineD3DDevice_GetRenderState(This->wineD3DDevice, hr = IWineD3DDevice_GetRenderState(This->wineD3DDevice,
RenderStateType, RenderStateType,
Value); Value);
@ -2640,22 +2690,39 @@ IDirect3DDeviceImpl_7_SetRenderState(IDirect3DDevice7 *iface,
/* Some render states need special care */ /* Some render states need special care */
switch(RenderStateType) switch(RenderStateType)
{ {
/*
* The ddraw texture filter mapping works like this:
* D3DFILTER_NEAREST Point min/mag, no mip
* D3DFILTER_MIPNEAREST Point min/mag, point mip
* D3DFILTER_LINEARMIPNEAREST: Point min/mag, linear mip
*
* D3DFILTER_LINEAR Linear min/mag, no mip
* D3DFILTER_MIPLINEAR Linear min/mag, point mip
* D3DFILTER_LINEARMIPLINEAR Linear min/mag, linear mip
*
* This is the opposite of the GL naming convention,
* D3DFILTER_LINEARMIPNEAREST corresponds to GL_NEAREST_MIPMAP_LINEAR.
*/
case D3DRENDERSTATE_TEXTUREMAG: case D3DRENDERSTATE_TEXTUREMAG:
{ {
WINED3DTEXTUREFILTERTYPE tex_mag = WINED3DTEXF_POINT; WINED3DTEXTUREFILTERTYPE tex_mag;
switch ((D3DTEXTUREFILTER) Value) switch (Value)
{ {
case D3DFILTER_NEAREST: case D3DFILTER_NEAREST:
case D3DFILTER_MIPNEAREST:
case D3DFILTER_LINEARMIPNEAREST: case D3DFILTER_LINEARMIPNEAREST:
tex_mag = WINED3DTEXF_POINT; tex_mag = WINED3DTEXF_POINT;
break; break;
case D3DFILTER_LINEAR: case D3DFILTER_LINEAR:
case D3DFILTER_MIPLINEAR:
case D3DFILTER_LINEARMIPLINEAR: case D3DFILTER_LINEARMIPLINEAR:
tex_mag = WINED3DTEXF_LINEAR; tex_mag = WINED3DTEXF_LINEAR;
break; break;
default: default:
tex_mag = WINED3DTEXF_POINT;
ERR("Unhandled texture mag %d !\n",Value); ERR("Unhandled texture mag %d !\n",Value);
break;
} }
hr = IWineD3DDevice_SetSamplerState(This->wineD3DDevice, hr = IWineD3DDevice_SetSamplerState(This->wineD3DDevice,
@ -2666,24 +2733,26 @@ IDirect3DDeviceImpl_7_SetRenderState(IDirect3DDevice7 *iface,
case D3DRENDERSTATE_TEXTUREMIN: case D3DRENDERSTATE_TEXTUREMIN:
{ {
WINED3DTEXTUREFILTERTYPE tex_min = WINED3DTEXF_POINT; WINED3DTEXTUREFILTERTYPE tex_min;
WINED3DTEXTUREFILTERTYPE tex_mip = WINED3DTEXF_NONE; WINED3DTEXTUREFILTERTYPE tex_mip;
switch ((D3DTEXTUREFILTER) Value) switch ((D3DTEXTUREFILTER) Value)
{ {
case D3DFILTER_NEAREST: case D3DFILTER_NEAREST:
tex_min = WINED3DTEXF_POINT; tex_min = WINED3DTEXF_POINT;
tex_mip = WINED3DTEXF_NONE;
break; break;
case D3DFILTER_LINEAR: case D3DFILTER_LINEAR:
tex_min = WINED3DTEXF_LINEAR; tex_min = WINED3DTEXF_LINEAR;
tex_mip = WINED3DTEXF_NONE;
break; break;
case D3DFILTER_MIPNEAREST: case D3DFILTER_MIPNEAREST:
tex_min = WINED3DTEXF_POINT; tex_min = WINED3DTEXF_POINT;
tex_mip = WINED3DTEXF_POINT; tex_mip = WINED3DTEXF_POINT;
break; break;
case D3DFILTER_MIPLINEAR: case D3DFILTER_MIPLINEAR:
tex_min = WINED3DTEXF_POINT; tex_min = WINED3DTEXF_LINEAR;
tex_mip = WINED3DTEXF_LINEAR; tex_mip = WINED3DTEXF_POINT;
break; break;
case D3DFILTER_LINEARMIPNEAREST: case D3DFILTER_LINEARMIPNEAREST:
tex_min = WINED3DTEXF_POINT; tex_min = WINED3DTEXF_POINT;
@ -2696,11 +2765,13 @@ IDirect3DDeviceImpl_7_SetRenderState(IDirect3DDevice7 *iface,
default: default:
ERR("Unhandled texture min %d !\n",Value); ERR("Unhandled texture min %d !\n",Value);
tex_min = WINED3DTEXF_POINT;
tex_mip = WINED3DTEXF_NONE;
break;
} }
IWineD3DDevice_SetSamplerState(This->wineD3DDevice, IWineD3DDevice_SetSamplerState(This->wineD3DDevice,
0, WINED3DSAMP_MIPFILTER, 0, WINED3DSAMP_MIPFILTER, tex_mip);
tex_mip);
hr = IWineD3DDevice_SetSamplerState(This->wineD3DDevice, hr = IWineD3DDevice_SetSamplerState(This->wineD3DDevice,
0, WINED3DSAMP_MINFILTER, 0, WINED3DSAMP_MINFILTER,
tex_min); tex_min);
@ -2723,9 +2794,22 @@ IDirect3DDeviceImpl_7_SetRenderState(IDirect3DDevice7 *iface,
Value); Value);
break; break;
default: case D3DRENDERSTATE_BORDERCOLOR:
/* This should probably just forward to the corresponding sampler
* state. Needs tests. */
FIXME("Unhandled render state D3DRENDERSTATE_BORDERCOLOR.\n");
hr = E_NOTIMPL;
break;
/* FIXME: Unhandled: D3DRENDERSTATE_STIPPLEPATTERN00 - 31 */ default:
if (RenderStateType >= D3DRENDERSTATE_STIPPLEPATTERN00
&& RenderStateType <= D3DRENDERSTATE_STIPPLEPATTERN31)
{
FIXME("Unhandled stipple pattern render state (%#x).\n",
RenderStateType);
hr = E_NOTIMPL;
break;
}
hr = IWineD3DDevice_SetRenderState(This->wineD3DDevice, hr = IWineD3DDevice_SetRenderState(This->wineD3DDevice,
RenderStateType, RenderStateType,

View file

@ -1273,6 +1273,7 @@ IDirect3DImpl_GetCaps(IWineD3D *WineD3D,
/* Copy the results into the d3d7 and d3d3 structures */ /* Copy the results into the d3d7 and d3d3 structures */
Desc7->dwDevCaps = WCaps.DevCaps; Desc7->dwDevCaps = WCaps.DevCaps;
Desc7->dpcLineCaps.dwMiscCaps = WCaps.PrimitiveMiscCaps;
Desc7->dpcLineCaps.dwRasterCaps = WCaps.RasterCaps; Desc7->dpcLineCaps.dwRasterCaps = WCaps.RasterCaps;
Desc7->dpcLineCaps.dwZCmpCaps = WCaps.ZCmpCaps; Desc7->dpcLineCaps.dwZCmpCaps = WCaps.ZCmpCaps;
Desc7->dpcLineCaps.dwSrcBlendCaps = WCaps.SrcBlendCaps; Desc7->dpcLineCaps.dwSrcBlendCaps = WCaps.SrcBlendCaps;

View file

@ -489,7 +489,7 @@ IDirect3DExecuteBufferImpl_Execute(IDirect3DExecuteBufferImpl *This,
memcpy(dst, src, ci->dwCount * sizeof(D3DTLVERTEX)); memcpy(dst, src, ci->dwCount * sizeof(D3DTLVERTEX));
} else { } else {
ERR("Unhandled vertex processing !\n"); ERR("Unhandled vertex processing flag %#x.\n", ci->dwFlags);
} }
instr += size; instr += size;
@ -703,7 +703,6 @@ IDirect3DExecuteBufferImpl_Lock(IDirect3DExecuteBuffer *iface,
TRACE("(%p)->(%p)\n", This, lpDesc); TRACE("(%p)->(%p)\n", This, lpDesc);
dwSize = lpDesc->dwSize; dwSize = lpDesc->dwSize;
memset(lpDesc, 0, dwSize);
memcpy(lpDesc, &This->desc, dwSize); memcpy(lpDesc, &This->desc, dwSize);
if (TRACE_ON(d3d7)) { if (TRACE_ON(d3d7)) {
@ -789,7 +788,6 @@ IDirect3DExecuteBufferImpl_GetExecuteData(IDirect3DExecuteBuffer *iface,
TRACE("(%p)->(%p): stub!\n", This, lpData); TRACE("(%p)->(%p): stub!\n", This, lpData);
dwSize = lpData->dwSize; dwSize = lpData->dwSize;
memset(lpData, 0, dwSize);
memcpy(lpData, &This->data, dwSize); memcpy(lpData, &This->data, dwSize);
if (TRACE_ON(d3d7)) { if (TRACE_ON(d3d7)) {

View file

@ -288,7 +288,7 @@ err_out:
/* Let's hope we never need this ;) */ /* Let's hope we never need this ;) */
if(wineD3DDevice) IWineD3DDevice_Release(wineD3DDevice); if(wineD3DDevice) IWineD3DDevice_Release(wineD3DDevice);
if(wineD3D) IWineD3D_Release(wineD3D); if(wineD3D) IWineD3D_Release(wineD3D);
if(This) HeapFree(GetProcessHeap(), 0, This->decls); HeapFree(GetProcessHeap(), 0, This->decls);
HeapFree(GetProcessHeap(), 0, This); HeapFree(GetProcessHeap(), 0, This);
return hr; return hr;
} }

View file

@ -294,7 +294,6 @@ IDirect3DMaterialImpl_GetMaterial(IDirect3DMaterial3 *iface,
/* Copies the material structure */ /* Copies the material structure */
EnterCriticalSection(&ddraw_cs); EnterCriticalSection(&ddraw_cs);
dwSize = lpMat->dwSize; dwSize = lpMat->dwSize;
memset(lpMat, 0, dwSize);
memcpy(lpMat, &This->mat, dwSize); memcpy(lpMat, &This->mat, dwSize);
LeaveCriticalSection(&ddraw_cs); LeaveCriticalSection(&ddraw_cs);

View file

@ -171,7 +171,7 @@ PixelFormat_WineD3DtoDD(DDPIXELFORMAT *DDPixelFormat,
DDPixelFormat->u2.dwRBitMask = 0x00E0; DDPixelFormat->u2.dwRBitMask = 0x00E0;
DDPixelFormat->u3.dwGBitMask = 0x001C; DDPixelFormat->u3.dwGBitMask = 0x001C;
DDPixelFormat->u4.dwBBitMask = 0x0003; DDPixelFormat->u4.dwBBitMask = 0x0003;
DDPixelFormat->u5.dwRGBAlphaBitMask = 0xF000; DDPixelFormat->u5.dwRGBAlphaBitMask = 0xFF00;
break; break;
case WINED3DFMT_B4G4R4X4_UNORM: case WINED3DFMT_B4G4R4X4_UNORM:
@ -182,7 +182,7 @@ PixelFormat_WineD3DtoDD(DDPIXELFORMAT *DDPixelFormat,
DDPixelFormat->u3.dwGBitMask = 0x00F0; DDPixelFormat->u3.dwGBitMask = 0x00F0;
DDPixelFormat->u4.dwBBitMask = 0x000F; DDPixelFormat->u4.dwBBitMask = 0x000F;
DDPixelFormat->u5.dwRGBAlphaBitMask = 0x0; DDPixelFormat->u5.dwRGBAlphaBitMask = 0x0;
return; break;
/* How are Z buffer bit depth and Stencil buffer bit depth related? /* How are Z buffer bit depth and Stencil buffer bit depth related?
*/ */
@ -236,8 +236,8 @@ PixelFormat_WineD3DtoDD(DDPIXELFORMAT *DDPixelFormat,
DDPixelFormat->u3.dwZBitMask = 0x00FFFFFFFF; DDPixelFormat->u3.dwZBitMask = 0x00FFFFFFFF;
DDPixelFormat->u4.dwStencilBitMask = 0x00000000; DDPixelFormat->u4.dwStencilBitMask = 0x00000000;
DDPixelFormat->u5.dwRGBAlphaBitMask = 0x0; DDPixelFormat->u5.dwRGBAlphaBitMask = 0x0;
break; break;
case WINED3DFMT_S1_UINT_D15_UNORM: case WINED3DFMT_S1_UINT_D15_UNORM:
DDPixelFormat->dwFlags = DDPF_ZBUFFER | DDPF_STENCILBUFFER; DDPixelFormat->dwFlags = DDPF_ZBUFFER | DDPF_STENCILBUFFER;
DDPixelFormat->dwFourCC = 0; DDPixelFormat->dwFourCC = 0;

File diff suppressed because it is too large Load diff

View file

@ -190,7 +190,6 @@ static const char *debug_mask(GLuint mask) {
default: return "Unexpected writemask"; default: return "Unexpected writemask";
} }
} }
#define GLINFO_LOCATION (*gl_info)
static void wrap_op1(const struct wined3d_gl_info *gl_info, GLuint op, GLuint dst, GLuint dstMask, GLuint dstMod, static void wrap_op1(const struct wined3d_gl_info *gl_info, GLuint op, GLuint dst, GLuint dstMask, GLuint dstMod,
GLuint arg1, GLuint arg1Rep, GLuint arg1Mod) GLuint arg1, GLuint arg1Rep, GLuint arg1Mod)
@ -796,11 +795,10 @@ static GLuint gen_ati_shader(const struct texture_stage_op op[MAX_TEXTURES], con
checkGLcall("GL_EXTCALL(glEndFragmentShaderATI())"); checkGLcall("GL_EXTCALL(glEndFragmentShaderATI())");
return ret; return ret;
} }
#undef GLINFO_LOCATION
#define GLINFO_LOCATION stateblock->device->adapter->gl_info
static void set_tex_op_atifs(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context) static void set_tex_op_atifs(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
{ {
const struct wined3d_gl_info *gl_info = context->gl_info;
IWineD3DDeviceImpl *This = stateblock->device; IWineD3DDeviceImpl *This = stateblock->device;
const struct atifs_ffp_desc *desc; const struct atifs_ffp_desc *desc;
struct ffp_frag_settings settings; struct ffp_frag_settings settings;
@ -818,14 +816,14 @@ static void set_tex_op_atifs(DWORD state, IWineD3DStateBlockImpl *stateblock, st
return; return;
} }
new_desc->num_textures_used = 0; new_desc->num_textures_used = 0;
for (i = 0; i < context->gl_info->limits.texture_stages; ++i) for (i = 0; i < gl_info->limits.texture_stages; ++i)
{ {
if(settings.op[i].cop == WINED3DTOP_DISABLE) break; if(settings.op[i].cop == WINED3DTOP_DISABLE) break;
new_desc->num_textures_used = i; new_desc->num_textures_used = i;
} }
memcpy(&new_desc->parent.settings, &settings, sizeof(settings)); memcpy(&new_desc->parent.settings, &settings, sizeof(settings));
new_desc->shader = gen_ati_shader(settings.op, context->gl_info); new_desc->shader = gen_ati_shader(settings.op, gl_info);
add_ffp_frag_shader(&priv->fragment_shaders, &new_desc->parent); add_ffp_frag_shader(&priv->fragment_shaders, &new_desc->parent);
TRACE("Allocated fixed function replacement shader descriptor %p\n", new_desc); TRACE("Allocated fixed function replacement shader descriptor %p\n", new_desc);
desc = new_desc; desc = new_desc;
@ -849,6 +847,7 @@ static void set_tex_op_atifs(DWORD state, IWineD3DStateBlockImpl *stateblock, st
static void state_texfactor_atifs(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context) static void state_texfactor_atifs(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
{ {
const struct wined3d_gl_info *gl_info = context->gl_info;
float col[4]; float col[4];
D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_TEXTUREFACTOR], col); D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_TEXTUREFACTOR], col);
@ -859,6 +858,7 @@ static void state_texfactor_atifs(DWORD state, IWineD3DStateBlockImpl *statebloc
static void set_bumpmat(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context) static void set_bumpmat(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
{ {
DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1); DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
const struct wined3d_gl_info *gl_info = context->gl_info;
float mat[2][2]; float mat[2][2];
mat[0][0] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT00]); mat[0][0] = *((float *) &stateblock->textureState[stage][WINED3DTSS_BUMPENVMAT00]);
@ -907,127 +907,124 @@ static void atifs_apply_pixelshader(DWORD state, IWineD3DStateBlockImpl *statebl
if(!isStateDirty(context, device->StateTable[STATE_VSHADER].representative)) { if(!isStateDirty(context, device->StateTable[STATE_VSHADER].representative)) {
device->shader_backend->shader_select(context, FALSE, use_vshader); device->shader_backend->shader_select(context, FALSE, use_vshader);
if (!isStateDirty(context, STATE_VERTEXSHADERCONSTANT) && use_vshader) { if (!isStateDirty(context, STATE_VERTEXSHADERCONSTANT) && use_vshader)
device->StateTable[STATE_VERTEXSHADERCONSTANT].apply(STATE_VERTEXSHADERCONSTANT, stateblock, context); stateblock_apply_state(STATE_VERTEXSHADERCONSTANT, stateblock, context);
}
} }
} }
#undef GLINFO_LOCATION
static const struct StateEntryTemplate atifs_fragmentstate_template[] = { 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_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 }, {STATE_RENDER(WINED3DRS_FOGCOLOR), { STATE_RENDER(WINED3DRS_FOGCOLOR), state_fogcolor }, WINED3D_GL_EXT_NONE },
{STATE_RENDER(WINED3DRS_FOGDENSITY), { STATE_RENDER(WINED3DRS_FOGDENSITY), state_fogdensity }, WINED3D_GL_EXT_NONE }, {STATE_RENDER(WINED3DRS_FOGDENSITY), { STATE_RENDER(WINED3DRS_FOGDENSITY), state_fogdensity }, WINED3D_GL_EXT_NONE },
{STATE_RENDER(WINED3DRS_FOGENABLE), { STATE_RENDER(WINED3DRS_FOGENABLE), state_fog_fragpart }, WINED3D_GL_EXT_NONE }, {STATE_RENDER(WINED3DRS_FOGENABLE), { STATE_RENDER(WINED3DRS_FOGENABLE), state_fog_fragpart }, WINED3D_GL_EXT_NONE },
{STATE_RENDER(WINED3DRS_FOGTABLEMODE), { STATE_RENDER(WINED3DRS_FOGENABLE), state_fog_fragpart }, WINED3D_GL_EXT_NONE }, {STATE_RENDER(WINED3DRS_FOGTABLEMODE), { STATE_RENDER(WINED3DRS_FOGENABLE), NULL }, WINED3D_GL_EXT_NONE },
{STATE_RENDER(WINED3DRS_FOGVERTEXMODE), { STATE_RENDER(WINED3DRS_FOGENABLE), state_fog_fragpart }, WINED3D_GL_EXT_NONE }, {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_FOGSTART), { STATE_RENDER(WINED3DRS_FOGSTART), state_fogstartend }, WINED3D_GL_EXT_NONE },
{STATE_RENDER(WINED3DRS_FOGEND), { STATE_RENDER(WINED3DRS_FOGSTART), state_fogstartend }, WINED3D_GL_EXT_NONE }, {STATE_RENDER(WINED3DRS_FOGEND), { STATE_RENDER(WINED3DRS_FOGSTART), NULL }, 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_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG1), { 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), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), set_tex_op_atifs }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), set_bumpmat }, WINED3D_GL_EXT_NONE }, {STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_SAMPLER(0), { STATE_SAMPLER(0), sampler_texdim }, WINED3D_GL_EXT_NONE }, { STATE_SAMPLER(0), { STATE_SAMPLER(0), sampler_texdim }, WINED3D_GL_EXT_NONE },
{ STATE_SAMPLER(1), { STATE_SAMPLER(1), sampler_texdim }, WINED3D_GL_EXT_NONE }, { STATE_SAMPLER(1), { STATE_SAMPLER(1), sampler_texdim }, WINED3D_GL_EXT_NONE },
{ STATE_SAMPLER(2), { STATE_SAMPLER(2), sampler_texdim }, WINED3D_GL_EXT_NONE }, { STATE_SAMPLER(2), { STATE_SAMPLER(2), sampler_texdim }, WINED3D_GL_EXT_NONE },
@ -1063,6 +1060,7 @@ static void atifs_enable(IWineD3DDevice *iface, BOOL enable) {
static void atifs_get_caps(const struct wined3d_gl_info *gl_info, struct fragment_caps *caps) static void atifs_get_caps(const struct wined3d_gl_info *gl_info, struct fragment_caps *caps)
{ {
caps->PrimitiveMiscCaps = WINED3DPMISCCAPS_TSSARGTEMP;
caps->TextureOpCaps = WINED3DTEXOPCAPS_DISABLE | caps->TextureOpCaps = WINED3DTEXOPCAPS_DISABLE |
WINED3DTEXOPCAPS_SELECTARG1 | WINED3DTEXOPCAPS_SELECTARG1 |
WINED3DTEXOPCAPS_SELECTARG2 | WINED3DTEXOPCAPS_SELECTARG2 |
@ -1105,8 +1103,6 @@ static void atifs_get_caps(const struct wined3d_gl_info *gl_info, struct fragmen
*/ */
caps->MaxTextureBlendStages = 8; caps->MaxTextureBlendStages = 8;
caps->MaxSimultaneousTextures = 6; caps->MaxSimultaneousTextures = 6;
caps->PrimitiveMiscCaps |= WINED3DPMISCCAPS_TSSARGTEMP;
} }
static HRESULT atifs_alloc(IWineD3DDevice *iface) { static HRESULT atifs_alloc(IWineD3DDevice *iface) {
@ -1128,11 +1124,11 @@ static HRESULT atifs_alloc(IWineD3DDevice *iface) {
return WINED3D_OK; return WINED3D_OK;
} }
#define GLINFO_LOCATION This->adapter->gl_info
/* Context activation is done by the caller. */ /* Context activation is done by the caller. */
static void atifs_free_ffpshader(struct wine_rb_entry *entry, void *context) static void atifs_free_ffpshader(struct wine_rb_entry *entry, void *context)
{ {
IWineD3DDeviceImpl *This = context; IWineD3DDeviceImpl *This = context;
const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
struct atifs_ffp_desc *entry_ati = WINE_RB_ENTRY_VALUE(entry, struct atifs_ffp_desc, parent.entry); struct atifs_ffp_desc *entry_ati = WINE_RB_ENTRY_VALUE(entry, struct atifs_ffp_desc, parent.entry);
ENTER_GL(); ENTER_GL();
@ -1152,7 +1148,6 @@ static void atifs_free(IWineD3DDevice *iface) {
HeapFree(GetProcessHeap(), 0, priv); HeapFree(GetProcessHeap(), 0, priv);
This->fragment_priv = NULL; This->fragment_priv = NULL;
} }
#undef GLINFO_LOCATION
static BOOL atifs_color_fixup_supported(struct color_fixup_desc fixup) static BOOL atifs_color_fixup_supported(struct color_fixup_desc fixup)
{ {

View file

@ -27,9 +27,10 @@
WINE_DEFAULT_DEBUG_CHANNEL(d3d_texture); WINE_DEFAULT_DEBUG_CHANNEL(d3d_texture);
HRESULT basetexture_init(IWineD3DBaseTextureImpl *texture, UINT levels, WINED3DRESOURCETYPE resource_type, HRESULT basetexture_init(IWineD3DBaseTextureImpl *texture, UINT layer_count, UINT level_count,
IWineD3DDeviceImpl *device, UINT size, DWORD usage, const struct GlPixelFormatDesc *format_desc, WINED3DRESOURCETYPE resource_type, IWineD3DDeviceImpl *device, UINT size, DWORD usage,
WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) const struct wined3d_format_desc *format_desc, WINED3DPOOL pool, IUnknown *parent,
const struct wined3d_parent_ops *parent_ops)
{ {
HRESULT hr; HRESULT hr;
@ -41,7 +42,17 @@ HRESULT basetexture_init(IWineD3DBaseTextureImpl *texture, UINT levels, WINED3DR
return hr; return hr;
} }
texture->baseTexture.levels = levels; texture->baseTexture.sub_resources = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY,
level_count * layer_count * sizeof(*texture->baseTexture.sub_resources));
if (!texture->baseTexture.sub_resources)
{
ERR("Failed to allocate sub-resource array.\n");
resource_cleanup((IWineD3DResource *)texture);
return E_OUTOFMEMORY;
}
texture->baseTexture.layer_count = layer_count;
texture->baseTexture.level_count = level_count;
texture->baseTexture.filterType = (usage & WINED3DUSAGE_AUTOGENMIPMAP) ? WINED3DTEXF_LINEAR : WINED3DTEXF_NONE; texture->baseTexture.filterType = (usage & WINED3DUSAGE_AUTOGENMIPMAP) ? WINED3DTEXF_LINEAR : WINED3DTEXF_NONE;
texture->baseTexture.LOD = 0; texture->baseTexture.LOD = 0;
texture->baseTexture.texture_rgb.dirty = TRUE; texture->baseTexture.texture_rgb.dirty = TRUE;
@ -66,9 +77,27 @@ HRESULT basetexture_init(IWineD3DBaseTextureImpl *texture, UINT levels, WINED3DR
void basetexture_cleanup(IWineD3DBaseTexture *iface) void basetexture_cleanup(IWineD3DBaseTexture *iface)
{ {
basetexture_unload(iface); basetexture_unload(iface);
HeapFree(GetProcessHeap(), 0, ((IWineD3DBaseTextureImpl *)iface)->baseTexture.sub_resources);
resource_cleanup((IWineD3DResource *)iface); resource_cleanup((IWineD3DResource *)iface);
} }
IWineD3DResourceImpl *basetexture_get_sub_resource(IWineD3DBaseTextureImpl *texture, UINT layer, UINT level)
{
if (layer >= texture->baseTexture.layer_count)
{
WARN("layer %u >= layer_count %u.\n", layer, texture->baseTexture.layer_count);
return NULL;
}
if (level >= texture->baseTexture.level_count)
{
WARN("level %u >= level_count %u.\n", level, texture->baseTexture.level_count);
return NULL;
}
return texture->baseTexture.sub_resources[layer * texture->baseTexture.level_count + level];
}
/* A GL context is provided by the caller */ /* A GL context is provided by the caller */
static void gltexture_delete(struct gl_texture *tex) static void gltexture_delete(struct gl_texture *tex)
{ {
@ -86,7 +115,7 @@ void basetexture_unload(IWineD3DBaseTexture *iface)
if (This->baseTexture.texture_rgb.name || This->baseTexture.texture_srgb.name) if (This->baseTexture.texture_rgb.name || This->baseTexture.texture_srgb.name)
{ {
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
} }
if(This->baseTexture.texture_rgb.name) { if(This->baseTexture.texture_rgb.name) {
@ -115,8 +144,8 @@ DWORD basetexture_set_lod(IWineD3DBaseTexture *iface, DWORD LODNew)
return 0; return 0;
} }
if(LODNew >= This->baseTexture.levels) if (LODNew >= This->baseTexture.level_count)
LODNew = This->baseTexture.levels - 1; LODNew = This->baseTexture.level_count - 1;
if(This->baseTexture.LOD != LODNew) { if(This->baseTexture.LOD != LODNew) {
This->baseTexture.LOD = LODNew; This->baseTexture.LOD = LODNew;
@ -145,8 +174,8 @@ DWORD basetexture_get_lod(IWineD3DBaseTexture *iface)
DWORD basetexture_get_level_count(IWineD3DBaseTexture *iface) DWORD basetexture_get_level_count(IWineD3DBaseTexture *iface)
{ {
IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface; IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
TRACE("(%p) : returning %d\n", This, This->baseTexture.levels); TRACE("iface %p, returning %u.\n", iface, This->baseTexture.level_count);
return This->baseTexture.levels; return This->baseTexture.level_count;
} }
HRESULT basetexture_set_autogen_filter_type(IWineD3DBaseTexture *iface, WINED3DTEXTUREFILTERTYPE FilterType) HRESULT basetexture_set_autogen_filter_type(IWineD3DBaseTexture *iface, WINED3DTEXTUREFILTERTYPE FilterType)
@ -164,7 +193,7 @@ HRESULT basetexture_set_autogen_filter_type(IWineD3DBaseTexture *iface, WINED3DT
* Or should we delay the applying until the texture is used for drawing? For now, apply * Or should we delay the applying until the texture is used for drawing? For now, apply
* immediately. * immediately.
*/ */
struct wined3d_context *context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); struct wined3d_context *context = context_acquire(device, NULL);
ENTER_GL(); ENTER_GL();
glBindTexture(textureDimensions, This->baseTexture.texture_rgb.name); glBindTexture(textureDimensions, This->baseTexture.texture_rgb.name);
@ -270,9 +299,7 @@ HRESULT basetexture_bind(IWineD3DBaseTexture *iface, BOOL srgb, BOOL *set_surfac
gl_tex->states[WINED3DTEXSTA_MAXMIPLEVEL] = 0; gl_tex->states[WINED3DTEXSTA_MAXMIPLEVEL] = 0;
gl_tex->states[WINED3DTEXSTA_MAXANISOTROPY] = 1; gl_tex->states[WINED3DTEXSTA_MAXANISOTROPY] = 1;
gl_tex->states[WINED3DTEXSTA_SRGBTEXTURE] = 0; gl_tex->states[WINED3DTEXSTA_SRGBTEXTURE] = 0;
gl_tex->states[WINED3DTEXSTA_ELEMENTINDEX] = 0; gl_tex->states[WINED3DTEXSTA_SHADOW] = FALSE;
gl_tex->states[WINED3DTEXSTA_DMAPOFFSET] = 0;
gl_tex->states[WINED3DTEXSTA_TSSADDRESSW] = WINED3DTADDRESS_WRAP;
IWineD3DBaseTexture_SetDirty(iface, TRUE); IWineD3DBaseTexture_SetDirty(iface, TRUE);
isNewTexture = TRUE; isNewTexture = TRUE;
@ -301,10 +328,11 @@ HRESULT basetexture_bind(IWineD3DBaseTexture *iface, BOOL srgb, BOOL *set_surfac
* relying on the partial GL_ARB_texture_non_power_of_two emulation with texture rectangles * relying on the partial GL_ARB_texture_non_power_of_two emulation with texture rectangles
* (ie, do not care for cond_np2 here, just look for GL_TEXTURE_RECTANGLE_ARB) * (ie, do not care for cond_np2 here, just look for GL_TEXTURE_RECTANGLE_ARB)
*/ */
if(textureDimensions != GL_TEXTURE_RECTANGLE_ARB) { if (textureDimensions != GL_TEXTURE_RECTANGLE_ARB)
TRACE("Setting GL_TEXTURE_MAX_LEVEL to %d\n", This->baseTexture.levels - 1); {
glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.levels - 1); TRACE("Setting GL_TEXTURE_MAX_LEVEL to %u.\n", This->baseTexture.level_count - 1);
checkGLcall("glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.levels)"); glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.level_count - 1);
checkGLcall("glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.level_count)");
} }
if(textureDimensions==GL_TEXTURE_CUBE_MAP_ARB) { if(textureDimensions==GL_TEXTURE_CUBE_MAP_ARB) {
/* Cubemaps are always set to clamp, regardless of the sampler state. */ /* Cubemaps are always set to clamp, regardless of the sampler state. */
@ -444,17 +472,18 @@ void basetexture_apply_state_changes(IWineD3DBaseTexture *iface,
glTexParameteri(textureDimensions, GL_TEXTURE_MIN_FILTER, glValue); glTexParameteri(textureDimensions, GL_TEXTURE_MIN_FILTER, glValue);
checkGLcall("glTexParameter GL_TEXTURE_MIN_FILTER, ..."); checkGLcall("glTexParameter GL_TEXTURE_MIN_FILTER, ...");
if(!cond_np2) { if (!cond_np2)
if(gl_tex->states[WINED3DTEXSTA_MIPFILTER] == WINED3DTEXF_NONE) { {
if (gl_tex->states[WINED3DTEXSTA_MIPFILTER] == WINED3DTEXF_NONE)
glValue = This->baseTexture.LOD; glValue = This->baseTexture.LOD;
} else if(gl_tex->states[WINED3DTEXSTA_MAXMIPLEVEL] >= This->baseTexture.levels) { else if (gl_tex->states[WINED3DTEXSTA_MAXMIPLEVEL] >= This->baseTexture.level_count)
glValue = This->baseTexture.levels - 1; glValue = This->baseTexture.level_count - 1;
} else if(gl_tex->states[WINED3DTEXSTA_MAXMIPLEVEL] < This->baseTexture.LOD) { else if (gl_tex->states[WINED3DTEXSTA_MAXMIPLEVEL] < This->baseTexture.LOD)
/* baseTexture.LOD is already clamped in the setter */ /* baseTexture.LOD is already clamped in the setter */
glValue = This->baseTexture.LOD; glValue = This->baseTexture.LOD;
} else { else
glValue = gl_tex->states[WINED3DTEXSTA_MAXMIPLEVEL]; glValue = gl_tex->states[WINED3DTEXSTA_MAXMIPLEVEL];
}
/* Note that D3DSAMP_MAXMIPLEVEL specifies the biggest mipmap(default 0), while /* Note that D3DSAMP_MAXMIPLEVEL specifies the biggest mipmap(default 0), while
* GL_TEXTURE_MAX_LEVEL specifies the smallest mimap used(default 1000). * GL_TEXTURE_MAX_LEVEL specifies the smallest mimap used(default 1000).
* So D3DSAMP_MAXMIPLEVEL is the same as GL_TEXTURE_BASE_LEVEL. * So D3DSAMP_MAXMIPLEVEL is the same as GL_TEXTURE_BASE_LEVEL.
@ -488,4 +517,22 @@ void basetexture_apply_state_changes(IWineD3DBaseTexture *iface,
} }
gl_tex->states[WINED3DTEXSTA_MAXANISOTROPY] = aniso; gl_tex->states[WINED3DTEXSTA_MAXANISOTROPY] = aniso;
} }
if (!(This->resource.format_desc->Flags & WINED3DFMT_FLAG_SHADOW)
!= !gl_tex->states[WINED3DTEXSTA_SHADOW])
{
if (This->resource.format_desc->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);
checkGLcall("glTexParameteri(textureDimensions, GL_TEXTURE_COMPARE_MODE_ARB, GL_COMPARE_R_TO_TEXTURE_ARB)");
gl_tex->states[WINED3DTEXSTA_SHADOW] = TRUE;
}
else
{
glTexParameteri(textureDimensions, GL_TEXTURE_COMPARE_MODE_ARB, GL_NONE);
checkGLcall("glTexParameteri(textureDimensions, GL_TEXTURE_COMPARE_MODE_ARB, GL_NONE)");
gl_tex->states[WINED3DTEXSTA_SHADOW] = FALSE;
}
}
} }

View file

@ -29,8 +29,6 @@
WINE_DEFAULT_DEBUG_CHANNEL(d3d); WINE_DEFAULT_DEBUG_CHANNEL(d3d);
#define GLINFO_LOCATION This->resource.device->adapter->gl_info
#define VB_MAXDECLCHANGES 100 /* After that number of decl changes we stop converting */ #define VB_MAXDECLCHANGES 100 /* After that number of decl changes we stop converting */
#define VB_RESETDECLCHANGE 1000 /* Reset the decl changecount after that number of draws */ #define VB_RESETDECLCHANGE 1000 /* Reset the decl changecount after that number of draws */
#define VB_MAXFULLCONVERSIONS 5 /* Number of full conversions before we stop converting */ #define VB_MAXFULLCONVERSIONS 5 /* Number of full conversions before we stop converting */
@ -97,11 +95,29 @@ static inline BOOL buffer_is_fully_dirty(struct wined3d_buffer *This)
return FALSE; return FALSE;
} }
/* Context activation is done by the caller */
static void delete_gl_buffer(struct wined3d_buffer *This, const struct wined3d_gl_info *gl_info)
{
if(!This->buffer_object) return;
ENTER_GL();
GL_EXTCALL(glDeleteBuffersARB(1, &This->buffer_object));
checkGLcall("glDeleteBuffersARB");
LEAVE_GL();
This->buffer_object = 0;
if(This->query)
{
wined3d_event_query_destroy(This->query);
This->query = NULL;
}
This->flags &= ~WINED3D_BUFFER_APPLESYNC;
}
/* Context activation is done by the caller. */ /* Context activation is done by the caller. */
static void buffer_create_buffer_object(struct wined3d_buffer *This) static void buffer_create_buffer_object(struct wined3d_buffer *This, const struct wined3d_gl_info *gl_info)
{ {
GLenum error, gl_usage; GLenum error, gl_usage;
const struct wined3d_gl_info *gl_info = &This->resource.device->adapter->gl_info;
TRACE("Creating an OpenGL vertex buffer object for IWineD3DVertexBuffer %p Usage(%s)\n", TRACE("Creating an OpenGL vertex buffer object for IWineD3DVertexBuffer %p Usage(%s)\n",
This, debug_d3dusage(This->resource.usage)); This, debug_d3dusage(This->resource.usage));
@ -157,6 +173,10 @@ static void buffer_create_buffer_object(struct wined3d_buffer *This)
GL_EXTCALL(glBufferParameteriAPPLE(This->buffer_type_hint, GL_BUFFER_FLUSHING_UNMAP_APPLE, GL_FALSE)); GL_EXTCALL(glBufferParameteriAPPLE(This->buffer_type_hint, GL_BUFFER_FLUSHING_UNMAP_APPLE, GL_FALSE));
checkGLcall("glBufferParameteriAPPLE(This->buffer_type_hint, GL_BUFFER_FLUSHING_UNMAP_APPLE, GL_FALSE)"); checkGLcall("glBufferParameteriAPPLE(This->buffer_type_hint, GL_BUFFER_FLUSHING_UNMAP_APPLE, GL_FALSE)");
This->flags |= WINED3D_BUFFER_FLUSH; This->flags |= WINED3D_BUFFER_FLUSH;
GL_EXTCALL(glBufferParameteriAPPLE(This->buffer_type_hint, GL_BUFFER_SERIALIZED_MODIFY_APPLE, GL_FALSE));
checkGLcall("glBufferParameteriAPPLE(This->buffer_type_hint, GL_BUFFER_SERIALIZED_MODIFY_APPLE, GL_FALSE)");
This->flags |= WINED3D_BUFFER_APPLESYNC;
} }
/* No setup is needed here for GL_ARB_map_buffer_range */ /* No setup is needed here for GL_ARB_map_buffer_range */
} }
@ -203,13 +223,7 @@ static void buffer_create_buffer_object(struct wined3d_buffer *This)
fail: fail:
/* Clean up all vbo init, but continue because we can work without a vbo :-) */ /* Clean up all vbo init, but continue because we can work without a vbo :-) */
ERR("Failed to create a vertex buffer object. Continuing, but performance issues may occur\n"); ERR("Failed to create a vertex buffer object. Continuing, but performance issues may occur\n");
if (This->buffer_object) delete_gl_buffer(This, gl_info);
{
ENTER_GL();
GL_EXTCALL(glDeleteBuffersARB(1, &This->buffer_object));
LEAVE_GL();
}
This->buffer_object = 0;
buffer_clear_dirty_areas(This); buffer_clear_dirty_areas(This);
} }
@ -258,12 +272,13 @@ static BOOL buffer_process_converted_attribute(struct wined3d_buffer *This,
attrib_size = attrib->format_desc->component_count * attrib->format_desc->component_size; attrib_size = attrib->format_desc->component_count * attrib->format_desc->component_size;
for (i = 0; i < attrib_size; ++i) for (i = 0; i < attrib_size; ++i)
{ {
if (This->conversion_map[data + i] != conversion_type) DWORD_PTR idx = (data + i) % This->stride;
if (This->conversion_map[idx] != conversion_type)
{ {
TRACE("Byte %ld in vertex changed\n", i + data); TRACE("Byte %ld in vertex changed\n", idx);
TRACE("It was type %d, is %d now\n", This->conversion_map[data + i], conversion_type); TRACE("It was type %d, is %d now\n", This->conversion_map[idx], conversion_type);
ret = TRUE; ret = TRUE;
This->conversion_map[data + i] = conversion_type; This->conversion_map[idx] = conversion_type;
} }
} }
@ -534,7 +549,7 @@ static BOOL buffer_find_decl(struct wined3d_buffer *This)
} }
/* Context activation is done by the caller. */ /* Context activation is done by the caller. */
static void buffer_check_buffer_object_size(struct wined3d_buffer *This) static void buffer_check_buffer_object_size(struct wined3d_buffer *This, const struct wined3d_gl_info *gl_info)
{ {
UINT size = This->conversion_stride ? UINT size = This->conversion_stride ?
This->conversion_stride * (This->resource.size / This->stride) : This->resource.size; This->conversion_stride * (This->resource.size / This->stride) : This->resource.size;
@ -550,7 +565,7 @@ static void buffer_check_buffer_object_size(struct wined3d_buffer *This)
/* Rescue the data before resizing the buffer object if we do not have our backup copy */ /* Rescue the data before resizing the buffer object if we do not have our backup copy */
if(!(This->flags & WINED3D_BUFFER_DOUBLEBUFFER)) if(!(This->flags & WINED3D_BUFFER_DOUBLEBUFFER))
{ {
buffer_get_sysmem(This); buffer_get_sysmem(This, gl_info);
} }
ENTER_GL(); ENTER_GL();
@ -595,7 +610,7 @@ static inline void fixup_transformed_pos(float *p)
} }
/* Context activation is done by the caller. */ /* Context activation is done by the caller. */
const BYTE *buffer_get_memory(IWineD3DBuffer *iface, UINT offset, GLuint *buffer_object) const BYTE *buffer_get_memory(IWineD3DBuffer *iface, const struct wined3d_gl_info *gl_info, GLuint *buffer_object)
{ {
struct wined3d_buffer *This = (struct wined3d_buffer *)iface; struct wined3d_buffer *This = (struct wined3d_buffer *)iface;
@ -604,19 +619,19 @@ const BYTE *buffer_get_memory(IWineD3DBuffer *iface, UINT offset, GLuint *buffer
{ {
if (This->flags & WINED3D_BUFFER_CREATEBO) if (This->flags & WINED3D_BUFFER_CREATEBO)
{ {
buffer_create_buffer_object(This); buffer_create_buffer_object(This, gl_info);
This->flags &= ~WINED3D_BUFFER_CREATEBO; This->flags &= ~WINED3D_BUFFER_CREATEBO;
if (This->buffer_object) if (This->buffer_object)
{ {
*buffer_object = This->buffer_object; *buffer_object = This->buffer_object;
return (const BYTE *)offset; return NULL;
} }
} }
return This->resource.allocatedMemory + offset; return This->resource.allocatedMemory;
} }
else else
{ {
return (const BYTE *)offset; return NULL;
} }
} }
@ -655,7 +670,7 @@ static ULONG STDMETHODCALLTYPE buffer_AddRef(IWineD3DBuffer *iface)
} }
/* Context activation is done by the caller. */ /* Context activation is done by the caller. */
BYTE *buffer_get_sysmem(struct wined3d_buffer *This) BYTE *buffer_get_sysmem(struct wined3d_buffer *This, const struct wined3d_gl_info *gl_info)
{ {
/* AllocatedMemory exists if the buffer is double buffered or has no buffer object at all */ /* AllocatedMemory exists if the buffer is double buffered or has no buffer object at all */
if(This->resource.allocatedMemory) return This->resource.allocatedMemory; if(This->resource.allocatedMemory) return This->resource.allocatedMemory;
@ -682,20 +697,16 @@ static void STDMETHODCALLTYPE buffer_UnLoad(IWineD3DBuffer *iface)
IWineD3DDeviceImpl *device = This->resource.device; IWineD3DDeviceImpl *device = This->resource.device;
struct wined3d_context *context; struct wined3d_context *context;
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
/* Download the buffer, but don't permanently enable double buffering */ /* Download the buffer, but don't permanently enable double buffering */
if(!(This->flags & WINED3D_BUFFER_DOUBLEBUFFER)) if(!(This->flags & WINED3D_BUFFER_DOUBLEBUFFER))
{ {
buffer_get_sysmem(This); buffer_get_sysmem(This, context->gl_info);
This->flags &= ~WINED3D_BUFFER_DOUBLEBUFFER; This->flags &= ~WINED3D_BUFFER_DOUBLEBUFFER;
} }
ENTER_GL(); delete_gl_buffer(This, context->gl_info);
GL_EXTCALL(glDeleteBuffersARB(1, &This->buffer_object));
checkGLcall("glDeleteBuffersARB");
LEAVE_GL();
This->buffer_object = 0;
This->flags |= WINED3D_BUFFER_CREATEBO; /* Recreate the buffer object next load */ This->flags |= WINED3D_BUFFER_CREATEBO; /* Recreate the buffer object next load */
buffer_clear_dirty_areas(This); buffer_clear_dirty_areas(This);
@ -766,26 +777,171 @@ static DWORD STDMETHODCALLTYPE buffer_GetPriority(IWineD3DBuffer *iface)
return resource_get_priority((IWineD3DResource *)iface); return resource_get_priority((IWineD3DResource *)iface);
} }
/* The caller provides a context and binds the buffer */
static void buffer_sync_apple(struct wined3d_buffer *This, DWORD flags, const struct wined3d_gl_info *gl_info)
{
enum wined3d_event_query_result ret;
/* No fencing needs to be done if the app promises not to overwrite
* existing data */
if(flags & WINED3DLOCK_NOOVERWRITE) return;
if(flags & WINED3DLOCK_DISCARD)
{
ENTER_GL();
GL_EXTCALL(glBufferDataARB(This->buffer_type_hint, This->resource.size, NULL, This->buffer_object_usage));
checkGLcall("glBufferDataARB\n");
LEAVE_GL();
return;
}
if(!This->query)
{
TRACE("Creating event query for buffer %p\n", This);
if (!wined3d_event_query_supported(gl_info))
{
FIXME("Event queries not supported, dropping async buffer locks.\n");
goto drop_query;
}
This->query = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*This->query));
if (!This->query)
{
ERR("Failed to allocate event query memory, dropping async buffer locks.\n");
goto drop_query;
}
/* Since we don't know about old draws a glFinish is needed once */
wglFinish();
return;
}
TRACE("Synchronizing buffer %p\n", This);
ret = wined3d_event_query_finish(This->query, This->resource.device);
switch(ret)
{
case WINED3D_EVENT_QUERY_NOT_STARTED:
case WINED3D_EVENT_QUERY_OK:
/* All done */
return;
case WINED3D_EVENT_QUERY_WRONG_THREAD:
WARN("Cannot synchronize buffer lock due to a thread conflict\n");
goto drop_query;
default:
ERR("wined3d_event_query_finish returned %u, dropping async buffer locks\n", ret);
goto drop_query;
}
drop_query:
if(This->query)
{
wined3d_event_query_destroy(This->query);
This->query = NULL;
}
wglFinish();
ENTER_GL();
GL_EXTCALL(glBufferParameteriAPPLE(This->buffer_type_hint, GL_BUFFER_SERIALIZED_MODIFY_APPLE, GL_TRUE));
checkGLcall("glBufferParameteriAPPLE(This->buffer_type_hint, GL_BUFFER_SERIALIZED_MODIFY_APPLE, GL_TRUE)");
LEAVE_GL();
This->flags &= ~WINED3D_BUFFER_APPLESYNC;
}
/* The caller provides a GL context */
static void buffer_direct_upload(struct wined3d_buffer *This, const struct wined3d_gl_info *gl_info, DWORD flags)
{
BYTE *map;
UINT start = 0, len = 0;
ENTER_GL();
GL_EXTCALL(glBindBufferARB(This->buffer_type_hint, This->buffer_object));
checkGLcall("glBindBufferARB");
if (gl_info->supported[ARB_MAP_BUFFER_RANGE])
{
GLbitfield mapflags;
mapflags = GL_MAP_WRITE_BIT | GL_MAP_FLUSH_EXPLICIT_BIT;
if (flags & WINED3D_BUFFER_DISCARD)
{
mapflags |= GL_MAP_UNSYNCHRONIZED_BIT | GL_MAP_INVALIDATE_BUFFER_BIT;
}
else if (flags & WINED3D_BUFFER_NOSYNC)
{
mapflags |= GL_MAP_UNSYNCHRONIZED_BIT;
}
map = GL_EXTCALL(glMapBufferRange(This->buffer_type_hint, 0,
This->resource.size, mapflags));
checkGLcall("glMapBufferRange");
}
else
{
if (This->flags & WINED3D_BUFFER_APPLESYNC)
{
DWORD syncflags = 0;
if (flags & WINED3D_BUFFER_DISCARD) syncflags |= WINED3DLOCK_DISCARD;
if (flags & WINED3D_BUFFER_NOSYNC) syncflags |= WINED3DLOCK_NOOVERWRITE;
LEAVE_GL();
buffer_sync_apple(This, syncflags, gl_info);
ENTER_GL();
}
map = GL_EXTCALL(glMapBufferARB(This->buffer_type_hint, GL_WRITE_ONLY_ARB));
checkGLcall("glMapBufferARB");
}
if (!map)
{
LEAVE_GL();
ERR("Failed to map opengl buffer\n");
return;
}
while(This->modified_areas)
{
This->modified_areas--;
start = This->maps[This->modified_areas].offset;
len = This->maps[This->modified_areas].size;
memcpy(map + start, This->resource.allocatedMemory + start, len);
if (gl_info->supported[ARB_MAP_BUFFER_RANGE])
{
GL_EXTCALL(glFlushMappedBufferRange(This->buffer_type_hint, start, len));
checkGLcall("glFlushMappedBufferRange");
}
else if (This->flags & WINED3D_BUFFER_FLUSH)
{
GL_EXTCALL(glFlushMappedBufferRangeAPPLE(This->buffer_type_hint, start, len));
checkGLcall("glFlushMappedBufferRangeAPPLE");
}
}
GL_EXTCALL(glUnmapBufferARB(This->buffer_type_hint));
checkGLcall("glUnmapBufferARB");
LEAVE_GL();
}
static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface) static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface)
{ {
struct wined3d_buffer *This = (struct wined3d_buffer *)iface; struct wined3d_buffer *This = (struct wined3d_buffer *)iface;
IWineD3DDeviceImpl *device = This->resource.device; IWineD3DDeviceImpl *device = This->resource.device;
UINT start = 0, end = 0, len = 0, vertices; UINT start = 0, end = 0, len = 0, vertices;
const struct wined3d_gl_info *gl_info;
struct wined3d_context *context; struct wined3d_context *context;
BOOL decl_changed = FALSE; BOOL decl_changed = FALSE;
unsigned int i, j; unsigned int i, j;
BYTE *data; BYTE *data;
DWORD flags = This->flags & (WINED3D_BUFFER_NOSYNC | WINED3D_BUFFER_DISCARD);
TRACE("iface %p\n", iface); TRACE("iface %p\n", iface);
This->flags &= ~(WINED3D_BUFFER_NOSYNC | WINED3D_BUFFER_DISCARD);
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
gl_info = context->gl_info;
if (!This->buffer_object) if (!This->buffer_object)
{ {
/* TODO: Make converting independent from VBOs */ /* TODO: Make converting independent from VBOs */
if (This->flags & WINED3D_BUFFER_CREATEBO) if (This->flags & WINED3D_BUFFER_CREATEBO)
{ {
buffer_create_buffer_object(This); buffer_create_buffer_object(This, gl_info);
This->flags &= ~WINED3D_BUFFER_CREATEBO; This->flags &= ~WINED3D_BUFFER_CREATEBO;
} }
else else
@ -836,7 +992,20 @@ static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface)
IWineD3DDeviceImpl_MarkStateDirty(device, STATE_STREAMSRC); IWineD3DDeviceImpl_MarkStateDirty(device, STATE_STREAMSRC);
goto end; goto end;
} }
buffer_check_buffer_object_size(This); buffer_check_buffer_object_size(This, gl_info);
/* The declaration changed, reload the whole buffer */
WARN("Reloading buffer because of decl change\n");
buffer_clear_dirty_areas(This);
if(!buffer_add_dirty_area(This, 0, 0))
{
ERR("buffer_add_dirty_area failed, this is not expected\n");
return;
}
/* Avoid unfenced updates, we might overwrite more areas of the buffer than the application
* cleared for unsynchronized updates
*/
flags = 0;
} }
else else
{ {
@ -864,18 +1033,6 @@ static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface)
} }
} }
if (decl_changed)
{
/* The declaration changed, reload the whole buffer */
WARN("Reloading buffer because of decl change\n");
buffer_clear_dirty_areas(This);
if(!buffer_add_dirty_area(This, 0, 0))
{
ERR("buffer_add_dirty_area failed, this is not expected\n");
return;
}
}
if(This->buffer_type_hint == GL_ELEMENT_ARRAY_BUFFER_ARB) if(This->buffer_type_hint == GL_ELEMENT_ARRAY_BUFFER_ARB)
{ {
IWineD3DDeviceImpl_MarkStateDirty(This->resource.device, STATE_INDEXBUFFER); IWineD3DDeviceImpl_MarkStateDirty(This->resource.device, STATE_INDEXBUFFER);
@ -896,18 +1053,7 @@ static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface)
return; return;
} }
ENTER_GL(); buffer_direct_upload(This, context->gl_info, flags);
GL_EXTCALL(glBindBufferARB(This->buffer_type_hint, This->buffer_object));
checkGLcall("glBindBufferARB");
while(This->modified_areas)
{
This->modified_areas--;
start = This->maps[This->modified_areas].offset;
len = This->maps[This->modified_areas].size;
GL_EXTCALL(glBufferSubDataARB(This->buffer_type_hint, start, len, This->resource.allocatedMemory + start));
checkGLcall("glBufferSubDataARB");
}
LEAVE_GL();
context_release(context); context_release(context);
return; return;
@ -915,7 +1061,7 @@ static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface)
if(!(This->flags & WINED3D_BUFFER_DOUBLEBUFFER)) if(!(This->flags & WINED3D_BUFFER_DOUBLEBUFFER))
{ {
buffer_get_sysmem(This); buffer_get_sysmem(This, gl_info);
} }
/* Now for each vertex in the buffer that needs conversion */ /* Now for each vertex in the buffer that needs conversion */
@ -1033,7 +1179,7 @@ static WINED3DRESOURCETYPE STDMETHODCALLTYPE buffer_GetType(IWineD3DBuffer *ifac
/* IWineD3DBuffer methods */ /* IWineD3DBuffer methods */
static DWORD buffer_sanitize_flags(DWORD flags) static DWORD buffer_sanitize_flags(struct wined3d_buffer *buffer, DWORD flags)
{ {
/* Not all flags make sense together, but Windows never returns an error. Catch the /* Not all flags make sense together, but Windows never returns an error. Catch the
* cases that could cause issues */ * cases that could cause issues */
@ -1055,6 +1201,11 @@ static DWORD buffer_sanitize_flags(DWORD flags)
WARN("WINED3DLOCK_DISCARD and WINED3DLOCK_NOOVERWRITE used together, ignoring\n"); WARN("WINED3DLOCK_DISCARD and WINED3DLOCK_NOOVERWRITE used together, ignoring\n");
return 0; return 0;
} }
else if (flags & (WINED3DLOCK_DISCARD | WINED3DLOCK_NOOVERWRITE) && !(buffer->resource.usage & WINED3DUSAGE_DYNAMIC))
{
WARN("DISCARD or NOOVERWRITE lock on non-dynamic buffer, ignoring\n");
return 0;
}
return flags; return flags;
} }
@ -1082,10 +1233,11 @@ static HRESULT STDMETHODCALLTYPE buffer_Map(IWineD3DBuffer *iface, UINT offset,
{ {
struct wined3d_buffer *This = (struct wined3d_buffer *)iface; struct wined3d_buffer *This = (struct wined3d_buffer *)iface;
LONG count; LONG count;
BOOL dirty = buffer_is_dirty(This);
TRACE("iface %p, offset %u, size %u, data %p, flags %#x\n", iface, offset, size, data, flags); TRACE("iface %p, offset %u, size %u, data %p, flags %#x\n", iface, offset, size, data, flags);
flags = buffer_sanitize_flags(flags); flags = buffer_sanitize_flags(This, flags);
if (!(flags & WINED3DLOCK_READONLY)) if (!(flags & WINED3DLOCK_READONLY))
{ {
if (!buffer_add_dirty_area(This, offset, size)) return E_OUTOFMEMORY; if (!buffer_add_dirty_area(This, offset, size)) return E_OUTOFMEMORY;
@ -1093,36 +1245,81 @@ static HRESULT STDMETHODCALLTYPE buffer_Map(IWineD3DBuffer *iface, UINT offset,
count = InterlockedIncrement(&This->lock_count); count = InterlockedIncrement(&This->lock_count);
if(!(This->flags & WINED3D_BUFFER_DOUBLEBUFFER) && This->buffer_object) if (This->buffer_object)
{ {
if(count == 1) if(!(This->flags & WINED3D_BUFFER_DOUBLEBUFFER))
{ {
IWineD3DDeviceImpl *device = This->resource.device; if(count == 1)
struct wined3d_context *context;
const struct wined3d_gl_info *gl_info;
if(This->buffer_type_hint == GL_ELEMENT_ARRAY_BUFFER_ARB)
{ {
IWineD3DDeviceImpl_MarkStateDirty(This->resource.device, STATE_INDEXBUFFER); IWineD3DDeviceImpl *device = This->resource.device;
struct wined3d_context *context;
const struct wined3d_gl_info *gl_info;
if(This->buffer_type_hint == GL_ELEMENT_ARRAY_BUFFER_ARB)
{
IWineD3DDeviceImpl_MarkStateDirty(This->resource.device, STATE_INDEXBUFFER);
}
context = context_acquire(device, NULL);
gl_info = context->gl_info;
ENTER_GL();
GL_EXTCALL(glBindBufferARB(This->buffer_type_hint, This->buffer_object));
if (gl_info->supported[ARB_MAP_BUFFER_RANGE])
{
GLbitfield mapflags = buffer_gl_map_flags(flags);
This->resource.allocatedMemory = GL_EXTCALL(glMapBufferRange(This->buffer_type_hint, 0,
This->resource.size, mapflags));
checkGLcall("glMapBufferRange");
}
else
{
if(This->flags & WINED3D_BUFFER_APPLESYNC)
{
LEAVE_GL();
buffer_sync_apple(This, flags, gl_info);
ENTER_GL();
}
This->resource.allocatedMemory = GL_EXTCALL(glMapBufferARB(This->buffer_type_hint, GL_READ_WRITE_ARB));
checkGLcall("glMapBufferARB");
}
LEAVE_GL();
if (((DWORD_PTR) This->resource.allocatedMemory) & (RESOURCE_ALIGNMENT - 1))
{
WARN("Pointer %p is not %u byte aligned, falling back to double buffered operation\n",
This->resource.allocatedMemory, RESOURCE_ALIGNMENT);
ENTER_GL();
GL_EXTCALL(glUnmapBufferARB(This->buffer_type_hint));
checkGLcall("glUnmapBufferARB");
LEAVE_GL();
This->resource.allocatedMemory = NULL;
buffer_get_sysmem(This, gl_info);
TRACE("New pointer is %p\n", This->resource.allocatedMemory);
}
context_release(context);
}
}
else
{
if (dirty)
{
if (This->flags & WINED3D_BUFFER_NOSYNC && !(flags & WINED3DLOCK_NOOVERWRITE))
{
This->flags &= ~WINED3D_BUFFER_NOSYNC;
}
}
else if(flags & WINED3DLOCK_NOOVERWRITE)
{
This->flags |= WINED3D_BUFFER_NOSYNC;
} }
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); if (flags & WINED3DLOCK_DISCARD)
gl_info = context->gl_info;
ENTER_GL();
GL_EXTCALL(glBindBufferARB(This->buffer_type_hint, This->buffer_object));
if (gl_info->supported[ARB_MAP_BUFFER_RANGE])
{ {
GLbitfield mapflags = buffer_gl_map_flags(flags); This->flags |= WINED3D_BUFFER_DISCARD;
This->resource.allocatedMemory = GL_EXTCALL(glMapBufferRange(This->buffer_type_hint, 0,
This->resource.size, mapflags));
} }
else
{
This->resource.allocatedMemory = GL_EXTCALL(glMapBufferARB(This->buffer_type_hint, GL_READ_WRITE_ARB));
}
LEAVE_GL();
context_release(context);
} }
} }
@ -1169,7 +1366,7 @@ static HRESULT STDMETHODCALLTYPE buffer_Unmap(IWineD3DBuffer *iface)
IWineD3DDeviceImpl_MarkStateDirty(This->resource.device, STATE_INDEXBUFFER); IWineD3DDeviceImpl_MarkStateDirty(This->resource.device, STATE_INDEXBUFFER);
} }
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
gl_info = context->gl_info; gl_info = context->gl_info;
ENTER_GL(); ENTER_GL();
GL_EXTCALL(glBindBufferARB(This->buffer_type_hint, This->buffer_object)); GL_EXTCALL(glBindBufferARB(This->buffer_type_hint, This->buffer_object));
@ -1251,7 +1448,7 @@ HRESULT buffer_init(struct wined3d_buffer *buffer, IWineD3DDeviceImpl *device,
UINT size, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool, GLenum bind_hint, UINT size, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool, GLenum bind_hint,
const char *data, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) const char *data, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
{ {
const struct GlPixelFormatDesc *format_desc = getFormatDescEntry(format, &device->adapter->gl_info); const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, &device->adapter->gl_info);
HRESULT hr; HRESULT hr;
const struct wined3d_gl_info *gl_info = &device->adapter->gl_info; const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
BOOL dynamic_buffer_ok; BOOL dynamic_buffer_ok;
@ -1276,7 +1473,8 @@ HRESULT buffer_init(struct wined3d_buffer *buffer, IWineD3DDeviceImpl *device,
TRACE("size %#x, usage %#x, format %s, memory @ %p, iface @ %p.\n", buffer->resource.size, buffer->resource.usage, 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_desc->format), buffer->resource.allocatedMemory, buffer);
dynamic_buffer_ok = gl_info->supported[APPLE_FLUSH_BUFFER_RANGE] || gl_info->supported[ARB_MAP_BUFFER_RANGE]; /* 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];
/* Observations show that drawStridedSlow is faster on dynamic VBs than converting + /* Observations show that drawStridedSlow is faster on dynamic VBs than converting +
* drawStridedFast (half-life 2 and others). * drawStridedFast (half-life 2 and others).

File diff suppressed because it is too large Load diff

View file

@ -31,11 +31,12 @@ static void cubetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3
{ {
/* Override the IWineD3DResource Preload method. */ /* Override the IWineD3DResource Preload method. */
IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface; IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface;
UINT sub_count = This->baseTexture.level_count * This->baseTexture.layer_count;
IWineD3DDeviceImpl *device = This->resource.device; IWineD3DDeviceImpl *device = This->resource.device;
struct wined3d_context *context = NULL; struct wined3d_context *context = NULL;
unsigned int i, j;
BOOL srgb_mode; BOOL srgb_mode;
BOOL *dirty; BOOL *dirty;
UINT i;
switch (srgb) switch (srgb)
{ {
@ -66,25 +67,24 @@ static void cubetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3
{ {
/* No danger of recursive calls, context_acquire() sets isInDraw to true /* No danger of recursive calls, context_acquire() sets isInDraw to true
* when loading offscreen render targets into their texture. */ * when loading offscreen render targets into their texture. */
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
} }
if (This->resource.format_desc->format == WINED3DFMT_P8_UINT if (This->resource.format_desc->format == WINED3DFMT_P8_UINT
|| This->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM) || This->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM)
{ {
for (i = 0; i < This->baseTexture.levels; ++i) for (i = 0; i < sub_count; ++i)
{ {
for (j = WINED3DCUBEMAP_FACE_POSITIVE_X; j <= WINED3DCUBEMAP_FACE_NEGATIVE_Z; ++j) IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)This->baseTexture.sub_resources[i];
if (palette9_changed(surface))
{ {
if (palette9_changed((IWineD3DSurfaceImpl *)This->surfaces[j][i])) TRACE("Reloading surface %p because the d3d8/9 palette was changed.\n", surface);
{ /* TODO: This is not necessarily needed with hw palettized texture support. */
TRACE("Reloading surface because the d3d8/9 palette was changed.\n"); IWineD3DSurface_LoadLocation((IWineD3DSurface *)surface, SFLAG_INSYSMEM, NULL);
/* TODO: This is not necessarily needed with hw palettized texture support. */ /* Make sure the texture is reloaded because of the palette change,
IWineD3DSurface_LoadLocation(This->surfaces[j][i], SFLAG_INSYSMEM, NULL); * this kills performance though :( */
/* Make sure the texture is reloaded because of the palette change, IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INTEXTURE, FALSE);
* this kills performance though :( */
IWineD3DSurface_ModifyLocation(This->surfaces[j][i], SFLAG_INTEXTURE, FALSE);
}
} }
} }
} }
@ -93,12 +93,9 @@ static void cubetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3
* since the last load then reload the surfaces. */ * since the last load then reload the surfaces. */
if (*dirty) if (*dirty)
{ {
for (i = 0; i < This->baseTexture.levels; ++i) for (i = 0; i < sub_count; ++i)
{ {
for (j = WINED3DCUBEMAP_FACE_POSITIVE_X; j <= WINED3DCUBEMAP_FACE_NEGATIVE_Z; ++j) IWineD3DSurface_LoadTexture((IWineD3DSurface *)This->baseTexture.sub_resources[i], srgb_mode);
{
IWineD3DSurface_LoadTexture(This->surfaces[j][i], srgb_mode);
}
} }
} }
else else
@ -114,26 +111,24 @@ static void cubetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3
static void cubetexture_cleanup(IWineD3DCubeTextureImpl *This) static void cubetexture_cleanup(IWineD3DCubeTextureImpl *This)
{ {
unsigned int i, j; UINT sub_count = This->baseTexture.level_count * This->baseTexture.layer_count;
UINT i;
TRACE("(%p) : Cleaning up.\n", This); TRACE("(%p) : Cleaning up.\n", This);
for (i = 0; i < This->baseTexture.levels; ++i) for (i = 0; i < sub_count; ++i)
{ {
for (j = 0; j < 6; ++j) IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)This->baseTexture.sub_resources[i];
{
IWineD3DSurface *surface = This->surfaces[j][i];
if (surface) if (surface)
{ {
/* Clean out the texture name we gave to the surface so that the /* Clean out the texture name we gave to the surface so that the
* surface doesn't try and release it. */ * surface doesn't try and release it. */
surface_set_texture_name(surface, 0, TRUE); surface_set_texture_name(surface, 0, TRUE);
surface_set_texture_name(surface, 0, FALSE); surface_set_texture_name(surface, 0, FALSE);
surface_set_texture_target(surface, 0); surface_set_texture_target(surface, 0);
IWineD3DSurface_SetContainer(surface, NULL); IWineD3DSurface_SetContainer((IWineD3DSurface *)surface, NULL);
IWineD3DSurface_Release(surface); IWineD3DSurface_Release((IWineD3DSurface *)surface);
}
} }
} }
basetexture_cleanup((IWineD3DBaseTexture *)This); basetexture_cleanup((IWineD3DBaseTexture *)This);
@ -207,21 +202,25 @@ static void WINAPI IWineD3DCubeTextureImpl_PreLoad(IWineD3DCubeTexture *iface) {
cubetexture_internal_preload((IWineD3DBaseTexture *) iface, SRGB_ANY); cubetexture_internal_preload((IWineD3DBaseTexture *) iface, SRGB_ANY);
} }
static void WINAPI IWineD3DCubeTextureImpl_UnLoad(IWineD3DCubeTexture *iface) { static void WINAPI IWineD3DCubeTextureImpl_UnLoad(IWineD3DCubeTexture *iface)
unsigned int i, j; {
IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface; IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface;
TRACE("(%p)\n", This); UINT sub_count = This->baseTexture.level_count * This->baseTexture.layer_count;
UINT i;
TRACE("iface %p.\n", iface);
/* Unload all the surfaces and reset the texture name. If UnLoad was called on the /* Unload all the surfaces and reset the texture name. If UnLoad was called on the
* surface before, this one will be a NOP and vice versa. Unloading an unloaded * surface before, this one will be a NOP and vice versa. Unloading an unloaded
* surface is fine * surface is fine. */
*/
for (i = 0; i < This->baseTexture.levels; i++) { for (i = 0; i < sub_count; ++i)
for (j = WINED3DCUBEMAP_FACE_POSITIVE_X; j <= WINED3DCUBEMAP_FACE_NEGATIVE_Z ; j++) { {
IWineD3DSurface_UnLoad(This->surfaces[j][i]); IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)This->baseTexture.sub_resources[i];
surface_set_texture_name(This->surfaces[j][i], 0, TRUE);
surface_set_texture_name(This->surfaces[j][i], 0, FALSE); IWineD3DSurface_UnLoad((IWineD3DSurface *)surface);
} surface_set_texture_name(surface, 0, TRUE);
surface_set_texture_name(surface, 0, FALSE);
} }
basetexture_unload((IWineD3DBaseTexture *)iface); basetexture_unload((IWineD3DBaseTexture *)iface);
@ -281,16 +280,19 @@ static HRESULT WINAPI IWineD3DCubeTextureImpl_BindTexture(IWineD3DCubeTexture *i
TRACE("(%p) : relay to BaseTexture\n", This); TRACE("(%p) : relay to BaseTexture\n", This);
hr = basetexture_bind((IWineD3DBaseTexture *)iface, srgb, &set_gl_texture_desc); hr = basetexture_bind((IWineD3DBaseTexture *)iface, srgb, &set_gl_texture_desc);
if (set_gl_texture_desc && SUCCEEDED(hr)) { if (set_gl_texture_desc && SUCCEEDED(hr))
UINT i, j; {
for (i = 0; i < This->baseTexture.levels; ++i) { UINT sub_count = This->baseTexture.level_count * This->baseTexture.layer_count;
for (j = WINED3DCUBEMAP_FACE_POSITIVE_X; j <= WINED3DCUBEMAP_FACE_NEGATIVE_Z; ++j) { UINT i;
if(This->baseTexture.is_srgb) {
surface_set_texture_name(This->surfaces[j][i], This->baseTexture.texture_srgb.name, TRUE); for (i = 0; i < sub_count; ++i)
} else { {
surface_set_texture_name(This->surfaces[j][i], This->baseTexture.texture_rgb.name, FALSE); IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)This->baseTexture.sub_resources[i];
}
} if (This->baseTexture.is_srgb)
surface_set_texture_name(surface, This->baseTexture.texture_srgb.name, TRUE);
else
surface_set_texture_name(surface, This->baseTexture.texture_rgb.name, FALSE);
} }
} }
@ -314,82 +316,102 @@ static BOOL WINAPI IWineD3DCubeTextureImpl_IsCondNP2(IWineD3DCubeTexture *iface)
/* ******************************************* /* *******************************************
IWineD3DCubeTexture IWineD3DCubeTexture parts follow IWineD3DCubeTexture IWineD3DCubeTexture parts follow
******************************************* */ ******************************************* */
static HRESULT WINAPI IWineD3DCubeTextureImpl_GetLevelDesc(IWineD3DCubeTexture *iface, UINT Level, WINED3DSURFACE_DESC* pDesc) { static HRESULT WINAPI IWineD3DCubeTextureImpl_GetLevelDesc(IWineD3DCubeTexture *iface,
IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface; UINT level, WINED3DSURFACE_DESC *desc)
{
IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DSurface *surface;
if (Level < This->baseTexture.levels) { TRACE("iface %p, level %u, desc %p.\n", iface, level, desc);
TRACE("(%p) level (%d)\n", This, Level);
return IWineD3DSurface_GetDesc(This->surfaces[0][Level], pDesc); if (!(surface = (IWineD3DSurface *)basetexture_get_sub_resource(texture, 0, level)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
WARN("(%p) level(%d) overflow Levels(%d)\n", This, Level, This->baseTexture.levels);
return WINED3DERR_INVALIDCALL; return IWineD3DSurface_GetDesc(surface, desc);
} }
static HRESULT WINAPI IWineD3DCubeTextureImpl_GetCubeMapSurface(IWineD3DCubeTexture *iface, WINED3DCUBEMAP_FACES FaceType, UINT Level, IWineD3DSurface** ppCubeMapSurface) { static HRESULT WINAPI IWineD3DCubeTextureImpl_GetCubeMapSurface(IWineD3DCubeTexture *iface,
IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface; WINED3DCUBEMAP_FACES face, UINT level, IWineD3DSurface **surface)
HRESULT hr = WINED3DERR_INVALIDCALL; {
IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DSurface *s;
if (Level < This->baseTexture.levels && FaceType <= WINED3DCUBEMAP_FACE_NEGATIVE_Z) { TRACE("iface %p, face %u, level %u, surface %p.\n",
*ppCubeMapSurface = This->surfaces[FaceType][Level]; iface, face, level, surface);
IWineD3DSurface_AddRef(*ppCubeMapSurface);
hr = WINED3D_OK; if (!(s = (IWineD3DSurface *)basetexture_get_sub_resource(texture, face, level)))
} {
if (WINED3D_OK == hr) { WARN("Failed to get sub-resource.\n");
TRACE("(%p) -> faceType(%d) level(%d) returning surface@%p\n", This, FaceType, Level, This->surfaces[FaceType][Level]); return WINED3DERR_INVALIDCALL;
} else {
WARN("(%p) level(%d) overflow Levels(%d) Or FaceType(%d)\n", This, Level, This->baseTexture.levels, FaceType);
} }
return hr; IWineD3DSurface_AddRef(s);
*surface = s;
TRACE("Returning surface %p.\n", *surface);
return WINED3D_OK;
} }
static HRESULT WINAPI IWineD3DCubeTextureImpl_LockRect(IWineD3DCubeTexture *iface, WINED3DCUBEMAP_FACES FaceType, UINT Level, WINED3DLOCKED_RECT* pLockedRect, CONST RECT* pRect, DWORD Flags) { static HRESULT WINAPI IWineD3DCubeTextureImpl_LockRect(IWineD3DCubeTexture *iface,
HRESULT hr = WINED3DERR_INVALIDCALL; WINED3DCUBEMAP_FACES face, UINT level, WINED3DLOCKED_RECT *locked_rect, const RECT *rect, DWORD flags)
IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface; {
IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DSurface *surface;
if (Level < This->baseTexture.levels && FaceType <= WINED3DCUBEMAP_FACE_NEGATIVE_Z) { TRACE("iface %p, face %u, level %u, locked_rect %p, rect %s, flags %#x.\n",
hr = IWineD3DSurface_LockRect(This->surfaces[FaceType][Level], pLockedRect, pRect, Flags); iface, face, level, locked_rect, wine_dbgstr_rect(rect), flags);
if (!(surface = (IWineD3DSurface *)basetexture_get_sub_resource(texture, face, level)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
if (WINED3D_OK == hr) { return IWineD3DSurface_LockRect(surface, locked_rect, rect, flags);
TRACE("(%p) -> faceType(%d) level(%d) returning memory@%p success(%u)\n", This, FaceType, Level, pLockedRect->pBits, hr);
} else {
WARN("(%p) level(%d) overflow Levels(%d) Or FaceType(%d)\n", This, Level, This->baseTexture.levels, FaceType);
}
return hr;
} }
static HRESULT WINAPI IWineD3DCubeTextureImpl_UnlockRect(IWineD3DCubeTexture *iface, WINED3DCUBEMAP_FACES FaceType, UINT Level) { static HRESULT WINAPI IWineD3DCubeTextureImpl_UnlockRect(IWineD3DCubeTexture *iface,
HRESULT hr = WINED3DERR_INVALIDCALL; WINED3DCUBEMAP_FACES face, UINT level)
IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface; {
IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DSurface *surface;
if (Level < This->baseTexture.levels && FaceType <= WINED3DCUBEMAP_FACE_NEGATIVE_Z) { TRACE("iface %p, face %u, level %u.\n",
hr = IWineD3DSurface_UnlockRect(This->surfaces[FaceType][Level]); iface, face, level);
if (!(surface = (IWineD3DSurface *)basetexture_get_sub_resource(texture, face, level)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
if (WINED3D_OK == hr) { return IWineD3DSurface_UnlockRect(surface);
TRACE("(%p) -> faceType(%d) level(%d) success(%u)\n", This, FaceType, Level, hr);
} else {
WARN("(%p) level(%d) overflow Levels(%d) Or FaceType(%d)\n", This, Level, This->baseTexture.levels, FaceType);
}
return hr;
} }
static HRESULT WINAPI IWineD3DCubeTextureImpl_AddDirtyRect(IWineD3DCubeTexture *iface, WINED3DCUBEMAP_FACES FaceType, CONST RECT* pDirtyRect) { static HRESULT WINAPI IWineD3DCubeTextureImpl_AddDirtyRect(IWineD3DCubeTexture *iface,
HRESULT hr = WINED3DERR_INVALIDCALL; WINED3DCUBEMAP_FACES face, const RECT *dirty_rect)
IWineD3DCubeTextureImpl *This = (IWineD3DCubeTextureImpl *)iface; {
This->baseTexture.texture_rgb.dirty = TRUE; IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
This->baseTexture.texture_srgb.dirty = TRUE; IWineD3DSurfaceImpl *surface;
TRACE("(%p) : dirtyfication of faceType(%d) Level (0)\n", This, FaceType);
if (FaceType <= WINED3DCUBEMAP_FACE_NEGATIVE_Z) { TRACE("iface %p, face %u, dirty_rect %s.\n",
surface_add_dirty_rect(This->surfaces[FaceType][0], pDirtyRect); iface, face, wine_dbgstr_rect(dirty_rect));
hr = WINED3D_OK;
} else { if (!(surface = (IWineD3DSurfaceImpl *)basetexture_get_sub_resource(texture, face, 0)))
WARN("(%p) overflow FaceType(%d)\n", This, FaceType); {
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
return hr;
texture->baseTexture.texture_rgb.dirty = TRUE;
texture->baseTexture.texture_srgb.dirty = TRUE;
surface_add_dirty_rect(surface, dirty_rect);
return WINED3D_OK;
} }
static const IWineD3DCubeTextureVtbl IWineD3DCubeTexture_Vtbl = static const IWineD3DCubeTextureVtbl IWineD3DCubeTexture_Vtbl =
@ -433,7 +455,7 @@ HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UIN
IUnknown *parent, const struct wined3d_parent_ops *parent_ops) IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
{ {
const struct wined3d_gl_info *gl_info = &device->adapter->gl_info; const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
const struct GlPixelFormatDesc *format_desc = getFormatDescEntry(format, gl_info); const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, gl_info);
UINT pow2_edge_length; UINT pow2_edge_length;
unsigned int i, j; unsigned int i, j;
UINT tmp_w; UINT tmp_w;
@ -478,8 +500,8 @@ HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UIN
texture->lpVtbl = &IWineD3DCubeTexture_Vtbl; texture->lpVtbl = &IWineD3DCubeTexture_Vtbl;
hr = basetexture_init((IWineD3DBaseTextureImpl *)texture, levels, WINED3DRTYPE_CUBETEXTURE, hr = basetexture_init((IWineD3DBaseTextureImpl *)texture, 6, levels,
device, 0, usage, format_desc, pool, parent, parent_ops); WINED3DRTYPE_CUBETEXTURE, device, 0, usage, format_desc, pool, parent, parent_ops);
if (FAILED(hr)) if (FAILED(hr))
{ {
WARN("Failed to initialize basetexture, returning %#x\n", hr); WARN("Failed to initialize basetexture, returning %#x\n", hr);
@ -510,7 +532,7 @@ HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UIN
/* Generate all the surfaces. */ /* Generate all the surfaces. */
tmp_w = edge_length; tmp_w = edge_length;
for (i = 0; i < texture->baseTexture.levels; ++i) for (i = 0; i < texture->baseTexture.level_count; ++i)
{ {
/* Create the 6 faces. */ /* Create the 6 faces. */
for (j = 0; j < 6; ++j) for (j = 0; j < 6; ++j)
@ -524,20 +546,22 @@ HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UIN
GL_TEXTURE_CUBE_MAP_POSITIVE_Z_ARB, GL_TEXTURE_CUBE_MAP_POSITIVE_Z_ARB,
GL_TEXTURE_CUBE_MAP_NEGATIVE_Z_ARB, GL_TEXTURE_CUBE_MAP_NEGATIVE_Z_ARB,
}; };
UINT idx = j * texture->baseTexture.level_count + i;
IWineD3DSurface *surface;
hr = IWineD3DDeviceParent_CreateSurface(device->device_parent, parent, tmp_w, tmp_w, hr = IWineD3DDeviceParent_CreateSurface(device->device_parent, parent, tmp_w, tmp_w,
format, usage, pool, i /* Level */, j, &texture->surfaces[j][i]); format, usage, pool, i /* Level */, j, &surface);
if (FAILED(hr)) if (FAILED(hr))
{ {
FIXME("(%p) Failed to create surface, hr %#x.\n", texture, hr); FIXME("(%p) Failed to create surface, hr %#x.\n", texture, hr);
texture->surfaces[j][i] = NULL;
cubetexture_cleanup(texture); cubetexture_cleanup(texture);
return hr; return hr;
} }
IWineD3DSurface_SetContainer(texture->surfaces[j][i], (IWineD3DBase *)texture); IWineD3DSurface_SetContainer(surface, (IWineD3DBase *)texture);
TRACE("Created surface level %u @ %p.\n", i, texture->surfaces[j][i]); surface_set_texture_target((IWineD3DSurfaceImpl *)surface, cube_targets[j]);
surface_set_texture_target(texture->surfaces[j][i], cube_targets[j]); texture->baseTexture.sub_resources[idx] = (IWineD3DResourceImpl *)surface;
TRACE("Created surface level %u @ %p.\n", i, surface);
} }
tmp_w = max(1, tmp_w >> 1); tmp_w = max(1, tmp_w >> 1);
} }

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -28,7 +28,6 @@
#include "wined3d_private.h" #include "wined3d_private.h"
WINE_DEFAULT_DEBUG_CHANNEL(d3d_draw); WINE_DEFAULT_DEBUG_CHANNEL(d3d_draw);
#define GLINFO_LOCATION This->adapter->gl_info
#include <stdio.h> #include <stdio.h>
#include <math.h> #include <math.h>
@ -71,7 +70,7 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
UINT vx_index; UINT vx_index;
IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
const UINT *streamOffset = This->stateBlock->streamOffset; const UINT *streamOffset = This->stateBlock->streamOffset;
long SkipnStrides = startIdx + This->stateBlock->loadBaseVertexIndex; LONG SkipnStrides = startIdx + This->stateBlock->loadBaseVertexIndex;
BOOL pixelShader = use_ps(This->stateBlock); BOOL pixelShader = use_ps(This->stateBlock);
BOOL specular_fog = FALSE; BOOL specular_fog = FALSE;
const BYTE *texCoords[WINED3DDP_MAXTEXCOORD]; const BYTE *texCoords[WINED3DDP_MAXTEXCOORD];
@ -85,14 +84,14 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
TRACE("Using slow vertex array code\n"); TRACE("Using slow vertex array code\n");
/* Variable Initialization */ /* Variable Initialization */
if (idxSize != 0) { if (idxSize)
/* Immediate mode drawing can't make use of indices in a vbo - get the data from the index buffer. {
* If the index buffer has no vbo(not supported or other reason), or with user pointer drawing /* Immediate mode drawing can't make use of indices in a vbo - get the
* idxData will be != NULL * data from the index buffer. If the index buffer has no vbo (not
*/ * supported or other reason), or with user pointer drawing idxData
if(idxData == NULL) { * will be non-NULL. */
idxData = buffer_get_sysmem((struct wined3d_buffer *) This->stateBlock->pIndexData); if (!idxData)
} idxData = buffer_get_sysmem((struct wined3d_buffer *)This->stateBlock->pIndexData, gl_info);
if (idxSize == 2) pIdxBufS = idxData; if (idxSize == 2) pIdxBufS = idxData;
else pIdxBufL = idxData; else pIdxBufL = idxData;
@ -102,7 +101,6 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
} }
/* Start drawing in GL */ /* Start drawing in GL */
VTRACE(("glBegin(%x)\n", glPrimType));
glBegin(glPrimType); glBegin(glPrimType);
if (si->use_map & (1 << WINED3D_FFP_POSITION)) if (si->use_map & (1 << WINED3D_FFP_POSITION))
@ -226,13 +224,10 @@ static void drawStridedSlow(IWineD3DDevice *iface, const struct wined3d_context
if (idxData != NULL) { if (idxData != NULL) {
/* Indexed so work out the number of strides to skip */ /* Indexed so work out the number of strides to skip */
if (idxSize == 2) { if (idxSize == 2)
VTRACE(("Idx for vertex %u = %u\n", vx_index, pIdxBufS[startIdx+vx_index]));
SkipnStrides = pIdxBufS[startIdx + vx_index] + This->stateBlock->loadBaseVertexIndex; SkipnStrides = pIdxBufS[startIdx + vx_index] + This->stateBlock->loadBaseVertexIndex;
} else { else
VTRACE(("Idx for vertex %u = %u\n", vx_index, pIdxBufL[startIdx+vx_index]));
SkipnStrides = pIdxBufL[startIdx + vx_index] + This->stateBlock->loadBaseVertexIndex; SkipnStrides = pIdxBufL[startIdx + vx_index] + This->stateBlock->loadBaseVertexIndex;
}
} }
tmp_tex_mask = tex_mask; tmp_tex_mask = tex_mask;
@ -426,7 +421,8 @@ static void drawStridedSlowVs(IWineD3DDevice *iface, const struct wined3d_stream
GLenum glPrimitiveType, const void *idxData, UINT idxSize, UINT startIdx) GLenum glPrimitiveType, const void *idxData, UINT idxSize, UINT startIdx)
{ {
IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface; IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *) iface;
long SkipnStrides = startIdx + This->stateBlock->loadBaseVertexIndex; const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
LONG SkipnStrides = startIdx + This->stateBlock->loadBaseVertexIndex;
const WORD *pIdxBufS = NULL; const WORD *pIdxBufS = NULL;
const DWORD *pIdxBufL = NULL; const DWORD *pIdxBufL = NULL;
UINT vx_index; UINT vx_index;
@ -434,14 +430,14 @@ static void drawStridedSlowVs(IWineD3DDevice *iface, const struct wined3d_stream
IWineD3DStateBlockImpl *stateblock = This->stateBlock; IWineD3DStateBlockImpl *stateblock = This->stateBlock;
const BYTE *ptr; const BYTE *ptr;
if (idxSize != 0) { if (idxSize)
/* Immediate mode drawing can't make use of indices in a vbo - get the data from the index buffer. {
* If the index buffer has no vbo(not supported or other reason), or with user pointer drawing /* Immediate mode drawing can't make use of indices in a vbo - get the
* idxData will be != NULL * data from the index buffer. If the index buffer has no vbo (not
*/ * supported or other reason), or with user pointer drawing idxData
if(idxData == NULL) { * will be non-NULL. */
idxData = buffer_get_sysmem((struct wined3d_buffer *) This->stateBlock->pIndexData); if (!idxData)
} idxData = buffer_get_sysmem((struct wined3d_buffer *)This->stateBlock->pIndexData, gl_info);
if (idxSize == 2) pIdxBufS = idxData; if (idxSize == 2) pIdxBufS = idxData;
else pIdxBufL = idxData; else pIdxBufL = idxData;
@ -451,20 +447,16 @@ static void drawStridedSlowVs(IWineD3DDevice *iface, const struct wined3d_stream
} }
/* Start drawing in GL */ /* Start drawing in GL */
VTRACE(("glBegin(%x)\n", glPrimitiveType));
glBegin(glPrimitiveType); glBegin(glPrimitiveType);
for (vx_index = 0; vx_index < numberOfVertices; ++vx_index) { for (vx_index = 0; vx_index < numberOfVertices; ++vx_index) {
if (idxData != NULL) { if (idxData != NULL) {
/* Indexed so work out the number of strides to skip */ /* Indexed so work out the number of strides to skip */
if (idxSize == 2) { if (idxSize == 2)
VTRACE(("Idx for vertex %d = %d\n", vx_index, pIdxBufS[startIdx+vx_index]));
SkipnStrides = pIdxBufS[startIdx + vx_index] + stateblock->loadBaseVertexIndex; SkipnStrides = pIdxBufS[startIdx + vx_index] + stateblock->loadBaseVertexIndex;
} else { else
VTRACE(("Idx for vertex %d = %d\n", vx_index, pIdxBufL[startIdx+vx_index]));
SkipnStrides = pIdxBufL[startIdx + vx_index] + stateblock->loadBaseVertexIndex; SkipnStrides = pIdxBufL[startIdx + vx_index] + stateblock->loadBaseVertexIndex;
}
} }
for (i = MAX_ATTRIBS - 1; i >= 0; i--) for (i = MAX_ATTRIBS - 1; i >= 0; i--)
@ -543,7 +535,7 @@ static inline void drawStridedInstanced(IWineD3DDevice *iface, const struct wine
{ {
struct wined3d_buffer *vb = struct wined3d_buffer *vb =
(struct wined3d_buffer *)stateblock->streamSource[si->elements[instancedData[j]].stream_idx]; (struct wined3d_buffer *)stateblock->streamSource[si->elements[instancedData[j]].stream_idx];
ptr += (long) buffer_get_sysmem(vb); ptr += (ULONG_PTR)buffer_get_sysmem(vb, &This->adapter->gl_info);
} }
send_attribute(This, si->elements[instancedData[j]].format_desc->format, instancedData[j], ptr); send_attribute(This, si->elements[instancedData[j]].format_desc->format, instancedData[j], ptr);
@ -555,7 +547,8 @@ static inline void drawStridedInstanced(IWineD3DDevice *iface, const struct wine
} }
} }
static inline void remove_vbos(IWineD3DDeviceImpl *This, struct wined3d_stream_info *s) static inline void remove_vbos(IWineD3DDeviceImpl *This, const struct wined3d_gl_info *gl_info,
struct wined3d_stream_info *s)
{ {
unsigned int i; unsigned int i;
@ -570,7 +563,7 @@ static inline void remove_vbos(IWineD3DDeviceImpl *This, struct wined3d_stream_i
{ {
struct wined3d_buffer *vb = (struct wined3d_buffer *)This->stateBlock->streamSource[e->stream_idx]; struct wined3d_buffer *vb = (struct wined3d_buffer *)This->stateBlock->streamSource[e->stream_idx];
e->buffer_object = 0; e->buffer_object = 0;
e->data = (BYTE *)((unsigned long)e->data + (unsigned long)buffer_get_sysmem(vb)); e->data = (BYTE *)((ULONG_PTR)e->data + (ULONG_PTR)buffer_get_sysmem(vb, gl_info));
} }
} }
} }
@ -580,7 +573,6 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
{ {
IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
IWineD3DSurfaceImpl *target;
struct wined3d_context *context; struct wined3d_context *context;
unsigned int i; unsigned int i;
@ -591,11 +583,11 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
/* Invalidate the back buffer memory so LockRect will read it the next time */ /* Invalidate the back buffer memory so LockRect will read it the next time */
for (i = 0; i < This->adapter->gl_info.limits.buffers; ++i) for (i = 0; i < This->adapter->gl_info.limits.buffers; ++i)
{ {
target = (IWineD3DSurfaceImpl *)This->render_targets[i]; IWineD3DSurface *target = (IWineD3DSurface *)This->render_targets[i];
if (target) if (target)
{ {
IWineD3DSurface_LoadLocation((IWineD3DSurface *)target, SFLAG_INDRAWABLE, NULL); IWineD3DSurface_LoadLocation(target, SFLAG_INDRAWABLE, NULL);
IWineD3DSurface_ModifyLocation((IWineD3DSurface *)target, SFLAG_INDRAWABLE, TRUE); IWineD3DSurface_ModifyLocation(target, SFLAG_INDRAWABLE, TRUE);
} }
} }
} }
@ -603,9 +595,18 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
/* Signals other modules that a drawing is in progress and the stateblock finalized */ /* Signals other modules that a drawing is in progress and the stateblock finalized */
This->isInDraw = TRUE; This->isInDraw = TRUE;
context = context_acquire(This, This->render_targets[0], CTXUSAGE_DRAWPRIM); context = context_acquire(This, This->render_targets[0]);
if (!context->valid)
{
context_release(context);
WARN("Invalid context, skipping draw.\n");
return;
}
if (This->stencilBufferTarget) { context_apply_draw_state(context, This);
if (This->depth_stencil)
{
/* Note that this depends on the context_acquire() call above to set /* Note that this depends on the context_acquire() call above to set
* This->render_offscreen properly. We don't currently take the * This->render_offscreen properly. We don't currently take the
* Z-compare function into account, but we could skip loading the * Z-compare function into account, but we could skip loading the
@ -614,9 +615,33 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
DWORD location = context->render_offscreen ? SFLAG_DS_OFFSCREEN : SFLAG_DS_ONSCREEN; DWORD location = context->render_offscreen ? SFLAG_DS_OFFSCREEN : SFLAG_DS_ONSCREEN;
if (This->stateBlock->renderState[WINED3DRS_ZWRITEENABLE] if (This->stateBlock->renderState[WINED3DRS_ZWRITEENABLE]
|| This->stateBlock->renderState[WINED3DRS_ZENABLE]) || This->stateBlock->renderState[WINED3DRS_ZENABLE])
surface_load_ds_location(This->stencilBufferTarget, context, location); {
if (This->stateBlock->renderState[WINED3DRS_ZWRITEENABLE]) RECT current_rect, draw_rect, r;
surface_modify_ds_location(This->stencilBufferTarget, location);
if (location == SFLAG_DS_ONSCREEN && This->depth_stencil != This->onscreen_depth_stencil)
device_switch_onscreen_ds(This, context, This->depth_stencil);
if (This->depth_stencil->Flags & location)
SetRect(&current_rect, 0, 0,
This->depth_stencil->ds_current_size.cx,
This->depth_stencil->ds_current_size.cy);
else
SetRectEmpty(&current_rect);
device_get_draw_rect(This, &draw_rect);
IntersectRect(&r, &draw_rect, &current_rect);
if (!EqualRect(&r, &draw_rect))
surface_load_ds_location(This->depth_stencil, context, location);
if (This->stateBlock->renderState[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);
}
}
} }
/* Ok, we will be updating the screen from here onwards so grab the lock */ /* Ok, we will be updating the screen from here onwards so grab the lock */
@ -659,7 +684,7 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
if(emulation) { if(emulation) {
stream_info = &stridedlcl; stream_info = &stridedlcl;
memcpy(&stridedlcl, &This->strided_streams, sizeof(stridedlcl)); memcpy(&stridedlcl, &This->strided_streams, sizeof(stridedlcl));
remove_vbos(This, &stridedlcl); remove_vbos(This, context->gl_info, &stridedlcl);
} }
} }
@ -691,7 +716,12 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
/* Finished updating the screen, restore lock */ /* Finished updating the screen, restore lock */
LEAVE_GL(); LEAVE_GL();
wglFlush(); /* Flush to ensure ordering across contexts. */ for(i = 0; i < This->num_buffer_queries; i++)
{
wined3d_event_query_issue(This->buffer_queries[i], This);
}
if (wined3d_settings.strict_draw_ordering) wglFlush(); /* Flush to ensure ordering across contexts. */
context_release(context); context_release(context);
@ -700,14 +730,14 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
/* Diagnostics */ /* Diagnostics */
#ifdef SHOW_FRAME_MAKEUP #ifdef SHOW_FRAME_MAKEUP
{ {
static long int primCounter = 0; static LONG primCounter = 0;
/* NOTE: set primCounter to the value reported by drawprim /* NOTE: set primCounter to the value reported by drawprim
before you want to to write frame makeup to /tmp */ before you want to to write frame makeup to /tmp */
if (primCounter >= 0) { if (primCounter >= 0) {
WINED3DLOCKED_RECT r; WINED3DLOCKED_RECT r;
char buffer[80]; char buffer[80];
IWineD3DSurface_LockRect(This->render_targets[0], &r, NULL, WINED3DLOCK_READONLY); IWineD3DSurface_LockRect(This->render_targets[0], &r, NULL, WINED3DLOCK_READONLY);
sprintf(buffer, "/tmp/backbuffer_%ld.tga", primCounter); sprintf(buffer, "/tmp/backbuffer_%d.tga", primCounter);
TRACE("Saving screenshot %s\n", buffer); TRACE("Saving screenshot %s\n", buffer);
IWineD3DSurface_SaveSnapshot(This->render_targets[0], buffer); IWineD3DSurface_SaveSnapshot(This->render_targets[0], buffer);
IWineD3DSurface_UnlockRect(This->render_targets[0]); IWineD3DSurface_UnlockRect(This->render_targets[0]);
@ -718,7 +748,7 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
int textureNo; int textureNo;
for (textureNo = 0; textureNo < MAX_COMBINED_SAMPLERS; ++textureNo) { for (textureNo = 0; textureNo < MAX_COMBINED_SAMPLERS; ++textureNo) {
if (This->stateBlock->textures[textureNo] != NULL) { if (This->stateBlock->textures[textureNo] != NULL) {
sprintf(buffer, "/tmp/texture_%p_%ld_%d.tga", This->stateBlock->textures[textureNo], primCounter, textureNo); sprintf(buffer, "/tmp/texture_%p_%d_%d.tga", This->stateBlock->textures[textureNo], primCounter, textureNo);
TRACE("Saving texture %s\n", buffer); TRACE("Saving texture %s\n", buffer);
if (IWineD3DBaseTexture_GetType(This->stateBlock->textures[textureNo]) == WINED3DRTYPE_TEXTURE) { if (IWineD3DBaseTexture_GetType(This->stateBlock->textures[textureNo]) == WINED3DRTYPE_TEXTURE) {
IWineD3DTexture_GetSurfaceLevel(This->stateBlock->textures[textureNo], 0, &pSur); IWineD3DTexture_GetSurfaceLevel(This->stateBlock->textures[textureNo], 0, &pSur);
@ -732,7 +762,7 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
} }
#endif #endif
} }
TRACE("drawprim #%ld\n", primCounter); TRACE("drawprim #%d\n", primCounter);
++primCounter; ++primCounter;
} }
#endif #endif
@ -788,7 +818,8 @@ HRESULT tesselate_rectpatch(IWineD3DDeviceImpl *This,
/* Simply activate the context for blitting. This disables all the things we don't want and /* Simply activate the context for blitting. This disables all the things we don't want and
* takes care of dirtifying. Dirtifying is preferred over pushing / popping, since drawing the * takes care of dirtifying. Dirtifying is preferred over pushing / popping, since drawing the
* patch (as opposed to normal draws) will most likely need different changes anyway. */ * patch (as opposed to normal draws) will most likely need different changes anyway. */
context = context_acquire(This, NULL, CTXUSAGE_BLIT); context = context_acquire(This, NULL);
context_apply_blit_state(context, This);
/* First, locate the position data. This is provided in a vertex buffer in the stateblock. /* First, locate the position data. This is provided in a vertex buffer in the stateblock.
* Beware of vbos * Beware of vbos
@ -800,7 +831,7 @@ HRESULT tesselate_rectpatch(IWineD3DDeviceImpl *This,
{ {
struct wined3d_buffer *vb; struct wined3d_buffer *vb;
vb = (struct wined3d_buffer *)This->stateBlock->streamSource[e->stream_idx]; vb = (struct wined3d_buffer *)This->stateBlock->streamSource[e->stream_idx];
e->data = (BYTE *)((unsigned long)e->data + (unsigned long)buffer_get_sysmem(vb)); e->data = (BYTE *)((ULONG_PTR)e->data + (ULONG_PTR)buffer_get_sysmem(vb, context->gl_info));
} }
vtxStride = e->stride; vtxStride = e->stride;
data = e->data + data = e->data +

View file

@ -39,8 +39,6 @@ WINE_DECLARE_DEBUG_CHANNEL(d3d_constants);
WINE_DECLARE_DEBUG_CHANNEL(d3d_caps); WINE_DECLARE_DEBUG_CHANNEL(d3d_caps);
WINE_DECLARE_DEBUG_CHANNEL(d3d); WINE_DECLARE_DEBUG_CHANNEL(d3d);
#define GLINFO_LOCATION (*gl_info)
#define WINED3D_GLSL_SAMPLE_PROJECTED 0x1 #define WINED3D_GLSL_SAMPLE_PROJECTED 0x1
#define WINED3D_GLSL_SAMPLE_RECT 0x2 #define WINED3D_GLSL_SAMPLE_RECT 0x2
#define WINED3D_GLSL_SAMPLE_LOD 0x4 #define WINED3D_GLSL_SAMPLE_LOD 0x4
@ -89,7 +87,8 @@ struct shader_glsl_priv {
struct constant_heap vconst_heap; struct constant_heap vconst_heap;
struct constant_heap pconst_heap; struct constant_heap pconst_heap;
unsigned char *stack; unsigned char *stack;
GLhandleARB depth_blt_program[tex_type_count]; GLhandleARB depth_blt_program_full[tex_type_count];
GLhandleARB depth_blt_program_masked[tex_type_count];
UINT next_constant_version; UINT next_constant_version;
}; };
@ -255,7 +254,7 @@ static void print_glsl_info_log(const struct wined3d_gl_info *gl_info, GLhandleA
/* GL locking is done by the caller. */ /* GL locking is done by the caller. */
static void shader_glsl_dump_program_source(const struct wined3d_gl_info *gl_info, GLhandleARB program) static void shader_glsl_dump_program_source(const struct wined3d_gl_info *gl_info, GLhandleARB program)
{ {
GLint i, object_count, source_size; GLint i, object_count, source_size = -1;
GLhandleARB *objects; GLhandleARB *objects;
char *source = NULL; char *source = NULL;
@ -275,7 +274,7 @@ static void shader_glsl_dump_program_source(const struct wined3d_gl_info *gl_inf
GL_EXTCALL(glGetObjectParameterivARB(objects[i], GL_OBJECT_SHADER_SOURCE_LENGTH_ARB, &tmp)); GL_EXTCALL(glGetObjectParameterivARB(objects[i], GL_OBJECT_SHADER_SOURCE_LENGTH_ARB, &tmp));
if (!source || source_size < tmp) if (source_size < tmp)
{ {
HeapFree(GetProcessHeap(), 0, source); HeapFree(GetProcessHeap(), 0, source);
@ -719,8 +718,8 @@ static void shader_glsl_load_np2fixup_constants(
static void shader_glsl_load_constants(const struct wined3d_context *context, static void shader_glsl_load_constants(const struct wined3d_context *context,
char usePixelShader, char useVertexShader) char usePixelShader, char useVertexShader)
{ {
IWineD3DDeviceImpl *device = ((IWineD3DSurfaceImpl *)context->surface)->resource.device;
const struct wined3d_gl_info *gl_info = context->gl_info; const struct wined3d_gl_info *gl_info = context->gl_info;
IWineD3DDeviceImpl *device = context->swapchain->device;
IWineD3DStateBlockImpl* stateBlock = device->stateBlock; IWineD3DStateBlockImpl* stateBlock = device->stateBlock;
struct shader_glsl_priv *priv = device->shader_priv; struct shader_glsl_priv *priv = device->shader_priv;
@ -807,7 +806,7 @@ static void shader_glsl_load_constants(const struct wined3d_context *context,
correction_params[1] = 1.0f; correction_params[1] = 1.0f;
} else { } else {
/* position is window relative, not viewport relative */ /* position is window relative, not viewport relative */
correction_params[0] = ((IWineD3DSurfaceImpl *)context->current_rt)->currentDesc.Height; correction_params[0] = context->current_rt->currentDesc.Height;
correction_params[1] = -1.0f; correction_params[1] = -1.0f;
} }
GL_EXTCALL(glUniform4fvARB(prog->ycorrection_location, 1, correction_params)); GL_EXTCALL(glUniform4fvARB(prog->ycorrection_location, 1, correction_params));
@ -1034,7 +1033,7 @@ static void shader_generate_glsl_declarations(const struct wined3d_context *cont
*/ */
FIXME("Cannot find a free uniform for vpos correction params\n"); FIXME("Cannot find a free uniform for vpos correction params\n");
shader_addline(buffer, "const vec4 ycorrection = vec4(%f, %f, 0.0, 0.0);\n", shader_addline(buffer, "const vec4 ycorrection = vec4(%f, %f, 0.0, 0.0);\n",
context->render_offscreen ? 0.0f : ((IWineD3DSurfaceImpl *)device->render_targets[0])->currentDesc.Height, context->render_offscreen ? 0.0f : device->render_targets[0]->currentDesc.Height,
context->render_offscreen ? 1.0f : -1.0f); context->render_offscreen ? 1.0f : -1.0f);
} }
shader_addline(buffer, "vec4 vpos;\n"); shader_addline(buffer, "vec4 vpos;\n");
@ -1048,20 +1047,37 @@ static void shader_generate_glsl_declarations(const struct wined3d_context *cont
switch (reg_maps->sampler_type[i]) switch (reg_maps->sampler_type[i])
{ {
case WINED3DSTT_1D: case WINED3DSTT_1D:
shader_addline(buffer, "uniform sampler1D %csampler%u;\n", prefix, i); if (pshader && ps_args->shadow & (1 << i))
shader_addline(buffer, "uniform sampler1DShadow %csampler%u;\n", prefix, i);
else
shader_addline(buffer, "uniform sampler1D %csampler%u;\n", prefix, i);
break; break;
case WINED3DSTT_2D: case WINED3DSTT_2D:
if(device->stateBlock->textures[i] && if (pshader && ps_args->shadow & (1 << i))
IWineD3DBaseTexture_GetTextureDimensions(device->stateBlock->textures[i]) == GL_TEXTURE_RECTANGLE_ARB) { {
shader_addline(buffer, "uniform sampler2DRect %csampler%u;\n", prefix, i); if (device->stateBlock->textures[i]
} else { && IWineD3DBaseTexture_GetTextureDimensions(device->stateBlock->textures[i])
shader_addline(buffer, "uniform sampler2D %csampler%u;\n", prefix, i); == 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)
shader_addline(buffer, "uniform sampler2DRect %csampler%u;\n", prefix, i);
else
shader_addline(buffer, "uniform sampler2D %csampler%u;\n", prefix, i);
} }
break; break;
case WINED3DSTT_CUBE: case WINED3DSTT_CUBE:
if (pshader && ps_args->shadow & (1 << i)) FIXME("Unsupported Cube shadow sampler.\n");
shader_addline(buffer, "uniform samplerCube %csampler%u;\n", prefix, i); shader_addline(buffer, "uniform samplerCube %csampler%u;\n", prefix, i);
break; break;
case WINED3DSTT_VOLUME: case WINED3DSTT_VOLUME:
if (pshader && ps_args->shadow & (1 << i)) FIXME("Unsupported 3D shadow sampler.\n");
shader_addline(buffer, "uniform sampler3D %csampler%u;\n", prefix, i); shader_addline(buffer, "uniform sampler3D %csampler%u;\n", prefix, i);
break; break;
default: default:
@ -1642,9 +1658,13 @@ static inline const char *shader_get_comp_op(DWORD op)
} }
} }
static void shader_glsl_get_sample_function(const struct wined3d_gl_info *gl_info, static void shader_glsl_get_sample_function(const struct wined3d_shader_context *ctx,
DWORD sampler_type, DWORD flags, glsl_sample_function_t *sample_function) DWORD sampler_idx, DWORD flags, glsl_sample_function_t *sample_function)
{ {
WINED3DSAMPLER_TEXTURE_TYPE sampler_type = ctx->reg_maps->sampler_type[sampler_idx];
const struct wined3d_gl_info *gl_info = ctx->gl_info;
BOOL shadow = shader_is_pshader_version(ctx->reg_maps->shader_version.type)
&& (((const struct shader_glsl_ctx_priv *)ctx->backend_data)->cur_ps_args->shadow & (1 << sampler_idx));
BOOL projected = flags & WINED3D_GLSL_SAMPLE_PROJECTED; BOOL projected = flags & WINED3D_GLSL_SAMPLE_PROJECTED;
BOOL texrect = flags & WINED3D_GLSL_SAMPLE_RECT; BOOL texrect = flags & WINED3D_GLSL_SAMPLE_RECT;
BOOL lod = flags & WINED3D_GLSL_SAMPLE_LOD; BOOL lod = flags & WINED3D_GLSL_SAMPLE_LOD;
@ -1653,115 +1673,225 @@ static void shader_glsl_get_sample_function(const struct wined3d_gl_info *gl_inf
/* Note that there's no such thing as a projected cube texture. */ /* Note that there's no such thing as a projected cube texture. */
switch(sampler_type) { switch(sampler_type) {
case WINED3DSTT_1D: case WINED3DSTT_1D:
if(lod) { if (shadow)
sample_function->name = projected ? "texture1DProjLod" : "texture1DLod";
}
else if (grad)
{ {
if (gl_info->supported[EXT_GPU_SHADER4]) if (lod)
sample_function->name = projected ? "texture1DProjGrad" : "texture1DGrad"; {
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD]) sample_function->name = projected ? "shadow1DProjLod" : "shadow1DLod";
sample_function->name = projected ? "texture1DProjGradARB" : "texture1DGradARB"; }
else if (grad)
{
if (gl_info->supported[EXT_GPU_SHADER4])
sample_function->name = projected ? "shadow1DProjGrad" : "shadow1DGrad";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD])
sample_function->name = projected ? "shadow1DProjGradARB" : "shadow1DGradARB";
else
{
FIXME("Unsupported 1D shadow grad function.\n");
sample_function->name = "unsupported1DGrad";
}
}
else else
{ {
FIXME("Unsupported 1D grad function.\n"); sample_function->name = projected ? "shadow1DProj" : "shadow1D";
sample_function->name = "unsupported1DGrad";
} }
sample_function->coord_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1;
} }
else else
{ {
sample_function->name = projected ? "texture1DProj" : "texture1D"; if (lod)
{
sample_function->name = projected ? "texture1DProjLod" : "texture1DLod";
}
else if (grad)
{
if (gl_info->supported[EXT_GPU_SHADER4])
sample_function->name = projected ? "texture1DProjGrad" : "texture1DGrad";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD])
sample_function->name = projected ? "texture1DProjGradARB" : "texture1DGradARB";
else
{
FIXME("Unsupported 1D grad function.\n");
sample_function->name = "unsupported1DGrad";
}
}
else
{
sample_function->name = projected ? "texture1DProj" : "texture1D";
}
sample_function->coord_mask = WINED3DSP_WRITEMASK_0;
} }
sample_function->coord_mask = WINED3DSP_WRITEMASK_0;
break; break;
case WINED3DSTT_2D: case WINED3DSTT_2D:
if(texrect) { if (shadow)
if(lod) { {
sample_function->name = projected ? "texture2DRectProjLod" : "texture2DRectLod"; if (texrect)
}
else if (grad)
{ {
if (gl_info->supported[EXT_GPU_SHADER4]) if (lod)
sample_function->name = projected ? "texture2DRectProjGrad" : "texture2DRectGrad"; {
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD]) sample_function->name = projected ? "shadow2DRectProjLod" : "shadow2DRectLod";
sample_function->name = projected ? "texture2DRectProjGradARB" : "texture2DRectGradARB"; }
else if (grad)
{
if (gl_info->supported[EXT_GPU_SHADER4])
sample_function->name = projected ? "shadow2DRectProjGrad" : "shadow2DRectGrad";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD])
sample_function->name = projected ? "shadow2DRectProjGradARB" : "shadow2DRectGradARB";
else
{
FIXME("Unsupported RECT shadow grad function.\n");
sample_function->name = "unsupported2DRectGrad";
}
}
else else
{ {
FIXME("Unsupported RECT grad function.\n"); sample_function->name = projected ? "shadow2DRectProj" : "shadow2DRect";
sample_function->name = "unsupported2DRectGrad";
} }
} }
else else
{ {
sample_function->name = projected ? "texture2DRectProj" : "texture2DRect"; if (lod)
} {
} else { sample_function->name = projected ? "shadow2DProjLod" : "shadow2DLod";
if(lod) { }
sample_function->name = projected ? "texture2DProjLod" : "texture2DLod"; else if (grad)
} {
else if (grad) if (gl_info->supported[EXT_GPU_SHADER4])
{ sample_function->name = projected ? "shadow2DProjGrad" : "shadow2DGrad";
if (gl_info->supported[EXT_GPU_SHADER4]) else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD])
sample_function->name = projected ? "texture2DProjGrad" : "texture2DGrad"; sample_function->name = projected ? "shadow2DProjGradARB" : "shadow2DGradARB";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD]) else
sample_function->name = projected ? "texture2DProjGradARB" : "texture2DGradARB"; {
FIXME("Unsupported 2D shadow grad function.\n");
sample_function->name = "unsupported2DGrad";
}
}
else else
{ {
FIXME("Unsupported 2D grad function.\n"); sample_function->name = projected ? "shadow2DProj" : "shadow2D";
sample_function->name = "unsupported2DGrad";
} }
} }
else sample_function->coord_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
{ }
sample_function->name = projected ? "texture2DProj" : "texture2D"; else
} {
if (texrect)
{
if (lod)
{
sample_function->name = projected ? "texture2DRectProjLod" : "texture2DRectLod";
}
else if (grad)
{
if (gl_info->supported[EXT_GPU_SHADER4])
sample_function->name = projected ? "texture2DRectProjGrad" : "texture2DRectGrad";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD])
sample_function->name = projected ? "texture2DRectProjGradARB" : "texture2DRectGradARB";
else
{
FIXME("Unsupported RECT grad function.\n");
sample_function->name = "unsupported2DRectGrad";
}
}
else
{
sample_function->name = projected ? "texture2DRectProj" : "texture2DRect";
}
}
else
{
if (lod)
{
sample_function->name = projected ? "texture2DProjLod" : "texture2DLod";
}
else if (grad)
{
if (gl_info->supported[EXT_GPU_SHADER4])
sample_function->name = projected ? "texture2DProjGrad" : "texture2DGrad";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD])
sample_function->name = projected ? "texture2DProjGradARB" : "texture2DGradARB";
else
{
FIXME("Unsupported 2D grad function.\n");
sample_function->name = "unsupported2DGrad";
}
}
else
{
sample_function->name = projected ? "texture2DProj" : "texture2D";
}
}
sample_function->coord_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1;
} }
sample_function->coord_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1;
break; break;
case WINED3DSTT_CUBE: case WINED3DSTT_CUBE:
if(lod) { if (shadow)
sample_function->name = "textureCubeLod";
}
else if (grad)
{ {
if (gl_info->supported[EXT_GPU_SHADER4]) FIXME("Unsupported Cube shadow function.\n ");
sample_function->name = "textureCubeGrad"; sample_function->name = "unsupportedCubeShadow";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD]) sample_function->coord_mask = 0;
sample_function->name = "textureCubeGradARB";
else
{
FIXME("Unsupported Cube grad function.\n");
sample_function->name = "unsupportedCubeGrad";
}
} }
else else
{ {
sample_function->name = "textureCube"; if (lod)
{
sample_function->name = "textureCubeLod";
}
else if (grad)
{
if (gl_info->supported[EXT_GPU_SHADER4])
sample_function->name = "textureCubeGrad";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD])
sample_function->name = "textureCubeGradARB";
else
{
FIXME("Unsupported Cube grad function.\n");
sample_function->name = "unsupportedCubeGrad";
}
}
else
{
sample_function->name = "textureCube";
}
sample_function->coord_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
} }
sample_function->coord_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
break; break;
case WINED3DSTT_VOLUME: case WINED3DSTT_VOLUME:
if(lod) { if (shadow)
sample_function->name = projected ? "texture3DProjLod" : "texture3DLod";
}
else if (grad)
{ {
if (gl_info->supported[EXT_GPU_SHADER4]) FIXME("Unsupported 3D shadow function.\n ");
sample_function->name = projected ? "texture3DProjGrad" : "texture3DGrad"; sample_function->name = "unsupported3DShadow";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD]) sample_function->coord_mask = 0;
sample_function->name = projected ? "texture3DProjGradARB" : "texture3DGradARB";
else
{
FIXME("Unsupported 3D grad function.\n");
sample_function->name = "unsupported3DGrad";
}
} }
else else
{ {
sample_function->name = projected ? "texture3DProj" : "texture3D"; if (lod)
{
sample_function->name = projected ? "texture3DProjLod" : "texture3DLod";
}
else if (grad)
{
if (gl_info->supported[EXT_GPU_SHADER4])
sample_function->name = projected ? "texture3DProjGrad" : "texture3DGrad";
else if (gl_info->supported[ARB_SHADER_TEXTURE_LOD])
sample_function->name = projected ? "texture3DProjGradARB" : "texture3DGradARB";
else
{
FIXME("Unsupported 3D grad function.\n");
sample_function->name = "unsupported3DGrad";
}
}
else
{
sample_function->name = projected ? "texture3DProj" : "texture3D";
}
sample_function->coord_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
} }
sample_function->coord_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
break; break;
default: default:
sample_function->name = ""; sample_function->name = "";
sample_function->coord_mask = 0; sample_function->coord_mask = 0;
@ -2164,16 +2294,26 @@ static void shader_glsl_nrm(const struct wined3d_shader_instruction *ins)
{ {
struct wined3d_shader_buffer *buffer = ins->ctx->buffer; struct wined3d_shader_buffer *buffer = ins->ctx->buffer;
glsl_src_param_t src_param; glsl_src_param_t src_param;
unsigned int mask_size;
DWORD write_mask; DWORD write_mask;
char dst_mask[6]; char dst_mask[6];
write_mask = shader_glsl_get_write_mask(ins->dst, dst_mask); write_mask = shader_glsl_get_write_mask(ins->dst, dst_mask);
mask_size = shader_glsl_get_write_mask_size(write_mask);
shader_glsl_add_src_param(ins, &ins->src[0], write_mask, &src_param); shader_glsl_add_src_param(ins, &ins->src[0], write_mask, &src_param);
shader_addline(buffer, "tmp0.x = length(%s);\n", src_param.param_str); shader_addline(buffer, "tmp0.x = length(%s);\n", src_param.param_str);
shader_glsl_append_dst(buffer, ins); shader_glsl_append_dst(buffer, ins);
shader_addline(buffer, "tmp0.x == 0.0 ? (%s * FLT_MAX) : (%s / tmp0.x));", if (mask_size > 1)
src_param.param_str, src_param.param_str); {
shader_addline(buffer, "tmp0.x == 0.0 ? vec%u(0.0) : (%s / tmp0.x));\n",
mask_size, src_param.param_str);
}
else
{
shader_addline(buffer, "tmp0.x == 0.0 ? 0.0 : (%s / tmp0.x));\n",
src_param.param_str);
}
} }
/** Process the WINED3DSIO_EXPP instruction in GLSL: /** Process the WINED3DSIO_EXPP instruction in GLSL:
@ -2868,10 +3008,8 @@ static void shader_glsl_tex(const struct wined3d_shader_instruction *ins)
IWineD3DDeviceImpl *deviceImpl = (IWineD3DDeviceImpl *)shader->baseShader.device; IWineD3DDeviceImpl *deviceImpl = (IWineD3DDeviceImpl *)shader->baseShader.device;
DWORD shader_version = WINED3D_SHADER_VERSION(ins->ctx->reg_maps->shader_version.major, DWORD shader_version = WINED3D_SHADER_VERSION(ins->ctx->reg_maps->shader_version.major,
ins->ctx->reg_maps->shader_version.minor); ins->ctx->reg_maps->shader_version.minor);
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
DWORD sample_flags = 0; DWORD sample_flags = 0;
WINED3DSAMPLER_TEXTURE_TYPE sampler_type;
DWORD sampler_idx; DWORD sampler_idx;
DWORD mask = 0, swizzle; DWORD mask = 0, swizzle;
@ -2879,11 +3017,11 @@ static void shader_glsl_tex(const struct wined3d_shader_instruction *ins)
* 2.0+: Use provided sampler source. */ * 2.0+: Use provided sampler source. */
if (shader_version < WINED3D_SHADER_VERSION(2,0)) sampler_idx = ins->dst[0].reg.idx; if (shader_version < WINED3D_SHADER_VERSION(2,0)) sampler_idx = ins->dst[0].reg.idx;
else sampler_idx = ins->src[1].reg.idx; else sampler_idx = ins->src[1].reg.idx;
sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
if (shader_version < WINED3D_SHADER_VERSION(1,4)) if (shader_version < WINED3D_SHADER_VERSION(1,4))
{ {
DWORD flags = deviceImpl->stateBlock->textureState[sampler_idx][WINED3DTSS_TEXTURETRANSFORMFLAGS]; DWORD flags = deviceImpl->stateBlock->textureState[sampler_idx][WINED3DTSS_TEXTURETRANSFORMFLAGS];
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. */ /* 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 & WINED3DTTFF_PROJECTED && sampler_type != WINED3DSTT_CUBE) {
@ -2922,7 +3060,7 @@ static void shader_glsl_tex(const struct wined3d_shader_instruction *ins)
sample_flags |= WINED3D_GLSL_SAMPLE_RECT; sample_flags |= WINED3D_GLSL_SAMPLE_RECT;
} }
shader_glsl_get_sample_function(gl_info, sampler_type, sample_flags, &sample_function); shader_glsl_get_sample_function(ins->ctx, sampler_idx, sample_flags, &sample_function);
mask |= sample_function.coord_mask; mask |= sample_function.coord_mask;
if (shader_version < WINED3D_SHADER_VERSION(2,0)) swizzle = WINED3DSP_NOSWIZZLE; if (shader_version < WINED3D_SHADER_VERSION(2,0)) swizzle = WINED3DSP_NOSWIZZLE;
@ -2960,7 +3098,6 @@ static void shader_glsl_texldd(const struct wined3d_shader_instruction *ins)
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
glsl_src_param_t coord_param, dx_param, dy_param; glsl_src_param_t coord_param, dx_param, dy_param;
DWORD sample_flags = WINED3D_GLSL_SAMPLE_GRAD; DWORD sample_flags = WINED3D_GLSL_SAMPLE_GRAD;
DWORD sampler_type;
DWORD sampler_idx; DWORD sampler_idx;
DWORD swizzle = ins->src[1].swizzle; DWORD swizzle = ins->src[1].swizzle;
@ -2971,13 +3108,12 @@ static void shader_glsl_texldd(const struct wined3d_shader_instruction *ins)
} }
sampler_idx = ins->src[1].reg.idx; sampler_idx = ins->src[1].reg.idx;
sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
if(deviceImpl->stateBlock->textures[sampler_idx] && if(deviceImpl->stateBlock->textures[sampler_idx] &&
IWineD3DBaseTexture_GetTextureDimensions(deviceImpl->stateBlock->textures[sampler_idx]) == GL_TEXTURE_RECTANGLE_ARB) { IWineD3DBaseTexture_GetTextureDimensions(deviceImpl->stateBlock->textures[sampler_idx]) == GL_TEXTURE_RECTANGLE_ARB) {
sample_flags |= WINED3D_GLSL_SAMPLE_RECT; sample_flags |= WINED3D_GLSL_SAMPLE_RECT;
} }
shader_glsl_get_sample_function(gl_info, sampler_type, sample_flags, &sample_function); 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); shader_glsl_add_src_param(ins, &ins->src[0], sample_function.coord_mask, &coord_param);
shader_glsl_add_src_param(ins, &ins->src[2], sample_function.coord_mask, &dx_param); shader_glsl_add_src_param(ins, &ins->src[2], sample_function.coord_mask, &dx_param);
shader_glsl_add_src_param(ins, &ins->src[3], sample_function.coord_mask, &dy_param); shader_glsl_add_src_param(ins, &ins->src[3], sample_function.coord_mask, &dy_param);
@ -2994,17 +3130,15 @@ static void shader_glsl_texldl(const struct wined3d_shader_instruction *ins)
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
glsl_src_param_t coord_param, lod_param; glsl_src_param_t coord_param, lod_param;
DWORD sample_flags = WINED3D_GLSL_SAMPLE_LOD; DWORD sample_flags = WINED3D_GLSL_SAMPLE_LOD;
DWORD sampler_type;
DWORD sampler_idx; DWORD sampler_idx;
DWORD swizzle = ins->src[1].swizzle; DWORD swizzle = ins->src[1].swizzle;
sampler_idx = ins->src[1].reg.idx; sampler_idx = ins->src[1].reg.idx;
sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
if(deviceImpl->stateBlock->textures[sampler_idx] && if(deviceImpl->stateBlock->textures[sampler_idx] &&
IWineD3DBaseTexture_GetTextureDimensions(deviceImpl->stateBlock->textures[sampler_idx]) == GL_TEXTURE_RECTANGLE_ARB) { IWineD3DBaseTexture_GetTextureDimensions(deviceImpl->stateBlock->textures[sampler_idx]) == GL_TEXTURE_RECTANGLE_ARB) {
sample_flags |= WINED3D_GLSL_SAMPLE_RECT; sample_flags |= WINED3D_GLSL_SAMPLE_RECT;
} }
shader_glsl_get_sample_function(gl_info, sampler_type, sample_flags, &sample_function); 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); shader_glsl_add_src_param(ins, &ins->src[0], sample_function.coord_mask, &coord_param);
shader_glsl_add_src_param(ins, &ins->src[0], WINED3DSP_WRITEMASK_3, &lod_param); shader_glsl_add_src_param(ins, &ins->src[0], WINED3DSP_WRITEMASK_3, &lod_param);
@ -3071,12 +3205,10 @@ static void shader_glsl_texcoord(const struct wined3d_shader_instruction *ins)
* then perform a 1D texture lookup from stage dstregnum, place into dst. */ * then perform a 1D texture lookup from stage dstregnum, place into dst. */
static void shader_glsl_texdp3tex(const struct wined3d_shader_instruction *ins) static void shader_glsl_texdp3tex(const struct wined3d_shader_instruction *ins)
{ {
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
glsl_src_param_t src0_param; glsl_src_param_t src0_param;
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
DWORD sampler_idx = ins->dst[0].reg.idx; DWORD sampler_idx = ins->dst[0].reg.idx;
DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2; DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
WINED3DSAMPLER_TEXTURE_TYPE sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
UINT mask_size; UINT mask_size;
shader_glsl_add_src_param(ins, &ins->src[0], src_mask, &src0_param); shader_glsl_add_src_param(ins, &ins->src[0], src_mask, &src0_param);
@ -3086,7 +3218,7 @@ static void shader_glsl_texdp3tex(const struct wined3d_shader_instruction *ins)
* *
* It is a dependent read - not valid with conditional NP2 textures * It is a dependent read - not valid with conditional NP2 textures
*/ */
shader_glsl_get_sample_function(gl_info, sampler_type, 0, &sample_function); shader_glsl_get_sample_function(ins->ctx, sampler_idx, 0, &sample_function);
mask_size = shader_glsl_get_write_mask_size(sample_function.coord_mask); mask_size = shader_glsl_get_write_mask_size(sample_function.coord_mask);
switch(mask_size) switch(mask_size)
@ -3199,18 +3331,16 @@ static void shader_glsl_texm3x3pad(const struct wined3d_shader_instruction *ins)
static void shader_glsl_texm3x2tex(const struct wined3d_shader_instruction *ins) static void shader_glsl_texm3x2tex(const struct wined3d_shader_instruction *ins)
{ {
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2; DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
DWORD reg = ins->dst[0].reg.idx; DWORD reg = ins->dst[0].reg.idx;
struct wined3d_shader_buffer *buffer = ins->ctx->buffer; struct wined3d_shader_buffer *buffer = ins->ctx->buffer;
glsl_src_param_t src0_param; glsl_src_param_t src0_param;
WINED3DSAMPLER_TEXTURE_TYPE sampler_type = ins->ctx->reg_maps->sampler_type[reg];
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
shader_glsl_add_src_param(ins, &ins->src[0], src_mask, &src0_param); shader_glsl_add_src_param(ins, &ins->src[0], src_mask, &src0_param);
shader_addline(buffer, "tmp0.y = dot(T%u.xyz, %s);\n", reg, src0_param.param_str); shader_addline(buffer, "tmp0.y = dot(T%u.xyz, %s);\n", reg, src0_param.param_str);
shader_glsl_get_sample_function(gl_info, sampler_type, 0, &sample_function); shader_glsl_get_sample_function(ins->ctx, reg, 0, &sample_function);
/* Sample the texture using the calculated coordinates */ /* Sample the texture using the calculated coordinates */
shader_glsl_gen_sample_code(ins, reg, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, "tmp0.xy"); shader_glsl_gen_sample_code(ins, reg, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, "tmp0.xy");
@ -3223,17 +3353,15 @@ static void shader_glsl_texm3x3tex(const struct wined3d_shader_instruction *ins)
DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2; DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader; IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
SHADER_PARSE_STATE *current_state = &shader->baseShader.parse_state; SHADER_PARSE_STATE *current_state = &shader->baseShader.parse_state;
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
glsl_src_param_t src0_param; glsl_src_param_t src0_param;
DWORD reg = ins->dst[0].reg.idx; DWORD reg = ins->dst[0].reg.idx;
WINED3DSAMPLER_TEXTURE_TYPE sampler_type = ins->ctx->reg_maps->sampler_type[reg];
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
shader_glsl_add_src_param(ins, &ins->src[0], src_mask, &src0_param); shader_glsl_add_src_param(ins, &ins->src[0], src_mask, &src0_param);
shader_addline(ins->ctx->buffer, "tmp0.z = dot(T%u.xyz, %s);\n", reg, src0_param.param_str); shader_addline(ins->ctx->buffer, "tmp0.z = dot(T%u.xyz, %s);\n", reg, src0_param.param_str);
/* Dependent read, not valid with conditional NP2 */ /* Dependent read, not valid with conditional NP2 */
shader_glsl_get_sample_function(gl_info, sampler_type, 0, &sample_function); shader_glsl_get_sample_function(ins->ctx, reg, 0, &sample_function);
/* Sample the texture using the calculated coordinates */ /* Sample the texture using the calculated coordinates */
shader_glsl_gen_sample_code(ins, reg, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, "tmp0.xyz"); shader_glsl_gen_sample_code(ins, reg, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, "tmp0.xyz");
@ -3266,13 +3394,11 @@ static void shader_glsl_texm3x3(const struct wined3d_shader_instruction *ins)
static void shader_glsl_texm3x3spec(const struct wined3d_shader_instruction *ins) static void shader_glsl_texm3x3spec(const struct wined3d_shader_instruction *ins)
{ {
IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader; IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
DWORD reg = ins->dst[0].reg.idx; DWORD reg = ins->dst[0].reg.idx;
glsl_src_param_t src0_param; glsl_src_param_t src0_param;
glsl_src_param_t src1_param; glsl_src_param_t src1_param;
struct wined3d_shader_buffer *buffer = ins->ctx->buffer; struct wined3d_shader_buffer *buffer = ins->ctx->buffer;
SHADER_PARSE_STATE* current_state = &shader->baseShader.parse_state; SHADER_PARSE_STATE* current_state = &shader->baseShader.parse_state;
WINED3DSAMPLER_TEXTURE_TYPE stype = ins->ctx->reg_maps->sampler_type[reg];
DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2; DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
@ -3285,7 +3411,7 @@ static void shader_glsl_texm3x3spec(const struct wined3d_shader_instruction *ins
shader_addline(buffer, "tmp0.xyz = -reflect((%s), normalize(tmp0.xyz));\n", src1_param.param_str); shader_addline(buffer, "tmp0.xyz = -reflect((%s), normalize(tmp0.xyz));\n", src1_param.param_str);
/* Dependent read, not valid with conditional NP2 */ /* Dependent read, not valid with conditional NP2 */
shader_glsl_get_sample_function(gl_info, stype, 0, &sample_function); shader_glsl_get_sample_function(ins->ctx, reg, 0, &sample_function);
/* Sample the texture */ /* Sample the texture */
shader_glsl_gen_sample_code(ins, reg, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, "tmp0.xyz"); shader_glsl_gen_sample_code(ins, reg, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, "tmp0.xyz");
@ -3298,13 +3424,11 @@ static void shader_glsl_texm3x3spec(const struct wined3d_shader_instruction *ins
static void shader_glsl_texm3x3vspec(const struct wined3d_shader_instruction *ins) static void shader_glsl_texm3x3vspec(const struct wined3d_shader_instruction *ins)
{ {
IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader; IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
DWORD reg = ins->dst[0].reg.idx; DWORD reg = ins->dst[0].reg.idx;
struct wined3d_shader_buffer *buffer = ins->ctx->buffer; struct wined3d_shader_buffer *buffer = ins->ctx->buffer;
SHADER_PARSE_STATE* current_state = &shader->baseShader.parse_state; SHADER_PARSE_STATE* current_state = &shader->baseShader.parse_state;
glsl_src_param_t src0_param; glsl_src_param_t src0_param;
DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2; DWORD src_mask = WINED3DSP_WRITEMASK_0 | WINED3DSP_WRITEMASK_1 | WINED3DSP_WRITEMASK_2;
WINED3DSAMPLER_TEXTURE_TYPE sampler_type = ins->ctx->reg_maps->sampler_type[reg];
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
shader_glsl_add_src_param(ins, &ins->src[0], src_mask, &src0_param); shader_glsl_add_src_param(ins, &ins->src[0], src_mask, &src0_param);
@ -3318,7 +3442,7 @@ static void shader_glsl_texm3x3vspec(const struct wined3d_shader_instruction *in
shader_addline(buffer, "tmp0.xyz = -reflect(tmp1.xyz, normalize(tmp0.xyz));\n"); shader_addline(buffer, "tmp0.xyz = -reflect(tmp1.xyz, normalize(tmp0.xyz));\n");
/* Dependent read, not valid with conditional NP2 */ /* Dependent read, not valid with conditional NP2 */
shader_glsl_get_sample_function(gl_info, sampler_type, 0, &sample_function); shader_glsl_get_sample_function(ins->ctx, reg, 0, &sample_function);
/* Sample the texture using the calculated coordinates */ /* Sample the texture using the calculated coordinates */
shader_glsl_gen_sample_code(ins, reg, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, "tmp0.xyz"); shader_glsl_gen_sample_code(ins, reg, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, "tmp0.xyz");
@ -3334,10 +3458,8 @@ static void shader_glsl_texbem(const struct wined3d_shader_instruction *ins)
{ {
IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader; IWineD3DBaseShaderImpl *shader = (IWineD3DBaseShaderImpl *)ins->ctx->shader;
IWineD3DDeviceImpl *deviceImpl = (IWineD3DDeviceImpl *)shader->baseShader.device; IWineD3DDeviceImpl *deviceImpl = (IWineD3DDeviceImpl *)shader->baseShader.device;
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
glsl_src_param_t coord_param; glsl_src_param_t coord_param;
WINED3DSAMPLER_TEXTURE_TYPE sampler_type;
DWORD sampler_idx; DWORD sampler_idx;
DWORD mask; DWORD mask;
DWORD flags; DWORD flags;
@ -3346,9 +3468,8 @@ static void shader_glsl_texbem(const struct wined3d_shader_instruction *ins)
sampler_idx = ins->dst[0].reg.idx; sampler_idx = ins->dst[0].reg.idx;
flags = deviceImpl->stateBlock->textureState[sampler_idx][WINED3DTSS_TEXTURETRANSFORMFLAGS]; flags = deviceImpl->stateBlock->textureState[sampler_idx][WINED3DTSS_TEXTURETRANSFORMFLAGS];
sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
/* Dependent read, not valid with conditional NP2 */ /* Dependent read, not valid with conditional NP2 */
shader_glsl_get_sample_function(gl_info, sampler_type, 0, &sample_function); shader_glsl_get_sample_function(ins->ctx, sampler_idx, 0, &sample_function);
mask = sample_function.coord_mask; mask = sample_function.coord_mask;
shader_glsl_write_mask_to_str(mask, coord_mask); shader_glsl_write_mask_to_str(mask, coord_mask);
@ -3407,15 +3528,13 @@ static void shader_glsl_bem(const struct wined3d_shader_instruction *ins)
* Sample 2D texture at dst using the alpha & red (wx) components of src as texture coordinates */ * Sample 2D texture at dst using the alpha & red (wx) components of src as texture coordinates */
static void shader_glsl_texreg2ar(const struct wined3d_shader_instruction *ins) static void shader_glsl_texreg2ar(const struct wined3d_shader_instruction *ins)
{ {
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
glsl_src_param_t src0_param; glsl_src_param_t src0_param;
DWORD sampler_idx = ins->dst[0].reg.idx; DWORD sampler_idx = ins->dst[0].reg.idx;
WINED3DSAMPLER_TEXTURE_TYPE sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
shader_glsl_add_src_param(ins, &ins->src[0], WINED3DSP_WRITEMASK_ALL, &src0_param); shader_glsl_add_src_param(ins, &ins->src[0], WINED3DSP_WRITEMASK_ALL, &src0_param);
shader_glsl_get_sample_function(gl_info, sampler_type, 0, &sample_function); shader_glsl_get_sample_function(ins->ctx, sampler_idx, 0, &sample_function);
shader_glsl_gen_sample_code(ins, sampler_idx, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, shader_glsl_gen_sample_code(ins, sampler_idx, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL,
"%s.wx", src0_param.reg_name); "%s.wx", src0_param.reg_name);
} }
@ -3424,15 +3543,13 @@ static void shader_glsl_texreg2ar(const struct wined3d_shader_instruction *ins)
* Sample 2D texture at dst using the green & blue (yz) components of src as texture coordinates */ * Sample 2D texture at dst using the green & blue (yz) components of src as texture coordinates */
static void shader_glsl_texreg2gb(const struct wined3d_shader_instruction *ins) static void shader_glsl_texreg2gb(const struct wined3d_shader_instruction *ins)
{ {
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
glsl_src_param_t src0_param; glsl_src_param_t src0_param;
DWORD sampler_idx = ins->dst[0].reg.idx; DWORD sampler_idx = ins->dst[0].reg.idx;
WINED3DSAMPLER_TEXTURE_TYPE sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
shader_glsl_add_src_param(ins, &ins->src[0], WINED3DSP_WRITEMASK_ALL, &src0_param); shader_glsl_add_src_param(ins, &ins->src[0], WINED3DSP_WRITEMASK_ALL, &src0_param);
shader_glsl_get_sample_function(gl_info, sampler_type, 0, &sample_function); shader_glsl_get_sample_function(ins->ctx, sampler_idx, 0, &sample_function);
shader_glsl_gen_sample_code(ins, sampler_idx, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, shader_glsl_gen_sample_code(ins, sampler_idx, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL,
"%s.yz", src0_param.reg_name); "%s.yz", src0_param.reg_name);
} }
@ -3441,14 +3558,12 @@ static void shader_glsl_texreg2gb(const struct wined3d_shader_instruction *ins)
* Sample texture at dst using the rgb (xyz) components of src as texture coordinates */ * Sample texture at dst using the rgb (xyz) components of src as texture coordinates */
static void shader_glsl_texreg2rgb(const struct wined3d_shader_instruction *ins) static void shader_glsl_texreg2rgb(const struct wined3d_shader_instruction *ins)
{ {
const struct wined3d_gl_info *gl_info = ins->ctx->gl_info;
glsl_src_param_t src0_param; glsl_src_param_t src0_param;
DWORD sampler_idx = ins->dst[0].reg.idx; DWORD sampler_idx = ins->dst[0].reg.idx;
WINED3DSAMPLER_TEXTURE_TYPE sampler_type = ins->ctx->reg_maps->sampler_type[sampler_idx];
glsl_sample_function_t sample_function; glsl_sample_function_t sample_function;
/* Dependent read, not valid with conditional NP2 */ /* Dependent read, not valid with conditional NP2 */
shader_glsl_get_sample_function(gl_info, sampler_type, 0, &sample_function); shader_glsl_get_sample_function(ins->ctx, sampler_idx, 0, &sample_function);
shader_glsl_add_src_param(ins, &ins->src[0], sample_function.coord_mask, &src0_param); shader_glsl_add_src_param(ins, &ins->src[0], sample_function.coord_mask, &src0_param);
shader_glsl_gen_sample_code(ins, sampler_idx, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL, shader_glsl_gen_sample_code(ins, sampler_idx, &sample_function, WINED3DSP_NOSWIZZLE, NULL, NULL, NULL,
@ -4453,10 +4568,12 @@ static void set_glsl_shader_program(const struct wined3d_context *context,
} }
/* GL locking is done by the caller */ /* GL locking is done by the caller */
static GLhandleARB create_glsl_blt_shader(const struct wined3d_gl_info *gl_info, enum tex_types tex_type) static GLhandleARB create_glsl_blt_shader(const struct wined3d_gl_info *gl_info, enum tex_types tex_type, BOOL masked)
{ {
GLhandleARB program_id; GLhandleARB program_id;
GLhandleARB vshader_id, pshader_id; GLhandleARB vshader_id, pshader_id;
const char *blt_pshader;
static const char *blt_vshader[] = static const char *blt_vshader[] =
{ {
"#version 120\n" "#version 120\n"
@ -4468,7 +4585,7 @@ static GLhandleARB create_glsl_blt_shader(const struct wined3d_gl_info *gl_info,
"}\n" "}\n"
}; };
static const char *blt_pshaders[tex_type_count] = static const char *blt_pshaders_full[tex_type_count] =
{ {
/* tex_1d */ /* tex_1d */
NULL, NULL,
@ -4498,7 +4615,44 @@ static GLhandleARB create_glsl_blt_shader(const struct wined3d_gl_info *gl_info,
"}\n", "}\n",
}; };
if (!blt_pshaders[tex_type]) static const char *blt_pshaders_masked[tex_type_count] =
{
/* tex_1d */
NULL,
/* tex_2d */
"#version 120\n"
"uniform sampler2D sampler;\n"
"uniform vec4 mask;\n"
"void main(void)\n"
"{\n"
" if (all(lessThan(gl_FragCoord.xy, mask.zw))) discard;\n"
" gl_FragDepth = texture2D(sampler, gl_TexCoord[0].xy).x;\n"
"}\n",
/* tex_3d */
NULL,
/* tex_cube */
"#version 120\n"
"uniform samplerCube sampler;\n"
"uniform vec4 mask;\n"
"void main(void)\n"
"{\n"
" if (all(lessThan(gl_FragCoord.xy, mask.zw))) discard;\n"
" gl_FragDepth = textureCube(sampler, gl_TexCoord[0].xyz).x;\n"
"}\n",
/* tex_rect */
"#version 120\n"
"#extension GL_ARB_texture_rectangle : enable\n"
"uniform sampler2DRect sampler;\n"
"uniform vec4 mask;\n"
"void main(void)\n"
"{\n"
" if (all(lessThan(gl_FragCoord.xy, mask.zw))) discard;\n"
" gl_FragDepth = texture2DRect(sampler, gl_TexCoord[0].xy).x;\n"
"}\n",
};
blt_pshader = masked ? blt_pshaders_masked[tex_type] : blt_pshaders_full[tex_type];
if (!blt_pshader)
{ {
FIXME("tex_type %#x not supported\n", tex_type); FIXME("tex_type %#x not supported\n", tex_type);
tex_type = tex_2d; tex_type = tex_2d;
@ -4509,7 +4663,7 @@ static GLhandleARB create_glsl_blt_shader(const struct wined3d_gl_info *gl_info,
GL_EXTCALL(glCompileShaderARB(vshader_id)); GL_EXTCALL(glCompileShaderARB(vshader_id));
pshader_id = GL_EXTCALL(glCreateShaderObjectARB(GL_FRAGMENT_SHADER_ARB)); pshader_id = GL_EXTCALL(glCreateShaderObjectARB(GL_FRAGMENT_SHADER_ARB));
GL_EXTCALL(glShaderSourceARB(pshader_id, 1, &blt_pshaders[tex_type], NULL)); GL_EXTCALL(glShaderSourceARB(pshader_id, 1, &blt_pshader, NULL));
GL_EXTCALL(glCompileShaderARB(pshader_id)); GL_EXTCALL(glCompileShaderARB(pshader_id));
program_id = GL_EXTCALL(glCreateProgramObjectARB()); program_id = GL_EXTCALL(glCreateProgramObjectARB());
@ -4530,8 +4684,8 @@ static GLhandleARB create_glsl_blt_shader(const struct wined3d_gl_info *gl_info,
/* GL locking is done by the caller */ /* GL locking is done by the caller */
static void shader_glsl_select(const struct wined3d_context *context, BOOL usePS, BOOL useVS) static void shader_glsl_select(const struct wined3d_context *context, BOOL usePS, BOOL useVS)
{ {
IWineD3DDeviceImpl *device = ((IWineD3DSurfaceImpl *)context->surface)->resource.device;
const struct wined3d_gl_info *gl_info = context->gl_info; const struct wined3d_gl_info *gl_info = context->gl_info;
IWineD3DDeviceImpl *device = context->swapchain->device;
struct shader_glsl_priv *priv = device->shader_priv; struct shader_glsl_priv *priv = device->shader_priv;
GLhandleARB program_id = 0; GLhandleARB program_id = 0;
GLenum old_vertex_color_clamp, current_vertex_color_clamp; GLenum old_vertex_color_clamp, current_vertex_color_clamp;
@ -4571,21 +4725,34 @@ static void shader_glsl_select(const struct wined3d_context *context, BOOL usePS
} }
/* GL locking is done by the caller */ /* GL locking is done by the caller */
static void shader_glsl_select_depth_blt(IWineD3DDevice *iface, enum tex_types tex_type) { static void shader_glsl_select_depth_blt(IWineD3DDevice *iface,
enum tex_types tex_type, const SIZE *ds_mask_size)
{
IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
const struct wined3d_gl_info *gl_info = &This->adapter->gl_info; const struct wined3d_gl_info *gl_info = &This->adapter->gl_info;
BOOL masked = ds_mask_size->cx && ds_mask_size->cy;
struct shader_glsl_priv *priv = This->shader_priv; struct shader_glsl_priv *priv = This->shader_priv;
GLhandleARB *blt_program = &priv->depth_blt_program[tex_type]; GLhandleARB *blt_program;
GLint loc;
if (!*blt_program) { blt_program = masked ? &priv->depth_blt_program_masked[tex_type] : &priv->depth_blt_program_full[tex_type];
GLint loc; if (!*blt_program)
*blt_program = create_glsl_blt_shader(gl_info, tex_type); {
*blt_program = create_glsl_blt_shader(gl_info, tex_type, masked);
loc = GL_EXTCALL(glGetUniformLocationARB(*blt_program, "sampler")); loc = GL_EXTCALL(glGetUniformLocationARB(*blt_program, "sampler"));
GL_EXTCALL(glUseProgramObjectARB(*blt_program)); GL_EXTCALL(glUseProgramObjectARB(*blt_program));
GL_EXTCALL(glUniform1iARB(loc, 0)); GL_EXTCALL(glUniform1iARB(loc, 0));
} else { }
else
{
GL_EXTCALL(glUseProgramObjectARB(*blt_program)); GL_EXTCALL(glUseProgramObjectARB(*blt_program));
} }
if (masked)
{
loc = GL_EXTCALL(glGetUniformLocationARB(*blt_program, "mask"));
GL_EXTCALL(glUniform4fARB(loc, 0.0f, 0.0f, (float)ds_mask_size->cx, (float)ds_mask_size->cy));
}
} }
/* GL locking is done by the caller */ /* GL locking is done by the caller */
@ -4625,7 +4792,7 @@ static void shader_glsl_destroy(IWineD3DBaseShader *iface) {
return; return;
} }
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
gl_info = context->gl_info; gl_info = context->gl_info;
if (priv->glsl_program && (IWineD3DBaseShader *)priv->glsl_program->pshader == iface) if (priv->glsl_program && (IWineD3DBaseShader *)priv->glsl_program->pshader == iface)
@ -4644,7 +4811,7 @@ static void shader_glsl_destroy(IWineD3DBaseShader *iface) {
return; return;
} }
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
gl_info = context->gl_info; gl_info = context->gl_info;
if (priv->glsl_program && (IWineD3DBaseShader *)priv->glsl_program->vshader == iface) if (priv->glsl_program && (IWineD3DBaseShader *)priv->glsl_program->vshader == iface)
@ -4821,9 +4988,13 @@ static void shader_glsl_free(IWineD3DDevice *iface) {
ENTER_GL(); ENTER_GL();
for (i = 0; i < tex_type_count; ++i) for (i = 0; i < tex_type_count; ++i)
{ {
if (priv->depth_blt_program[i]) if (priv->depth_blt_program_full[i])
{ {
GL_EXTCALL(glDeleteObjectARB(priv->depth_blt_program[i])); GL_EXTCALL(glDeleteObjectARB(priv->depth_blt_program_full[i]));
}
if (priv->depth_blt_program_masked[i])
{
GL_EXTCALL(glDeleteObjectARB(priv->depth_blt_program_masked[i]));
} }
} }
LEAVE_GL(); LEAVE_GL();

View file

@ -28,8 +28,6 @@
WINE_DEFAULT_DEBUG_CHANNEL(d3d); WINE_DEFAULT_DEBUG_CHANNEL(d3d);
#define GLINFO_LOCATION stateblock->device->adapter->gl_info
/* GL locking for state handlers is done by the caller. */ /* 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(DWORD stage, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
@ -137,7 +135,6 @@ void set_tex_op_nvrc(IWineD3DDevice *iface, BOOL is_alpha, int stage, WINED3DTEX
GLenum portion = is_alpha ? GL_ALPHA : GL_RGB; GLenum portion = is_alpha ? GL_ALPHA : GL_RGB;
GLenum target = GL_COMBINER0_NV + stage; GLenum target = GL_COMBINER0_NV + stage;
GLenum output; GLenum output;
IWineD3DStateBlockImpl *stateblock = This->stateBlock; /* For GLINFO_LOCATION */
TRACE("stage %d, is_alpha %d, op %s, arg1 %#x, arg2 %#x, arg3 %#x, texture_idx %d\n", TRACE("stage %d, is_alpha %d, op %s, arg1 %#x, arg2 %#x, arg3 %#x, texture_idx %d\n",
stage, is_alpha, debug_d3dtop(op), arg1, arg2, arg3, texture_idx); stage, is_alpha, debug_d3dtop(op), arg1, arg2, arg3, texture_idx);
@ -579,6 +576,7 @@ static void nvts_bumpenvmat(DWORD state, IWineD3DStateBlockImpl *stateblock, str
{ {
DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1); DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
DWORD mapped_stage = stateblock->device->texUnitMap[stage + 1]; DWORD mapped_stage = stateblock->device->texUnitMap[stage + 1];
const struct wined3d_gl_info *gl_info = context->gl_info;
float mat[2][2]; float mat[2][2];
/* Direct3D sets the matrix in the stage reading the perturbation map. The result is used to /* Direct3D sets the matrix in the stage reading the perturbation map. The result is used to
@ -587,7 +585,7 @@ static void nvts_bumpenvmat(DWORD state, IWineD3DStateBlockImpl *stateblock, str
* map is read from a specified source stage(always stage - 1 for d3d). Thus set the matrix * map is read from a specified source stage(always stage - 1 for d3d). Thus set the matrix
* for stage + 1. Keep the nvrc tex unit mapping in mind too * for stage + 1. Keep the nvrc tex unit mapping in mind too
*/ */
if (mapped_stage < context->gl_info->limits.textures) if (mapped_stage < gl_info->limits.textures)
{ {
GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage)); GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
checkGLcall("GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage))"); checkGLcall("GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage))");
@ -606,6 +604,7 @@ static void nvts_bumpenvmat(DWORD state, IWineD3DStateBlockImpl *stateblock, str
static void nvrc_texfactor(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context) static void nvrc_texfactor(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
{ {
const struct wined3d_gl_info *gl_info = context->gl_info;
float col[4]; float col[4];
D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_TEXTUREFACTOR], col); D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_TEXTUREFACTOR], col);
GL_EXTCALL(glCombinerParameterfvNV(GL_CONSTANT_COLOR0_NV, &col[0])); GL_EXTCALL(glCombinerParameterfvNV(GL_CONSTANT_COLOR0_NV, &col[0]));
@ -629,6 +628,15 @@ static void nvts_enable(IWineD3DDevice *iface, BOOL enable) {
static void nvrc_fragment_get_caps(const struct wined3d_gl_info *gl_info, struct fragment_caps *pCaps) static void nvrc_fragment_get_caps(const struct wined3d_gl_info *gl_info, struct fragment_caps *pCaps)
{ {
pCaps->PrimitiveMiscCaps = WINED3DPMISCCAPS_TSSARGTEMP;
/* The caps below can be supported but aren't handled yet in utils.c
* 'd3dta_to_combiner_input', disable them until support is fixed */
#if 0
if (gl_info->supported[NV_REGISTER_COMBINERS2])
pCaps->PrimitiveMiscCaps |= WINED3DPMISCCAPS_PERSTAGECONSTANT;
#endif
pCaps->TextureOpCaps = WINED3DTEXOPCAPS_ADD | pCaps->TextureOpCaps = WINED3DTEXOPCAPS_ADD |
WINED3DTEXOPCAPS_ADDSIGNED | WINED3DTEXOPCAPS_ADDSIGNED |
WINED3DTEXOPCAPS_ADDSIGNED2X | WINED3DTEXOPCAPS_ADDSIGNED2X |
@ -672,14 +680,6 @@ static void nvrc_fragment_get_caps(const struct wined3d_gl_info *gl_info, struct
pCaps->MaxTextureBlendStages = min(MAX_TEXTURES, gl_info->limits.general_combiners); pCaps->MaxTextureBlendStages = min(MAX_TEXTURES, gl_info->limits.general_combiners);
pCaps->MaxSimultaneousTextures = gl_info->limits.textures; pCaps->MaxSimultaneousTextures = gl_info->limits.textures;
pCaps->PrimitiveMiscCaps |= WINED3DPMISCCAPS_TSSARGTEMP;
/* The caps below can be supported but aren't handled yet in utils.c 'd3dta_to_combiner_input', disable them until support is fixed */
#if 0
if (gl_info->supported[NV_REGISTER_COMBINERS2])
pCaps->PrimitiveMiscCaps |= WINED3DPMISCCAPS_PERSTAGECONSTANT;
#endif
} }
static HRESULT nvrc_fragment_alloc(IWineD3DDevice *iface) { return WINED3D_OK; } static HRESULT nvrc_fragment_alloc(IWineD3DDevice *iface) { return WINED3D_OK; }
@ -713,119 +713,119 @@ static BOOL nvts_color_fixup_supported(struct color_fixup_desc fixup)
static const struct StateEntryTemplate nvrc_fragmentstate_template[] = { static const struct StateEntryTemplate nvrc_fragmentstate_template[] = {
{ STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), nvrc_colorop }, 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), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(0, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(0, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(0, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(1, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(1, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(1, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(2, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(2, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(2, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(3, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(3, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(3, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(4, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(4, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(4, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(5, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(5, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(5, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(6, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(6, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(6, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG1), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG2), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG1), { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG2), { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT01), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT10), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), nvts_bumpenvmat }, NV_TEXTURE_SHADER2 }, { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT11), { STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVMAT00), NULL }, NV_TEXTURE_SHADER2 },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(7, WINED3DTSS_COLORARG0), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), tex_alphaop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAARG0), { STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_TEXTURESTAGE(7, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), nvrc_colorop }, WINED3D_GL_EXT_NONE }, { STATE_TEXTURESTAGE(7, WINED3DTSS_RESULTARG), { STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_PIXELSHADER, { STATE_PIXELSHADER, apply_pixelshader }, WINED3D_GL_EXT_NONE }, { STATE_PIXELSHADER, { STATE_PIXELSHADER, apply_pixelshader }, WINED3D_GL_EXT_NONE },
{ STATE_RENDER(WINED3DRS_SRGBWRITEENABLE), { STATE_PIXELSHADER, apply_pixelshader }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3DRS_SRGBWRITEENABLE), { STATE_PIXELSHADER, NULL }, WINED3D_GL_EXT_NONE },
{ STATE_RENDER(WINED3DRS_TEXTUREFACTOR), { STATE_RENDER(WINED3DRS_TEXTUREFACTOR), nvrc_texfactor }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3DRS_TEXTUREFACTOR), { STATE_RENDER(WINED3DRS_TEXTUREFACTOR), nvrc_texfactor }, WINED3D_GL_EXT_NONE },
{ STATE_RENDER(WINED3DRS_FOGCOLOR), { STATE_RENDER(WINED3DRS_FOGCOLOR), state_fogcolor }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3DRS_FOGCOLOR), { STATE_RENDER(WINED3DRS_FOGCOLOR), state_fogcolor }, WINED3D_GL_EXT_NONE },
{ STATE_RENDER(WINED3DRS_FOGDENSITY), { STATE_RENDER(WINED3DRS_FOGDENSITY), state_fogdensity }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3DRS_FOGDENSITY), { STATE_RENDER(WINED3DRS_FOGDENSITY), state_fogdensity }, WINED3D_GL_EXT_NONE },
{ STATE_RENDER(WINED3DRS_FOGENABLE), { STATE_RENDER(WINED3DRS_FOGENABLE), state_fog_fragpart }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3DRS_FOGENABLE), { STATE_RENDER(WINED3DRS_FOGENABLE), state_fog_fragpart }, WINED3D_GL_EXT_NONE },
{ STATE_RENDER(WINED3DRS_FOGTABLEMODE), { STATE_RENDER(WINED3DRS_FOGENABLE), state_fog_fragpart }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3DRS_FOGTABLEMODE), { STATE_RENDER(WINED3DRS_FOGENABLE), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_RENDER(WINED3DRS_FOGVERTEXMODE), { STATE_RENDER(WINED3DRS_FOGENABLE), state_fog_fragpart }, WINED3D_GL_EXT_NONE }, { 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_FOGSTART), { STATE_RENDER(WINED3DRS_FOGSTART), state_fogstartend }, WINED3D_GL_EXT_NONE },
{ STATE_RENDER(WINED3DRS_FOGEND), { STATE_RENDER(WINED3DRS_FOGSTART), state_fogstartend }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3DRS_FOGEND), { STATE_RENDER(WINED3DRS_FOGSTART), NULL }, WINED3D_GL_EXT_NONE },
{ STATE_SAMPLER(0), { STATE_SAMPLER(0), nvts_texdim }, NV_TEXTURE_SHADER2 }, { STATE_SAMPLER(0), { STATE_SAMPLER(0), nvts_texdim }, NV_TEXTURE_SHADER2 },
{ STATE_SAMPLER(0), { STATE_SAMPLER(0), sampler_texdim }, WINED3D_GL_EXT_NONE }, { STATE_SAMPLER(0), { STATE_SAMPLER(0), sampler_texdim }, WINED3D_GL_EXT_NONE },
{ STATE_SAMPLER(1), { STATE_SAMPLER(1), nvts_texdim }, NV_TEXTURE_SHADER2 }, { STATE_SAMPLER(1), { STATE_SAMPLER(1), nvts_texdim }, NV_TEXTURE_SHADER2 },

View file

@ -74,7 +74,8 @@ static ULONG WINAPI IWineD3DPaletteImpl_Release(IWineD3DPalette *iface) {
} }
/* Not called from the vtable */ /* Not called from the vtable */
DWORD IWineD3DPaletteImpl_Size(DWORD dwFlags) { static DWORD IWineD3DPaletteImpl_Size(DWORD dwFlags)
{
switch (dwFlags & SIZE_BITS) { switch (dwFlags & SIZE_BITS) {
case WINEDDPCAPS_1BIT: return 2; case WINEDDPCAPS_1BIT: return 2;
case WINEDDPCAPS_2BIT: return 4; case WINEDDPCAPS_2BIT: return 4;
@ -183,7 +184,7 @@ static HRESULT WINAPI IWineD3DPaletteImpl_GetParent(IWineD3DPalette *iface, IUn
return WINED3D_OK; return WINED3D_OK;
} }
const IWineD3DPaletteVtbl IWineD3DPalette_Vtbl = static const IWineD3DPaletteVtbl IWineD3DPalette_Vtbl =
{ {
/*** IUnknown ***/ /*** IUnknown ***/
IWineD3DPaletteImpl_QueryInterface, IWineD3DPaletteImpl_QueryInterface,
@ -195,3 +196,33 @@ const IWineD3DPaletteVtbl IWineD3DPalette_Vtbl =
IWineD3DPaletteImpl_GetCaps, IWineD3DPaletteImpl_GetCaps,
IWineD3DPaletteImpl_SetEntries IWineD3DPaletteImpl_SetEntries
}; };
HRESULT wined3d_palette_init(IWineD3DPaletteImpl *palette, IWineD3DDeviceImpl *device,
DWORD flags, const PALETTEENTRY *entries, IUnknown *parent)
{
HRESULT hr;
palette->lpVtbl = &IWineD3DPalette_Vtbl;
palette->ref = 1;
palette->parent = parent;
palette->device = device;
palette->Flags = flags;
palette->palNumEntries = IWineD3DPaletteImpl_Size(flags);
palette->hpal = CreatePalette((const LOGPALETTE *)&palette->palVersion);
if (!palette->hpal)
{
WARN("Failed to create palette.\n");
return E_FAIL;
}
hr = IWineD3DPalette_SetEntries((IWineD3DPalette *)palette, 0, 0, IWineD3DPaletteImpl_Size(flags), entries);
if (FAILED(hr))
{
WARN("Failed to set palette entries, hr %#x.\n", hr);
DeleteObject(palette->hpal);
return hr;
}
return WINED3D_OK;
}

View file

@ -25,33 +25,19 @@
#include "wined3d_private.h" #include "wined3d_private.h"
WINE_DEFAULT_DEBUG_CHANNEL(d3d); WINE_DEFAULT_DEBUG_CHANNEL(d3d);
#define GLINFO_LOCATION (*gl_info)
static HRESULT wined3d_event_query_init(const struct wined3d_gl_info *gl_info, struct wined3d_event_query **query) BOOL wined3d_event_query_supported(const struct wined3d_gl_info *gl_info)
{ {
struct wined3d_event_query *ret; return gl_info->supported[ARB_SYNC] || gl_info->supported[NV_FENCE] || gl_info->supported[APPLE_FENCE];
*query = NULL;
if (!gl_info->supported[ARB_SYNC] && !gl_info->supported[NV_FENCE]
&& !gl_info->supported[APPLE_FENCE]) return E_NOTIMPL;
ret = HeapAlloc(GetProcessHeap(), 0, sizeof(*ret));
if (!ret)
{
ERR("Failed to allocate a wined3d event query structure.\n");
return E_OUTOFMEMORY;
}
ret->context = NULL;
*query = ret;
return WINED3D_OK;
} }
static void wined3d_event_query_destroy(struct wined3d_event_query *query) void wined3d_event_query_destroy(struct wined3d_event_query *query)
{ {
if (query->context) context_free_event_query(query); if (query->context) context_free_event_query(query);
HeapFree(GetProcessHeap(), 0, query); HeapFree(GetProcessHeap(), 0, query);
} }
static enum wined3d_event_query_result wined3d_event_query_test(struct wined3d_event_query *query, IWineD3DDeviceImpl *device) enum wined3d_event_query_result wined3d_event_query_test(struct wined3d_event_query *query, IWineD3DDeviceImpl *device)
{ {
struct wined3d_context *context; struct wined3d_context *context;
const struct wined3d_gl_info *gl_info; const struct wined3d_gl_info *gl_info;
@ -72,7 +58,7 @@ static enum wined3d_event_query_result wined3d_event_query_test(struct wined3d_e
return WINED3D_EVENT_QUERY_WRONG_THREAD; return WINED3D_EVENT_QUERY_WRONG_THREAD;
} }
context = context_acquire(device, query->context->current_rt, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, query->context->current_rt);
gl_info = context->gl_info; gl_info = context->gl_info;
ENTER_GL(); ENTER_GL();
@ -125,7 +111,75 @@ static enum wined3d_event_query_result wined3d_event_query_test(struct wined3d_e
return ret; return ret;
} }
static void wined3d_event_query_issue(struct wined3d_event_query *query, IWineD3DDeviceImpl *device) enum wined3d_event_query_result wined3d_event_query_finish(struct wined3d_event_query *query, IWineD3DDeviceImpl *device)
{
struct wined3d_context *context;
const struct wined3d_gl_info *gl_info;
enum wined3d_event_query_result ret;
TRACE("(%p)\n", query);
if (!query->context)
{
TRACE("Query not started\n");
return WINED3D_EVENT_QUERY_NOT_STARTED;
}
gl_info = query->context->gl_info;
if (query->context->tid != GetCurrentThreadId() && !gl_info->supported[ARB_SYNC])
{
/* A glFinish does not reliably wait for draws in other contexts. The caller has
* to find its own way to cope with the thread switch
*/
WARN("Event query finished from wrong thread\n");
return WINED3D_EVENT_QUERY_WRONG_THREAD;
}
context = context_acquire(device, query->context->current_rt);
ENTER_GL();
if (gl_info->supported[ARB_SYNC])
{
GLenum gl_ret = GL_EXTCALL(glClientWaitSync(query->object.sync, 0, ~(GLuint64)0));
checkGLcall("glClientWaitSync");
switch (gl_ret)
{
case GL_ALREADY_SIGNALED:
case GL_CONDITION_SATISFIED:
ret = WINED3D_EVENT_QUERY_OK;
break;
/* We don't expect a timeout for a ~584 year wait */
default:
ERR("glClientWaitSync returned %#x.\n", gl_ret);
ret = WINED3D_EVENT_QUERY_ERROR;
}
}
else if (context->gl_info->supported[APPLE_FENCE])
{
GL_EXTCALL(glFinishFenceAPPLE(query->object.id));
checkGLcall("glFinishFenceAPPLE");
ret = WINED3D_EVENT_QUERY_OK;
}
else if (context->gl_info->supported[NV_FENCE])
{
GL_EXTCALL(glFinishFenceNV(query->object.id));
checkGLcall("glFinishFenceNV");
ret = WINED3D_EVENT_QUERY_OK;
}
else
{
ERR("Event query created without GL support\n");
ret = WINED3D_EVENT_QUERY_ERROR;
}
LEAVE_GL();
context_release(context);
return ret;
}
void wined3d_event_query_issue(struct wined3d_event_query *query, IWineD3DDeviceImpl *device)
{ {
const struct wined3d_gl_info *gl_info; const struct wined3d_gl_info *gl_info;
struct wined3d_context *context; struct wined3d_context *context;
@ -135,17 +189,17 @@ static void wined3d_event_query_issue(struct wined3d_event_query *query, IWineD3
if (!query->context->gl_info->supported[ARB_SYNC] && query->context->tid != GetCurrentThreadId()) if (!query->context->gl_info->supported[ARB_SYNC] && query->context->tid != GetCurrentThreadId())
{ {
context_free_event_query(query); context_free_event_query(query);
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
context_alloc_event_query(context, query); context_alloc_event_query(context, query);
} }
else else
{ {
context = context_acquire(device, query->context->current_rt, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, query->context->current_rt);
} }
} }
else else
{ {
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
context_alloc_event_query(context, query); context_alloc_event_query(context, query);
} }
@ -293,7 +347,7 @@ static HRESULT WINAPI IWineD3DOcclusionQueryImpl_GetData(IWineD3DQuery* iface,
return S_OK; return S_OK;
} }
context = context_acquire(This->device, query->context->current_rt, CTXUSAGE_RESOURCELOAD); context = context_acquire(This->device, query->context->current_rt);
ENTER_GL(); ENTER_GL();
@ -430,12 +484,12 @@ static HRESULT WINAPI IWineD3DOcclusionQueryImpl_Issue(IWineD3DQuery* iface, D
FIXME("Wrong thread, can't restart query.\n"); FIXME("Wrong thread, can't restart query.\n");
context_free_occlusion_query(query); context_free_occlusion_query(query);
context = context_acquire(This->device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(This->device, NULL);
context_alloc_occlusion_query(context, query); context_alloc_occlusion_query(context, query);
} }
else else
{ {
context = context_acquire(This->device, query->context->current_rt, CTXUSAGE_RESOURCELOAD); context = context_acquire(This->device, query->context->current_rt);
ENTER_GL(); ENTER_GL();
GL_EXTCALL(glEndQueryARB(GL_SAMPLES_PASSED_ARB)); GL_EXTCALL(glEndQueryARB(GL_SAMPLES_PASSED_ARB));
@ -446,7 +500,7 @@ static HRESULT WINAPI IWineD3DOcclusionQueryImpl_Issue(IWineD3DQuery* iface, D
else else
{ {
if (query->context) context_free_occlusion_query(query); if (query->context) context_free_occlusion_query(query);
context = context_acquire(This->device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(This->device, NULL);
context_alloc_occlusion_query(context, query); context_alloc_occlusion_query(context, query);
} }
@ -470,7 +524,7 @@ static HRESULT WINAPI IWineD3DOcclusionQueryImpl_Issue(IWineD3DQuery* iface, D
} }
else else
{ {
context = context_acquire(This->device, query->context->current_rt, CTXUSAGE_RESOURCELOAD); context = context_acquire(This->device, query->context->current_rt);
ENTER_GL(); ENTER_GL();
GL_EXTCALL(glEndQueryARB(GL_SAMPLES_PASSED_ARB)); GL_EXTCALL(glEndQueryARB(GL_SAMPLES_PASSED_ARB));
@ -525,7 +579,6 @@ HRESULT query_init(IWineD3DQueryImpl *query, IWineD3DDeviceImpl *device,
WINED3DQUERYTYPE type, IUnknown *parent) WINED3DQUERYTYPE type, IUnknown *parent)
{ {
const struct wined3d_gl_info *gl_info = &device->adapter->gl_info; const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
HRESULT hr;
switch (type) switch (type)
{ {
@ -548,9 +601,7 @@ HRESULT query_init(IWineD3DQueryImpl *query, IWineD3DDeviceImpl *device,
case WINED3DQUERYTYPE_EVENT: case WINED3DQUERYTYPE_EVENT:
TRACE("Event query.\n"); TRACE("Event query.\n");
query->lpVtbl = &IWineD3DEventQuery_Vtbl; if (!wined3d_event_query_supported(gl_info))
hr = wined3d_event_query_init(gl_info, (struct wined3d_event_query **) &query->extendedData);
if (hr == E_NOTIMPL)
{ {
/* Half-Life 2 needs this query. It does not render the main /* Half-Life 2 needs this query. It does not render the main
* menu correctly otherwise. Pretend to support it, faking * menu correctly otherwise. Pretend to support it, faking
@ -558,9 +609,12 @@ HRESULT query_init(IWineD3DQueryImpl *query, IWineD3DDeviceImpl *device,
* lowering performance. */ * lowering performance. */
FIXME("Event query: Unimplemented, but pretending to be supported.\n"); FIXME("Event query: Unimplemented, but pretending to be supported.\n");
} }
else if(FAILED(hr)) query->lpVtbl = &IWineD3DEventQuery_Vtbl;
query->extendedData = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(struct wined3d_event_query));
if (!query->extendedData)
{ {
return hr; ERR("Failed to allocate event query memory.\n");
return E_OUTOFMEMORY;
} }
break; break;

View file

@ -28,7 +28,7 @@
WINE_DEFAULT_DEBUG_CHANNEL(d3d); WINE_DEFAULT_DEBUG_CHANNEL(d3d);
HRESULT resource_init(IWineD3DResource *iface, WINED3DRESOURCETYPE resource_type, HRESULT resource_init(IWineD3DResource *iface, WINED3DRESOURCETYPE resource_type,
IWineD3DDeviceImpl *device, UINT size, DWORD usage, const struct GlPixelFormatDesc *format_desc, IWineD3DDeviceImpl *device, UINT size, DWORD usage, const struct wined3d_format_desc *format_desc,
WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
{ {
struct IWineD3DResourceClass *resource = &((IWineD3DResourceImpl *)iface)->resource; struct IWineD3DResourceClass *resource = &((IWineD3DResourceImpl *)iface)->resource;
@ -247,11 +247,3 @@ HRESULT resource_get_parent(IWineD3DResource *iface, IUnknown **pParent)
*pParent = This->resource.parent; *pParent = This->resource.parent;
return WINED3D_OK; return WINED3D_OK;
} }
void dumpResources(struct list *list) {
IWineD3DResourceImpl *resource;
LIST_FOR_EACH_ENTRY(resource, list, IWineD3DResourceImpl, resource.resource_list_entry) {
FIXME("Leftover resource %p with type %d,%s\n", resource, IWineD3DResource_GetType((IWineD3DResource *) resource), debug_d3dresourcetype(IWineD3DResource_GetType((IWineD3DResource *) resource)));
}
}

View file

@ -721,6 +721,7 @@ static HRESULT shader_get_registers_used(IWineD3DBaseShader *iface, const struct
else if (ins.handler_idx == WINED3DSIH_MOVA) reg_maps->usesmova = 1; else if (ins.handler_idx == WINED3DSIH_MOVA) reg_maps->usesmova = 1;
else if (ins.handler_idx == WINED3DSIH_IFC) reg_maps->usesifc = 1; else if (ins.handler_idx == WINED3DSIH_IFC) reg_maps->usesifc = 1;
else if (ins.handler_idx == WINED3DSIH_CALL) reg_maps->usescall = 1; else if (ins.handler_idx == WINED3DSIH_CALL) reg_maps->usescall = 1;
else if (ins.handler_idx == WINED3DSIH_RCP) reg_maps->usesrcp = 1;
limit = ins.src_count + (ins.predicate ? 1 : 0); limit = ins.src_count + (ins.predicate ? 1 : 0);
for (i = 0; i < limit; ++i) for (i = 0; i < limit; ++i)
@ -1150,7 +1151,11 @@ void shader_generate_main(IWineD3DBaseShader *iface, struct wined3d_shader_buffe
if (ins.dst_count) fe->shader_read_dst_param(fe_data, &ptr, &dst_param, &dst_rel_addr); if (ins.dst_count) fe->shader_read_dst_param(fe_data, &ptr, &dst_param, &dst_rel_addr);
/* Predication token */ /* Predication token */
if (ins.predicate) ins.predicate = *ptr++; if (ins.predicate)
{
FIXME("Predicates not implemented.\n");
ins.predicate = *ptr++;
}
/* Other source tokens */ /* Other source tokens */
for (i = 0; i < ins.src_count; ++i) for (i = 0; i < ins.src_count; ++i)
@ -1399,7 +1404,7 @@ static void shader_cleanup(IWineD3DBaseShader *iface)
static void shader_none_handle_instruction(const struct wined3d_shader_instruction *ins) {} static void shader_none_handle_instruction(const struct wined3d_shader_instruction *ins) {}
static void shader_none_select(const struct wined3d_context *context, BOOL usePS, BOOL useVS) {} static void shader_none_select(const struct wined3d_context *context, BOOL usePS, BOOL useVS) {}
static void shader_none_select_depth_blt(IWineD3DDevice *iface, enum tex_types tex_type) {} static void shader_none_select_depth_blt(IWineD3DDevice *iface, enum tex_types tex_type, const SIZE *ds_mask_size) {}
static void shader_none_deselect_depth_blt(IWineD3DDevice *iface) {} static void shader_none_deselect_depth_blt(IWineD3DDevice *iface) {}
static void shader_none_update_float_vertex_constants(IWineD3DDevice *iface, UINT start, UINT count) {} static void shader_none_update_float_vertex_constants(IWineD3DDevice *iface, UINT start, UINT count) {}
static void shader_none_update_float_pixel_constants(IWineD3DDevice *iface, UINT start, UINT count) {} static void shader_none_update_float_pixel_constants(IWineD3DDevice *iface, UINT start, UINT count) {}
@ -1414,8 +1419,11 @@ static void shader_none_get_caps(const struct wined3d_gl_info *gl_info, struct s
{ {
/* Set the shader caps to 0 for the none shader backend */ /* Set the shader caps to 0 for the none shader backend */
caps->VertexShaderVersion = 0; caps->VertexShaderVersion = 0;
caps->MaxVertexShaderConst = 0;
caps->PixelShaderVersion = 0; caps->PixelShaderVersion = 0;
caps->PixelShader1xMaxValue = 0.0f; caps->PixelShader1xMaxValue = 0.0f;
caps->MaxPixelShaderConst = 0;
caps->VSClipping = FALSE;
} }
static BOOL shader_none_color_fixup_supported(struct color_fixup_desc fixup) static BOOL shader_none_color_fixup_supported(struct color_fixup_desc fixup)
@ -2017,6 +2025,9 @@ void find_ps_compile_args(IWineD3DPixelShaderImpl *shader,
} }
args->color_fixup[i] = texture->resource.format_desc->color_fixup; args->color_fixup[i] = texture->resource.format_desc->color_fixup;
if (texture->resource.format_desc->Flags & WINED3DFMT_FLAG_SHADOW)
args->shadow |= 1 << i;
/* Flag samplers that need NP2 texcoord fixup. */ /* Flag samplers that need NP2 texcoord fixup. */
if (!texture->baseTexture.pow2Matrix_identity) if (!texture->baseTexture.pow2Matrix_identity)
{ {

File diff suppressed because it is too large Load diff

View file

@ -757,7 +757,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
{ {
TRACE("Updating scissor rect.\n"); TRACE("Updating scissor rect.\n");
targetStateBlock->scissorRect = This->scissorRect; This->scissorRect = targetStateBlock->scissorRect;
} }
map = This->changed.streamSource; map = This->changed.streamSource;
@ -866,7 +866,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Capture(IWineD3DStateBlock *iface)
return WINED3D_OK; return WINED3D_OK;
} }
static void apply_lights(IWineD3DDevice *pDevice, const IWineD3DStateBlockImpl *This) static void apply_lights(IWineD3DDevice *device, const IWineD3DStateBlockImpl *This)
{ {
UINT i; UINT i;
for(i = 0; i < LIGHTMAP_SIZE; i++) { for(i = 0; i < LIGHTMAP_SIZE; i++) {
@ -876,8 +876,8 @@ static void apply_lights(IWineD3DDevice *pDevice, const IWineD3DStateBlockImpl *
{ {
const struct wined3d_light_info *light = LIST_ENTRY(e, struct wined3d_light_info, entry); const struct wined3d_light_info *light = LIST_ENTRY(e, struct wined3d_light_info, entry);
IWineD3DDevice_SetLight(pDevice, light->OriginalIndex, &light->OriginalParms); IWineD3DDevice_SetLight(device, light->OriginalIndex, &light->OriginalParms);
IWineD3DDevice_SetLightEnable(pDevice, light->OriginalIndex, light->glIndex != -1); IWineD3DDevice_SetLightEnable(device, light->OriginalIndex, light->glIndex != -1);
} }
} }
} }
@ -885,58 +885,58 @@ static void apply_lights(IWineD3DDevice *pDevice, const IWineD3DStateBlockImpl *
static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface) static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
{ {
IWineD3DStateBlockImpl *This = (IWineD3DStateBlockImpl *)iface; IWineD3DStateBlockImpl *This = (IWineD3DStateBlockImpl *)iface;
IWineD3DDevice *pDevice = (IWineD3DDevice *)This->device; IWineD3DDevice *device = (IWineD3DDevice *)This->device;
unsigned int i; unsigned int i;
DWORD map; DWORD map;
TRACE("(%p) : Applying state block %p ------------------v\n", This, pDevice); TRACE("(%p) : Applying state block %p ------------------v\n", This, device);
TRACE("Blocktype: %d\n", This->blockType); TRACE("Blocktype: %d\n", This->blockType);
if (This->changed.vertexShader) IWineD3DDevice_SetVertexShader(pDevice, This->vertexShader); if (This->changed.vertexShader) IWineD3DDevice_SetVertexShader(device, This->vertexShader);
/* Vertex Shader Constants */ /* Vertex Shader Constants */
for (i = 0; i < This->num_contained_vs_consts_f; ++i) for (i = 0; i < This->num_contained_vs_consts_f; ++i)
{ {
IWineD3DDevice_SetVertexShaderConstantF(pDevice, This->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->vertexShaderConstantF + This->contained_vs_consts_f[i] * 4, 1);
} }
for (i = 0; i < This->num_contained_vs_consts_i; ++i) for (i = 0; i < This->num_contained_vs_consts_i; ++i)
{ {
IWineD3DDevice_SetVertexShaderConstantI(pDevice, This->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->vertexShaderConstantI + This->contained_vs_consts_i[i] * 4, 1);
} }
for (i = 0; i < This->num_contained_vs_consts_b; ++i) for (i = 0; i < This->num_contained_vs_consts_b; ++i)
{ {
IWineD3DDevice_SetVertexShaderConstantB(pDevice, This->contained_vs_consts_b[i], IWineD3DDevice_SetVertexShaderConstantB(device, This->contained_vs_consts_b[i],
This->vertexShaderConstantB + This->contained_vs_consts_b[i], 1); This->vertexShaderConstantB + This->contained_vs_consts_b[i], 1);
} }
apply_lights(pDevice, This); apply_lights(device, This);
if (This->changed.pixelShader) IWineD3DDevice_SetPixelShader(pDevice, This->pixelShader); if (This->changed.pixelShader) IWineD3DDevice_SetPixelShader(device, This->pixelShader);
/* Pixel Shader Constants */ /* Pixel Shader Constants */
for (i = 0; i < This->num_contained_ps_consts_f; ++i) for (i = 0; i < This->num_contained_ps_consts_f; ++i)
{ {
IWineD3DDevice_SetPixelShaderConstantF(pDevice, This->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->pixelShaderConstantF + This->contained_ps_consts_f[i] * 4, 1);
} }
for (i = 0; i < This->num_contained_ps_consts_i; ++i) for (i = 0; i < This->num_contained_ps_consts_i; ++i)
{ {
IWineD3DDevice_SetPixelShaderConstantI(pDevice, This->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->pixelShaderConstantI + This->contained_ps_consts_i[i] * 4, 1);
} }
for (i = 0; i < This->num_contained_ps_consts_b; ++i) for (i = 0; i < This->num_contained_ps_consts_b; ++i)
{ {
IWineD3DDevice_SetPixelShaderConstantB(pDevice, This->contained_ps_consts_b[i], IWineD3DDevice_SetPixelShaderConstantB(device, This->contained_ps_consts_b[i],
This->pixelShaderConstantB + This->contained_ps_consts_b[i], 1); This->pixelShaderConstantB + This->contained_ps_consts_b[i], 1);
} }
/* Render */ /* Render */
for (i = 0; i < This->num_contained_render_states; ++i) for (i = 0; i < This->num_contained_render_states; ++i)
{ {
IWineD3DDevice_SetRenderState(pDevice, This->contained_render_states[i], IWineD3DDevice_SetRenderState(device, This->contained_render_states[i],
This->renderState[This->contained_render_states[i]]); This->renderState[This->contained_render_states[i]]);
} }
@ -946,7 +946,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
DWORD stage = This->contained_tss_states[i].stage; DWORD stage = This->contained_tss_states[i].stage;
DWORD state = This->contained_tss_states[i].state; DWORD state = This->contained_tss_states[i].state;
IWineD3DDevice_SetTextureStageState(pDevice, stage, state, This->textureState[stage][state]); IWineD3DDevice_SetTextureStageState(device, stage, state, This->textureState[stage][state]);
} }
/* Sampler states */ /* Sampler states */
@ -957,12 +957,12 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
DWORD value = This->samplerState[stage][state]; DWORD value = This->samplerState[stage][state];
if (stage >= MAX_FRAGMENT_SAMPLERS) stage += WINED3DVERTEXTEXTURESAMPLER0 - MAX_FRAGMENT_SAMPLERS; if (stage >= MAX_FRAGMENT_SAMPLERS) stage += WINED3DVERTEXTEXTURESAMPLER0 - MAX_FRAGMENT_SAMPLERS;
IWineD3DDevice_SetSamplerState(pDevice, stage, state, value); IWineD3DDevice_SetSamplerState(device, stage, state, value);
} }
for (i = 0; i < This->num_contained_transform_states; ++i) for (i = 0; i < This->num_contained_transform_states; ++i)
{ {
IWineD3DDevice_SetTransform(pDevice, This->contained_transform_states[i], IWineD3DDevice_SetTransform(device, This->contained_transform_states[i],
&This->transforms[This->contained_transform_states[i]]); &This->transforms[This->contained_transform_states[i]]);
} }
@ -974,40 +974,40 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
if (This->changed.indices) if (This->changed.indices)
{ {
IWineD3DDevice_SetIndexBuffer(pDevice, This->pIndexData, This->IndexFmt); IWineD3DDevice_SetIndexBuffer(device, This->pIndexData, This->IndexFmt);
IWineD3DDevice_SetBaseVertexIndex(pDevice, This->baseVertexIndex); IWineD3DDevice_SetBaseVertexIndex(device, This->baseVertexIndex);
} }
if (This->changed.vertexDecl && This->vertexDecl) if (This->changed.vertexDecl && This->vertexDecl)
{ {
IWineD3DDevice_SetVertexDeclaration(pDevice, This->vertexDecl); IWineD3DDevice_SetVertexDeclaration(device, This->vertexDecl);
} }
if (This->changed.material) if (This->changed.material)
{ {
IWineD3DDevice_SetMaterial(pDevice, &This->material); IWineD3DDevice_SetMaterial(device, &This->material);
} }
if (This->changed.viewport) if (This->changed.viewport)
{ {
IWineD3DDevice_SetViewport(pDevice, &This->viewport); IWineD3DDevice_SetViewport(device, &This->viewport);
} }
if (This->changed.scissorRect) if (This->changed.scissorRect)
{ {
IWineD3DDevice_SetScissorRect(pDevice, &This->scissorRect); IWineD3DDevice_SetScissorRect(device, &This->scissorRect);
} }
map = This->changed.streamSource; map = This->changed.streamSource;
for (i = 0; map; map >>= 1, ++i) for (i = 0; map; map >>= 1, ++i)
{ {
if (map & 1) IWineD3DDevice_SetStreamSource(pDevice, i, This->streamSource[i], 0, This->streamStride[i]); if (map & 1) IWineD3DDevice_SetStreamSource(device, i, This->streamSource[i], 0, This->streamStride[i]);
} }
map = This->changed.streamFreq; map = This->changed.streamFreq;
for (i = 0; map; map >>= 1, ++i) for (i = 0; map; map >>= 1, ++i)
{ {
if (map & 1) IWineD3DDevice_SetStreamSourceFreq(pDevice, i, This->streamFreq[i] | This->streamFlags[i]); if (map & 1) IWineD3DDevice_SetStreamSourceFreq(device, i, This->streamFreq[i] | This->streamFlags[i]);
} }
map = This->changed.textures; map = This->changed.textures;
@ -1018,7 +1018,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
if (!(map & 1)) continue; if (!(map & 1)) continue;
stage = i < MAX_FRAGMENT_SAMPLERS ? i : WINED3DVERTEXTEXTURESAMPLER0 + i - MAX_FRAGMENT_SAMPLERS; stage = i < MAX_FRAGMENT_SAMPLERS ? i : WINED3DVERTEXTEXTURESAMPLER0 + i - MAX_FRAGMENT_SAMPLERS;
IWineD3DDevice_SetTexture(pDevice, stage, This->textures[i]); IWineD3DDevice_SetTexture(device, stage, This->textures[i]);
} }
map = This->changed.clipplane; map = This->changed.clipplane;
@ -1032,7 +1032,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
clip[1] = This->clipplane[i][1]; clip[1] = This->clipplane[i][1];
clip[2] = This->clipplane[i][2]; clip[2] = This->clipplane[i][2];
clip[3] = This->clipplane[i][3]; clip[3] = This->clipplane[i][3];
IWineD3DDevice_SetClipPlane(pDevice, i, clip); IWineD3DDevice_SetClipPlane(device, i, clip);
} }
This->device->stateBlock->lowest_disabled_stage = MAX_TEXTURES - 1; This->device->stateBlock->lowest_disabled_stage = MAX_TEXTURES - 1;
@ -1044,7 +1044,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
break; break;
} }
} }
TRACE("(%p) : Applied state block %p ------------------^\n", This, pDevice); TRACE("(%p) : Applied state block %p ------------------^\n", This, device);
return WINED3D_OK; return WINED3D_OK;
} }
@ -1052,8 +1052,8 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_Apply(IWineD3DStateBlock *iface)
static HRESULT WINAPI IWineD3DStateBlockImpl_InitStartupStateBlock(IWineD3DStateBlock* iface) { static HRESULT WINAPI IWineD3DStateBlockImpl_InitStartupStateBlock(IWineD3DStateBlock* iface) {
IWineD3DStateBlockImpl *This = (IWineD3DStateBlockImpl *)iface; IWineD3DStateBlockImpl *This = (IWineD3DStateBlockImpl *)iface;
IWineD3DDevice *device = (IWineD3DDevice *)This->device; IWineD3DDevice *device = (IWineD3DDevice *)This->device;
IWineD3DDeviceImpl *ThisDevice = (IWineD3DDeviceImpl *)device; IWineD3DDeviceImpl *device_impl = (IWineD3DDeviceImpl *)device;
const struct wined3d_gl_info *gl_info = &ThisDevice->adapter->gl_info; const struct wined3d_gl_info *gl_info = &device_impl->adapter->gl_info;
union { union {
WINED3DLINEPATTERN lp; WINED3DLINEPATTERN lp;
DWORD d; DWORD d;
@ -1070,7 +1070,7 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_InitStartupStateBlock(IWineD3DStat
/* Note this may have a large overhead but it should only be executed /* 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 once, in order to initialize the complete state of the device and
all opengl equivalents */ all opengl equivalents */
TRACE("(%p) -----------------------> Setting up device defaults... %p\n", This, ThisDevice); 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) */ /* 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; This->blockType = WINED3DSBT_INIT;
@ -1083,11 +1083,10 @@ static HRESULT WINAPI IWineD3DStateBlockImpl_InitStartupStateBlock(IWineD3DStat
TRACE("Render states\n"); TRACE("Render states\n");
/* Render states: */ /* Render states: */
if (ThisDevice->auto_depth_stencil_buffer != NULL) { if (device_impl->auto_depth_stencil)
IWineD3DDevice_SetRenderState(device, WINED3DRS_ZENABLE, WINED3DZB_TRUE); IWineD3DDevice_SetRenderState(device, WINED3DRS_ZENABLE, WINED3DZB_TRUE);
} else { else
IWineD3DDevice_SetRenderState(device, WINED3DRS_ZENABLE, WINED3DZB_FALSE); IWineD3DDevice_SetRenderState(device, WINED3DRS_ZENABLE, WINED3DZB_FALSE);
}
IWineD3DDevice_SetRenderState(device, WINED3DRS_FILLMODE, WINED3DFILL_SOLID); IWineD3DDevice_SetRenderState(device, WINED3DRS_FILLMODE, WINED3DFILL_SOLID);
IWineD3DDevice_SetRenderState(device, WINED3DRS_SHADEMODE, WINED3DSHADE_GOURAUD); IWineD3DDevice_SetRenderState(device, WINED3DRS_SHADEMODE, WINED3DSHADE_GOURAUD);
lp.lp.wRepeatFactor = 0; lp.lp.wRepeatFactor = 0;

File diff suppressed because it is too large Load diff

View file

@ -83,9 +83,6 @@ static inline unsigned short float_32_to_16(const float *in)
return ret; return ret;
} }
/* Do NOT define GLINFO_LOCATION in this file. THIS CODE MUST NOT USE IT */
/* ******************************************* /* *******************************************
IWineD3DSurface IUnknown parts follow IWineD3DSurface IUnknown parts follow
******************************************* */ ******************************************* */
@ -326,7 +323,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_GetPalette(IWineD3DSurface *iface, IWineD
DWORD WINAPI IWineD3DBaseSurfaceImpl_GetPitch(IWineD3DSurface *iface) { DWORD WINAPI IWineD3DBaseSurfaceImpl_GetPitch(IWineD3DSurface *iface) {
IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface; IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *) iface;
const struct GlPixelFormatDesc *format_desc = This->resource.format_desc; const struct wined3d_format_desc *format_desc = This->resource.format_desc;
DWORD ret; DWORD ret;
TRACE("(%p)\n", This); TRACE("(%p)\n", This);
@ -502,7 +499,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetContainer(IWineD3DSurface *iface, IWin
HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetFormat(IWineD3DSurface *iface, WINED3DFORMAT format) { HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetFormat(IWineD3DSurface *iface, WINED3DFORMAT format) {
IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface; IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
const struct GlPixelFormatDesc *format_desc = getFormatDescEntry(format, const struct wined3d_format_desc *format_desc = getFormatDescEntry(format,
&This->resource.device->adapter->gl_info); &This->resource.device->adapter->gl_info);
if (This->resource.format_desc->format != WINED3DFMT_UNKNOWN) if (This->resource.format_desc->format != WINED3DFMT_UNKNOWN)
@ -527,7 +524,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_SetFormat(IWineD3DSurface *iface, WINED3D
HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) { HRESULT IWineD3DBaseSurfaceImpl_CreateDIBSection(IWineD3DSurface *iface) {
IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface; IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
const struct GlPixelFormatDesc *format_desc = This->resource.format_desc; const struct wined3d_format_desc *format_desc = This->resource.format_desc;
int extraline = 0; int extraline = 0;
SYSTEM_INFO sysInfo; SYSTEM_INFO sysInfo;
BITMAPINFO* b_info; BITMAPINFO* b_info;
@ -742,6 +739,55 @@ static void convert_a8r8g8b8_x8r8g8b8(const BYTE *src, BYTE *dst,
} }
} }
static inline BYTE cliptobyte(int x)
{
return (BYTE) ((x < 0) ? 0 : ((x > 255) ? 255 : x));
}
static void convert_yuy2_x8r8g8b8(const BYTE *src, BYTE *dst,
DWORD pitch_in, DWORD pitch_out, unsigned int w, unsigned int h)
{
unsigned int x, y;
int c2, d, e, r2 = 0, g2 = 0, b2 = 0;
TRACE("Converting %ux%u pixels, pitches %u %u\n", w, h, pitch_in, pitch_out);
for (y = 0; y < h; ++y)
{
const BYTE *src_line = src + y * pitch_in;
DWORD *dst_line = (DWORD *)(dst + y * pitch_out);
for (x = 0; x < w; ++x)
{
/* YUV to RGB conversion formulas from http://en.wikipedia.org/wiki/YUV:
* C = Y - 16; D = U - 128; E = V - 128;
* R = cliptobyte((298 * C + 409 * E + 128) >> 8);
* G = cliptobyte((298 * C - 100 * D - 208 * E + 128) >> 8);
* B = cliptobyte((298 * C + 516 * D + 128) >> 8);
* Two adjacent YUY2 pixels are stored as four bytes: Y0 U Y1 V .
* U and V are shared between the pixels.
*/
if (!(x & 1)) /* for every even pixel, read new U and V */
{
d = (int) src_line[1] - 128;
e = (int) src_line[3] - 128;
r2 = 409 * e + 128;
g2 = - 100 * d - 208 * e + 128;
b2 = 516 * d + 128;
}
c2 = 298 * ((int) src_line[0] - 16);
dst_line[x] = 0xff000000
| cliptobyte((c2 + r2) >> 8) << 16 /* red */
| cliptobyte((c2 + g2) >> 8) << 8 /* green */
| cliptobyte((c2 + b2) >> 8); /* blue */
/* Scale RGB values to 0..255 range,
* then clip them if still not in range (may be negative),
* then shift them within DWORD if necessary.
*/
src_line += 2;
}
}
}
struct d3dfmt_convertor_desc { struct d3dfmt_convertor_desc {
WINED3DFORMAT from, to; WINED3DFORMAT from, to;
void (*convert)(const BYTE *src, BYTE *dst, DWORD pitch_in, DWORD pitch_out, unsigned int w, unsigned int h); void (*convert)(const BYTE *src, BYTE *dst, DWORD pitch_in, DWORD pitch_out, unsigned int w, unsigned int h);
@ -752,6 +798,7 @@ static const struct d3dfmt_convertor_desc convertors[] =
{WINED3DFMT_R32_FLOAT, WINED3DFMT_R16_FLOAT, convert_r32_float_r16_float}, {WINED3DFMT_R32_FLOAT, WINED3DFMT_R16_FLOAT, convert_r32_float_r16_float},
{WINED3DFMT_B5G6R5_UNORM, WINED3DFMT_B8G8R8X8_UNORM, convert_r5g6b5_x8r8g8b8}, {WINED3DFMT_B5G6R5_UNORM, WINED3DFMT_B8G8R8X8_UNORM, convert_r5g6b5_x8r8g8b8},
{WINED3DFMT_B8G8R8A8_UNORM, WINED3DFMT_B8G8R8X8_UNORM, convert_a8r8g8b8_x8r8g8b8}, {WINED3DFMT_B8G8R8A8_UNORM, WINED3DFMT_B8G8R8X8_UNORM, convert_a8r8g8b8_x8r8g8b8},
{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(WINED3DFORMAT from, WINED3DFORMAT to)
@ -892,7 +939,7 @@ static HRESULT
/***************************************************************************** /*****************************************************************************
* IWineD3DSurface::Blt, SW emulation version * IWineD3DSurface::Blt, SW emulation version
* *
* Performs blits to a surface, eigher from a source of source-less blts * Performs a blit to a surface, with or without a source surface.
* This is the main functionality of DirectDraw * This is the main functionality of DirectDraw
* *
* Params: * Params:
@ -909,7 +956,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
HRESULT ret = WINED3D_OK; HRESULT ret = WINED3D_OK;
WINED3DLOCKED_RECT dlock, slock; WINED3DLOCKED_RECT dlock, slock;
int bpp, srcheight, srcwidth, dstheight, dstwidth, width; int bpp, srcheight, srcwidth, dstheight, dstwidth, width;
const struct GlPixelFormatDesc *sEntry, *dEntry; const struct wined3d_format_desc *sEntry, *dEntry;
int x, y; int x, y;
const BYTE *sbuf; const BYTE *sbuf;
BYTE *dbuf; BYTE *dbuf;
@ -943,144 +990,145 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_Blt(IWineD3DSurface *iface, const RECT *D
FIXME("Filters not supported in software blit\n"); FIXME("Filters not supported in software blit\n");
} }
/* First check for the validity of source / destination rectangles. This was /* First check for the validity of source / destination rectangles.
* verified using a test application + by MSDN. * This was verified using a test application + by MSDN. */
*/
if ((Src != NULL) && (SrcRect != NULL) &&
((SrcRect->bottom > Src->currentDesc.Height)||(SrcRect->bottom < 0) ||
(SrcRect->top > Src->currentDesc.Height)||(SrcRect->top < 0) ||
(SrcRect->left > Src->currentDesc.Width) ||(SrcRect->left < 0) ||
(SrcRect->right > Src->currentDesc.Width) ||(SrcRect->right < 0) ||
(SrcRect->right < SrcRect->left) ||(SrcRect->bottom < SrcRect->top)))
{
WARN("Application gave us bad source rectangle for Blt.\n");
return WINEDDERR_INVALIDRECT;
}
/* For the Destination rect, it can be out of bounds on the condition that a clipper
* is set for the given surface.
*/
if ((/*This->clipper == NULL*/ TRUE) && (DestRect) &&
((DestRect->bottom > This->currentDesc.Height)||(DestRect->bottom < 0) ||
(DestRect->top > This->currentDesc.Height)||(DestRect->top < 0) ||
(DestRect->left > This->currentDesc.Width) ||(DestRect->left < 0) ||
(DestRect->right > This->currentDesc.Width) ||(DestRect->right < 0) ||
(DestRect->right < DestRect->left) ||(DestRect->bottom < DestRect->top)))
{
WARN("Application gave us bad destination rectangle for Blt without a clipper set.\n");
return WINEDDERR_INVALIDRECT;
}
/* Now handle negative values in the rectangles. Warning: only supported for now if (SrcRect)
in the 'simple' cases (ie not in any stretching / rotation cases).
First, the case where nothing is to be done.
*/
if ((DestRect && ((DestRect->bottom <= 0) || (DestRect->right <= 0) ||
(DestRect->top >= (int) This->currentDesc.Height) ||
(DestRect->left >= (int) This->currentDesc.Width))) ||
((Src != NULL) && (SrcRect != NULL) &&
((SrcRect->bottom <= 0) || (SrcRect->right <= 0) ||
(SrcRect->top >= (int) Src->currentDesc.Height) ||
(SrcRect->left >= (int) Src->currentDesc.Width)) ))
{ {
TRACE("Nothing to be done !\n"); if (Src)
return WINED3D_OK; {
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)
{
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)
{
TRACE("Nothing to be done.\n");
return WINED3D_OK;
}
}
xsrc = *SrcRect;
}
else if (Src)
{
xsrc.left = 0;
xsrc.top = 0;
xsrc.right = Src->currentDesc.Width;
xsrc.bottom = Src->currentDesc.Height;
}
else
{
memset(&xsrc, 0, sizeof(xsrc));
} }
if (DestRect) if (DestRect)
{ {
xdst = *DestRect; /* For the Destination rect, it can be out of bounds on the condition
} * that a clipper is set for the given surface. */
else if (!This->clipper && (DestRect->right < DestRect->left || DestRect->bottom < DestRect->top
{ || DestRect->left > This->currentDesc.Width || DestRect->left < 0
xdst.top = 0; || DestRect->top > This->currentDesc.Height || DestRect->top < 0
xdst.bottom = This->currentDesc.Height; || DestRect->right > This->currentDesc.Width || DestRect->right < 0
xdst.left = 0; || DestRect->bottom > This->currentDesc.Height || DestRect->bottom < 0))
xdst.right = This->currentDesc.Width;
}
if (SrcRect)
{
xsrc = *SrcRect;
}
else
{
if (Src)
{ {
xsrc.top = 0; WARN("Application gave us bad destination rectangle for Blt without a clipper set.\n");
xsrc.bottom = Src->currentDesc.Height; return WINEDDERR_INVALIDRECT;
xsrc.left = 0; }
xsrc.right = Src->currentDesc.Width;
if (DestRect->right <= 0 || DestRect->bottom <= 0
|| DestRect->left >= (int)This->currentDesc.Width
|| DestRect->top >= (int)This->currentDesc.Height)
{
TRACE("Nothing to be done.\n");
return WINED3D_OK;
}
if (!Src)
{
RECT full_rect;
full_rect.left = 0;
full_rect.top = 0;
full_rect.right = This->currentDesc.Width;
full_rect.bottom = This->currentDesc.Height;
IntersectRect(&xdst, &full_rect, DestRect);
} }
else else
{ {
memset(&xsrc,0,sizeof(xsrc)); BOOL clip_horiz, clip_vert;
xdst = *DestRect;
clip_horiz = xdst.left < 0 || xdst.right > (int)This->currentDesc.Width;
clip_vert = xdst.top < 0 || xdst.bottom > (int)This->currentDesc.Height;
if (clip_vert || clip_horiz)
{
/* Now check if this is a special case or not... */
if ((Flags & WINEDDBLT_DDFX)
|| (clip_horiz && xdst.right - xdst.left != xsrc.right - xsrc.left)
|| (clip_vert && xdst.bottom - xdst.top != xsrc.bottom - xsrc.top))
{
WARN("Out of screen rectangle in special case. Not handled right now.\n");
return WINED3D_OK;
}
if (clip_horiz)
{
if (xdst.left < 0)
{
xsrc.left -= xdst.left;
xdst.left = 0;
}
if (xdst.right > This->currentDesc.Width)
{
xsrc.right -= (xdst.right - (int)This->currentDesc.Width);
xdst.right = (int)This->currentDesc.Width;
}
}
if (clip_vert)
{
if (xdst.top < 0)
{
xsrc.top -= xdst.top;
xdst.top = 0;
}
if (xdst.bottom > This->currentDesc.Height)
{
xsrc.bottom -= (xdst.bottom - (int)This->currentDesc.Height);
xdst.bottom = (int)This->currentDesc.Height;
}
}
/* And check if after clipping something is still to be done... */
if ((xdst.right <= 0) || (xdst.bottom <= 0)
|| (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))
{
TRACE("Nothing to be done after clipping.\n");
return WINED3D_OK;
}
}
} }
} }
else
/* The easy case : the source-less blits.... */
if (Src == NULL && DestRect)
{ {
RECT full_rect; xdst.left = 0;
RECT temp_rect; /* No idea if intersect rect can be the same as one of the source rect */ xdst.top = 0;
xdst.right = This->currentDesc.Width;
full_rect.left = 0; xdst.bottom = This->currentDesc.Height;
full_rect.top = 0;
full_rect.right = This->currentDesc.Width;
full_rect.bottom = This->currentDesc.Height;
IntersectRect(&temp_rect, &full_rect, DestRect);
xdst = temp_rect;
}
else if (DestRect)
{
/* Only handle clipping on the destination rectangle */
int clip_horiz = (DestRect->left < 0) || (DestRect->right > (int) This->currentDesc.Width );
int clip_vert = (DestRect->top < 0) || (DestRect->bottom > (int) This->currentDesc.Height);
if (clip_vert || clip_horiz)
{
/* Now check if this is a special case or not... */
if ((((DestRect->bottom - DestRect->top ) != (xsrc.bottom - xsrc.top )) && clip_vert ) ||
(((DestRect->right - DestRect->left) != (xsrc.right - xsrc.left)) && clip_horiz) ||
(Flags & WINEDDBLT_DDFX))
{
WARN("Out of screen rectangle in special case. Not handled right now.\n");
return WINED3D_OK;
}
if (clip_horiz)
{
if (DestRect->left < 0) { xsrc.left -= DestRect->left; xdst.left = 0; }
if (DestRect->right > This->currentDesc.Width)
{
xsrc.right -= (DestRect->right - (int) This->currentDesc.Width);
xdst.right = (int) This->currentDesc.Width;
}
}
if (clip_vert)
{
if (DestRect->top < 0)
{
xsrc.top -= DestRect->top;
xdst.top = 0;
}
if (DestRect->bottom > This->currentDesc.Height)
{
xsrc.bottom -= (DestRect->bottom - (int) This->currentDesc.Height);
xdst.bottom = (int) This->currentDesc.Height;
}
}
/* And check if after clipping something is still to be done... */
if ((xdst.bottom <= 0) || (xdst.right <= 0) ||
(xdst.top >= (int) This->currentDesc.Height) ||
(xdst.left >= (int) This->currentDesc.Width) ||
(xsrc.bottom <= 0) || (xsrc.right <= 0) ||
(xsrc.top >= (int) Src->currentDesc.Height) ||
(xsrc.left >= (int) Src->currentDesc.Width))
{
TRACE("Nothing to be done after clipping !\n");
return WINED3D_OK;
}
}
} }
if (Src == This) if (Src == This)
@ -1552,7 +1600,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_BltFast(IWineD3DSurface *iface, DWORD dst
RECT lock_src, lock_dst, lock_union; RECT lock_src, lock_dst, lock_union;
const BYTE *sbuf; const BYTE *sbuf;
BYTE *dbuf; BYTE *dbuf;
const struct GlPixelFormatDesc *sEntry, *dEntry; const struct wined3d_format_desc *sEntry, *dEntry;
if (TRACE_ON(d3d_surface)) if (TRACE_ON(d3d_surface))
{ {
@ -1833,7 +1881,7 @@ HRESULT WINAPI IWineD3DBaseSurfaceImpl_LockRect(IWineD3DSurface *iface, WINED3DL
} }
else else
{ {
const struct GlPixelFormatDesc *format_desc = This->resource.format_desc; const struct wined3d_format_desc *format_desc = This->resource.format_desc;
TRACE("Lock Rect (%p) = l %d, t %d, r %d, b %d\n", TRACE("Lock Rect (%p) = l %d, t %d, r %d, b %d\n",
pRect, pRect->left, pRect->top, pRect->right, pRect->bottom); pRect, pRect->left, pRect->top, pRect->right, pRect->bottom);

View file

@ -200,7 +200,7 @@ IWineGDISurfaceImpl_UnlockRect(IWineD3DSurface *iface)
/* Tell the swapchain to update the screen */ /* Tell the swapchain to update the screen */
if (SUCCEEDED(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DSwapChain, (void **)&swapchain))) if (SUCCEEDED(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DSwapChain, (void **)&swapchain)))
{ {
if(iface == swapchain->frontBuffer) if (This == swapchain->front_buffer)
{ {
x11_copy_to_screen(swapchain, &This->lockedRect); x11_copy_to_screen(swapchain, &This->lockedRect);
} }
@ -240,7 +240,8 @@ IWineGDISurfaceImpl_Flip(IWineD3DSurface *iface,
return WINEDDERR_NOTFLIPPABLE; return WINEDDERR_NOTFLIPPABLE;
} }
hr = IWineD3DSwapChain_Present((IWineD3DSwapChain *) swapchain, NULL, NULL, 0, NULL, 0); hr = IWineD3DSwapChain_Present((IWineD3DSwapChain *)swapchain,
NULL, NULL, swapchain->win_handle, NULL, 0);
IWineD3DSwapChain_Release((IWineD3DSwapChain *) swapchain); IWineD3DSwapChain_Release((IWineD3DSwapChain *) swapchain);
return hr; return hr;
} }
@ -296,9 +297,9 @@ const char* filename)
FILE* f = NULL; FILE* f = NULL;
UINT y = 0, x = 0; UINT y = 0, x = 0;
IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface; IWineD3DSurfaceImpl *This = (IWineD3DSurfaceImpl *)iface;
const struct wined3d_format_desc *format_desc = This->resource.format_desc;
static char *output = NULL; static char *output = NULL;
static UINT size = 0; static UINT size = 0;
const struct GlPixelFormatDesc *format_desc = This->resource.format_desc;
if (This->pow2Width > size) { if (This->pow2Width > size) {
output = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, This->pow2Width * 3); output = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, This->pow2Width * 3);
@ -340,14 +341,13 @@ const char* filename)
fwrite(output, 3 * This->pow2Width, 1, f); fwrite(output, 3 * This->pow2Width, 1, f);
} }
} else { } else {
int red_shift, green_shift, blue_shift, pix_width, alpha_shift; int red_shift, green_shift, blue_shift, pix_width;
pix_width = format_desc->byte_count; pix_width = format_desc->byte_count;
red_shift = get_shift(format_desc->red_mask); red_shift = get_shift(format_desc->red_mask);
green_shift = get_shift(format_desc->green_mask); green_shift = get_shift(format_desc->green_mask);
blue_shift = get_shift(format_desc->blue_mask); blue_shift = get_shift(format_desc->blue_mask);
alpha_shift = get_shift(format_desc->alpha_mask);
for (y = 0; y < This->pow2Height; y++) { for (y = 0; y < This->pow2Height; y++) {
const unsigned char *src = This->resource.allocatedMemory + (y * 1 * IWineD3DSurface_GetPitch(iface)); const unsigned char *src = This->resource.allocatedMemory + (y * 1 * IWineD3DSurface_GetPitch(iface));
@ -366,8 +366,8 @@ const char* filename)
output[3 * x + 0] = red_shift > 0 ? comp >> red_shift : comp << -red_shift; output[3 * x + 0] = red_shift > 0 ? comp >> red_shift : comp << -red_shift;
comp = color & format_desc->green_mask; comp = color & format_desc->green_mask;
output[3 * x + 1] = green_shift > 0 ? comp >> green_shift : comp << -green_shift; output[3 * x + 1] = green_shift > 0 ? comp >> green_shift : comp << -green_shift;
comp = color & format_desc->alpha_mask; comp = color & format_desc->blue_mask;
output[3 * x + 2] = alpha_shift > 0 ? comp >> alpha_shift : comp << -alpha_shift; output[3 * x + 2] = blue_shift > 0 ? comp >> blue_shift : comp << -blue_shift;
} }
fwrite(output, 3 * This->pow2Width, 1, f); fwrite(output, 3 * This->pow2Width, 1, f);
} }
@ -430,7 +430,7 @@ static HRESULT WINAPI IWineGDISurfaceImpl_GetDC(IWineD3DSurface *iface, HDC *pHD
IWineD3DSurfaceImpl *dds_primary; IWineD3DSurfaceImpl *dds_primary;
IWineD3DSwapChainImpl *swapchain; IWineD3DSwapChainImpl *swapchain;
swapchain = (IWineD3DSwapChainImpl *)This->resource.device->swapchains[0]; swapchain = (IWineD3DSwapChainImpl *)This->resource.device->swapchains[0];
dds_primary = (IWineD3DSurfaceImpl *)swapchain->frontBuffer; dds_primary = swapchain->front_buffer;
if (dds_primary && dds_primary->palette) if (dds_primary && dds_primary->palette)
pal = dds_primary->palette->palents; pal = dds_primary->palette->palents;
} }
@ -500,7 +500,7 @@ static HRESULT WINAPI IWineGDISurfaceImpl_RealizePalette(IWineD3DSurface *iface)
/* Tell the swapchain to update the screen */ /* Tell the swapchain to update the screen */
if (SUCCEEDED(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DSwapChain, (void **)&swapchain))) if (SUCCEEDED(IWineD3DSurface_GetContainer(iface, &IID_IWineD3DSwapChain, (void **)&swapchain)))
{ {
if(iface == swapchain->frontBuffer) if (This == swapchain->front_buffer)
{ {
x11_copy_to_screen(swapchain, NULL); x11_copy_to_screen(swapchain, NULL);
} }

View file

@ -33,8 +33,6 @@
WINE_DEFAULT_DEBUG_CHANNEL(d3d); WINE_DEFAULT_DEBUG_CHANNEL(d3d);
WINE_DECLARE_DEBUG_CHANNEL(fps); WINE_DECLARE_DEBUG_CHANNEL(fps);
#define GLINFO_LOCATION This->device->adapter->gl_info
/*IWineD3DSwapChain parts follow: */ /*IWineD3DSwapChain parts follow: */
static void WINAPI IWineD3DSwapChainImpl_Destroy(IWineD3DSwapChain *iface) static void WINAPI IWineD3DSwapChainImpl_Destroy(IWineD3DSwapChain *iface)
{ {
@ -46,32 +44,32 @@ static void WINAPI IWineD3DSwapChainImpl_Destroy(IWineD3DSwapChain *iface)
IWineD3DSwapChain_SetGammaRamp(iface, 0, &This->orig_gamma); IWineD3DSwapChain_SetGammaRamp(iface, 0, &This->orig_gamma);
/* Release the swapchain's draw buffers. Make sure This->backBuffer[0] is /* Release the swapchain's draw buffers. Make sure This->back_buffers[0] is
* the last buffer to be destroyed, FindContext() depends on that. */ * the last buffer to be destroyed, FindContext() depends on that. */
if (This->frontBuffer) if (This->front_buffer)
{ {
IWineD3DSurface_SetContainer(This->frontBuffer, 0); IWineD3DSurface_SetContainer((IWineD3DSurface *)This->front_buffer, NULL);
if (IWineD3DSurface_Release(This->frontBuffer)) if (IWineD3DSurface_Release((IWineD3DSurface *)This->front_buffer))
{ {
WARN("(%p) Something's still holding the front buffer (%p).\n", WARN("(%p) Something's still holding the front buffer (%p).\n",
This, This->frontBuffer); This, This->front_buffer);
} }
This->frontBuffer = NULL; This->front_buffer = NULL;
} }
if (This->backBuffer) if (This->back_buffers)
{ {
UINT i = This->presentParms.BackBufferCount; UINT i = This->presentParms.BackBufferCount;
while (i--) while (i--)
{ {
IWineD3DSurface_SetContainer(This->backBuffer[i], 0); IWineD3DSurface_SetContainer((IWineD3DSurface *)This->back_buffers[i], NULL);
if (IWineD3DSurface_Release(This->backBuffer[i])) if (IWineD3DSurface_Release((IWineD3DSurface *)This->back_buffers[i]))
WARN("(%p) Something's still holding back buffer %u (%p).\n", WARN("(%p) Something's still holding back buffer %u (%p).\n",
This, i, This->backBuffer[i]); This, i, This->back_buffers[i]);
} }
HeapFree(GetProcessHeap(), 0, This->backBuffer); HeapFree(GetProcessHeap(), 0, This->back_buffers);
This->backBuffer = NULL; This->back_buffers = NULL;
} }
for (i = 0; i < This->num_contexts; ++i) for (i = 0; i < This->num_contexts; ++i)
@ -100,11 +98,13 @@ static void swapchain_blit(IWineD3DSwapChainImpl *This, struct wined3d_context *
const RECT *src_rect, const RECT *dst_rect) const RECT *src_rect, const RECT *dst_rect)
{ {
IWineD3DDeviceImpl *device = This->device; IWineD3DDeviceImpl *device = This->device;
IWineD3DSurfaceImpl *backbuffer = ((IWineD3DSurfaceImpl *) This->backBuffer[0]); IWineD3DSurfaceImpl *backbuffer = This->back_buffers[0];
UINT src_w = src_rect->right - src_rect->left; UINT src_w = src_rect->right - src_rect->left;
UINT src_h = src_rect->bottom - src_rect->top; UINT src_h = src_rect->bottom - src_rect->top;
GLenum gl_filter; GLenum gl_filter;
const struct wined3d_gl_info *gl_info = context->gl_info; const struct wined3d_gl_info *gl_info = context->gl_info;
RECT win_rect;
UINT win_h;
TRACE("swapchain %p, context %p, src_rect %s, dst_rect %s.\n", TRACE("swapchain %p, context %p, src_rect %s, dst_rect %s.\n",
This, context, wine_dbgstr_rect(src_rect), wine_dbgstr_rect(dst_rect)); This, context, wine_dbgstr_rect(src_rect), wine_dbgstr_rect(dst_rect));
@ -114,12 +114,14 @@ static void swapchain_blit(IWineD3DSwapChainImpl *This, struct wined3d_context *
else else
gl_filter = GL_LINEAR; gl_filter = GL_LINEAR;
if (gl_info->fbo_ops.glBlitFramebuffer) 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))
{ {
ENTER_GL(); ENTER_GL();
context_bind_fbo(context, GL_READ_FRAMEBUFFER, &context->src_fbo); context_apply_fbo_state_blit(context, GL_READ_FRAMEBUFFER, backbuffer, NULL);
context_attach_surface_fbo(context, GL_READ_FRAMEBUFFER, 0, This->backBuffer[0]); glReadBuffer(GL_COLOR_ATTACHMENT0);
context_attach_depth_stencil_fbo(context, GL_READ_FRAMEBUFFER, NULL, FALSE);
context_bind_fbo(context, GL_DRAW_FRAMEBUFFER, NULL); context_bind_fbo(context, GL_DRAW_FRAMEBUFFER, NULL);
context_set_draw_buffer(context, GL_BACK); context_set_draw_buffer(context, GL_BACK);
@ -129,8 +131,8 @@ static void swapchain_blit(IWineD3DSwapChainImpl *This, struct wined3d_context *
/* Note that the texture is upside down */ /* Note that the texture is upside down */
gl_info->fbo_ops.glBlitFramebuffer(src_rect->left, src_rect->top, src_rect->right, src_rect->bottom, gl_info->fbo_ops.glBlitFramebuffer(src_rect->left, src_rect->top, src_rect->right, src_rect->bottom,
dst_rect->left, dst_rect->bottom, dst_rect->right, dst_rect->top, dst_rect->left, win_h - dst_rect->top, dst_rect->right, win_h - dst_rect->bottom,
GL_COLOR_BUFFER_BIT, gl_filter); GL_COLOR_BUFFER_BIT, gl_filter);
checkGLcall("Swapchain present blit(EXT_framebuffer_blit)\n"); checkGLcall("Swapchain present blit(EXT_framebuffer_blit)\n");
LEAVE_GL(); LEAVE_GL();
} }
@ -142,7 +144,8 @@ static void swapchain_blit(IWineD3DSwapChainImpl *This, struct wined3d_context *
float tex_right = src_rect->right; float tex_right = src_rect->right;
float tex_bottom = src_rect->bottom; float tex_bottom = src_rect->bottom;
context2 = context_acquire(This->device, This->backBuffer[0], CTXUSAGE_BLIT); context2 = context_acquire(This->device, This->back_buffers[0]);
context_apply_blit_state(context2, device);
if(backbuffer->Flags & SFLAG_NORMCOORD) if(backbuffer->Flags & SFLAG_NORMCOORD)
{ {
@ -152,30 +155,31 @@ static void swapchain_blit(IWineD3DSwapChainImpl *This, struct wined3d_context *
tex_bottom /= src_h; tex_bottom /= src_h;
} }
if (is_complex_fixup(backbuffer->resource.format_desc->color_fixup))
gl_filter = GL_NEAREST;
ENTER_GL(); ENTER_GL();
context_bind_fbo(context2, GL_DRAW_FRAMEBUFFER, NULL); context_bind_fbo(context2, GL_DRAW_FRAMEBUFFER, NULL);
/* Set up the texture. The surface is not in a IWineD3D*Texture container, /* Set up the texture. The surface is not in a IWineD3D*Texture container,
* so there are no d3d texture settings to dirtify * so there are no d3d texture settings to dirtify
*/ */
device->blitter->set_shader((IWineD3DDevice *) device, backbuffer->resource.format_desc, device->blitter->set_shader((IWineD3DDevice *) device, backbuffer);
backbuffer->texture_target, backbuffer->pow2Width, glTexParameteri(backbuffer->texture_target, GL_TEXTURE_MIN_FILTER, gl_filter);
backbuffer->pow2Height); glTexParameteri(backbuffer->texture_target, GL_TEXTURE_MAG_FILTER, gl_filter);
glTexParameteri(backbuffer->texture_target, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(backbuffer->texture_target, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
context_set_draw_buffer(context, GL_BACK); context_set_draw_buffer(context, GL_BACK);
/* Set the viewport to the destination rectandle, disable any projection /* Set the viewport to the destination rectandle, disable any projection
* transformation set up by CTXUSAGE_BLIT, and draw a (-1,-1)-(1,1) quad. * transformation set up by context_apply_blit_state(), and draw a
* (-1,-1)-(1,1) quad.
* *
* Back up viewport and matrix to avoid breaking last_was_blit * Back up viewport and matrix to avoid breaking last_was_blit
* *
* Note that CTXUSAGE_BLIT set up viewport and ortho to match the surface * Note that context_apply_blit_state() set up viewport and ortho to
* size - we want the GL drawable(=window) size. * match the surface size - we want the GL drawable(=window) size. */
*/
glPushAttrib(GL_VIEWPORT_BIT); glPushAttrib(GL_VIEWPORT_BIT);
glViewport(dst_rect->left, dst_rect->top, dst_rect->right, dst_rect->bottom); glViewport(dst_rect->left, win_h - dst_rect->bottom, dst_rect->right, win_h - dst_rect->top);
glMatrixMode(GL_PROJECTION); glMatrixMode(GL_PROJECTION);
glPushMatrix(); glPushMatrix();
glLoadIdentity(); glLoadIdentity();
@ -211,6 +215,7 @@ static void swapchain_blit(IWineD3DSwapChainImpl *This, struct wined3d_context *
static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CONST RECT *pSourceRect, CONST RECT *pDestRect, HWND hDestWindowOverride, CONST RGNDATA *pDirtyRegion, DWORD dwFlags) { static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CONST RECT *pSourceRect, CONST RECT *pDestRect, HWND hDestWindowOverride, CONST RGNDATA *pDirtyRegion, DWORD dwFlags) {
IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface; IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface;
const struct wined3d_gl_info *gl_info;
struct wined3d_context *context; struct wined3d_context *context;
RECT src_rect, dst_rect; RECT src_rect, dst_rect;
BOOL render_to_fbo; BOOL render_to_fbo;
@ -219,7 +224,15 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
IWineD3DSwapChain_SetDestWindowOverride(iface, hDestWindowOverride); IWineD3DSwapChain_SetDestWindowOverride(iface, hDestWindowOverride);
context = context_acquire(This->device, This->backBuffer[0], CTXUSAGE_RESOURCELOAD); context = context_acquire(This->device, This->back_buffers[0]);
if (!context->valid)
{
context_release(context);
WARN("Invalid context, skipping present.\n");
return WINED3D_OK;
}
gl_info = context->gl_info;
/* Render the cursor onto the back buffer, using our nifty directdraw blitting code :-) */ /* Render the cursor onto the back buffer, using our nifty directdraw blitting code :-) */
if (This->device->bCursorVisible && This->device->cursorTexture) if (This->device->bCursorVisible && This->device->cursorTexture)
@ -242,17 +255,13 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
cursor.resource.ref = 1; cursor.resource.ref = 1;
cursor.resource.device = This->device; cursor.resource.device = This->device;
cursor.resource.pool = WINED3DPOOL_SCRATCH; cursor.resource.pool = WINED3DPOOL_SCRATCH;
cursor.resource.format_desc = getFormatDescEntry(WINED3DFMT_B8G8R8A8_UNORM, context->gl_info); cursor.resource.format_desc = getFormatDescEntry(WINED3DFMT_B8G8R8A8_UNORM, gl_info);
cursor.resource.resourceType = WINED3DRTYPE_SURFACE; cursor.resource.resourceType = WINED3DRTYPE_SURFACE;
cursor.texture_name = This->device->cursorTexture; cursor.texture_name = This->device->cursorTexture;
cursor.texture_target = GL_TEXTURE_2D; cursor.texture_target = GL_TEXTURE_2D;
cursor.texture_level = 0; cursor.texture_level = 0;
cursor.currentDesc.Width = This->device->cursorWidth; cursor.currentDesc.Width = This->device->cursorWidth;
cursor.currentDesc.Height = This->device->cursorHeight; cursor.currentDesc.Height = This->device->cursorHeight;
cursor.glRect.left = 0;
cursor.glRect.top = 0;
cursor.glRect.right = cursor.currentDesc.Width;
cursor.glRect.bottom = cursor.currentDesc.Height;
/* The cursor must have pow2 sizes */ /* The cursor must have pow2 sizes */
cursor.pow2Width = cursor.currentDesc.Width; cursor.pow2Width = cursor.currentDesc.Width;
cursor.pow2Height = cursor.currentDesc.Height; cursor.pow2Height = cursor.currentDesc.Height;
@ -264,14 +273,15 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
if (This->presentParms.Windowed) { if (This->presentParms.Windowed) {
MapWindowPoints(NULL, This->win_handle, (LPPOINT)&destRect, 2); MapWindowPoints(NULL, This->win_handle, (LPPOINT)&destRect, 2);
} }
IWineD3DSurface_Blt(This->backBuffer[0], &destRect, (IWineD3DSurface *)&cursor, IWineD3DSurface_Blt((IWineD3DSurface *)This->back_buffers[0], &destRect, (IWineD3DSurface *)&cursor,
NULL, WINEDDBLT_KEYSRC, NULL, WINED3DTEXF_POINT); NULL, WINEDDBLT_KEYSRC, NULL, WINED3DTEXF_POINT);
} }
if (This->device->logo_surface) if (This->device->logo_surface)
{ {
/* Blit the logo into the upper left corner of the drawable. */ /* Blit the logo into the upper left corner of the drawable. */
IWineD3DSurface_BltFast(This->backBuffer[0], 0, 0, This->device->logo_surface, NULL, WINEDDBLTFAST_SRCCOLORKEY); IWineD3DSurface_BltFast((IWineD3DSurface *)This->back_buffers[0], 0, 0,
This->device->logo_surface, NULL, WINEDDBLTFAST_SRCCOLORKEY);
} }
TRACE("Presenting HDC %p.\n", context->hdc); TRACE("Presenting HDC %p.\n", context->hdc);
@ -315,8 +325,8 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
*/ */
if (!This->render_to_fbo && render_to_fbo && wined3d_settings.offscreen_rendering_mode == ORM_FBO) if (!This->render_to_fbo && render_to_fbo && wined3d_settings.offscreen_rendering_mode == ORM_FBO)
{ {
IWineD3DSurface_LoadLocation(This->backBuffer[0], SFLAG_INTEXTURE, NULL); IWineD3DSurface_LoadLocation((IWineD3DSurface *)This->back_buffers[0], SFLAG_INTEXTURE, NULL);
IWineD3DSurface_ModifyLocation(This->backBuffer[0], SFLAG_INDRAWABLE, FALSE); IWineD3DSurface_ModifyLocation((IWineD3DSurface *)This->back_buffers[0], SFLAG_INDRAWABLE, FALSE);
This->render_to_fbo = TRUE; This->render_to_fbo = TRUE;
/* Force the context manager to update the render target configuration next draw. */ /* Force the context manager to update the render target configuration next draw. */
@ -420,14 +430,14 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
WINED3DCLEAR_TARGET, 0xff00ffff, 1.0f, 0); WINED3DCLEAR_TARGET, 0xff00ffff, 1.0f, 0);
} }
if(!This->render_to_fbo && if (!This->render_to_fbo && ((This->front_buffer->Flags & SFLAG_INSYSMEM)
( ((IWineD3DSurfaceImpl *) This->frontBuffer)->Flags & SFLAG_INSYSMEM || || (This->back_buffers[0]->Flags & SFLAG_INSYSMEM)))
((IWineD3DSurfaceImpl *) This->backBuffer[0])->Flags & SFLAG_INSYSMEM ) ) { {
/* Both memory copies of the surfaces are ok, flip them around too instead of dirtifying /* Both memory copies of the surfaces are ok, flip them around too instead of dirtifying
* Doesn't work with render_to_fbo because we're not flipping * Doesn't work with render_to_fbo because we're not flipping
*/ */
IWineD3DSurfaceImpl *front = (IWineD3DSurfaceImpl *) This->frontBuffer; IWineD3DSurfaceImpl *front = This->front_buffer;
IWineD3DSurfaceImpl *back = (IWineD3DSurfaceImpl *) This->backBuffer[0]; IWineD3DSurfaceImpl *back = This->back_buffers[0];
if(front->resource.size == back->resource.size) { if(front->resource.size == back->resource.size) {
DWORD fbflags; DWORD fbflags;
@ -438,35 +448,45 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
* This serves to update the emulated overlay, if any * This serves to update the emulated overlay, if any
*/ */
fbflags = front->Flags; fbflags = front->Flags;
IWineD3DSurface_ModifyLocation(This->frontBuffer, SFLAG_INDRAWABLE, TRUE); IWineD3DSurface_ModifyLocation((IWineD3DSurface *)front, SFLAG_INDRAWABLE, TRUE);
front->Flags = fbflags; front->Flags = fbflags;
} else { } else {
IWineD3DSurface_ModifyLocation((IWineD3DSurface *) front, SFLAG_INDRAWABLE, TRUE); IWineD3DSurface_ModifyLocation((IWineD3DSurface *) front, SFLAG_INDRAWABLE, TRUE);
IWineD3DSurface_ModifyLocation((IWineD3DSurface *) back, SFLAG_INDRAWABLE, TRUE); IWineD3DSurface_ModifyLocation((IWineD3DSurface *) back, SFLAG_INDRAWABLE, TRUE);
} }
} else { }
IWineD3DSurface_ModifyLocation(This->frontBuffer, SFLAG_INDRAWABLE, TRUE); else
{
IWineD3DSurface_ModifyLocation((IWineD3DSurface *)This->front_buffer, SFLAG_INDRAWABLE, TRUE);
/* If the swapeffect is DISCARD, the back buffer is undefined. That means the SYSMEM /* 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. * 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, * If the swapeffect is COPY, the content remains the same. If it is FLIP however,
* the texture / sysmem copy needs to be reloaded from the drawable * the texture / sysmem copy needs to be reloaded from the drawable
*/ */
if(This->presentParms.SwapEffect == WINED3DSWAPEFFECT_FLIP) { if (This->presentParms.SwapEffect == WINED3DSWAPEFFECT_FLIP)
IWineD3DSurface_ModifyLocation(This->backBuffer[0], SFLAG_INDRAWABLE, TRUE); {
IWineD3DSurface_ModifyLocation((IWineD3DSurface *)This->back_buffers[0], SFLAG_INDRAWABLE, TRUE);
} }
} }
if (This->device->stencilBufferTarget) if (This->device->depth_stencil)
{ {
if (This->presentParms.Flags & WINED3DPRESENTFLAG_DISCARD_DEPTHSTENCIL if (This->presentParms.Flags & WINED3DPRESENTFLAG_DISCARD_DEPTHSTENCIL
|| ((IWineD3DSurfaceImpl *)This->device->stencilBufferTarget)->Flags & SFLAG_DISCARD) || This->device->depth_stencil->Flags & SFLAG_DISCARD)
{ {
surface_modify_ds_location(This->device->stencilBufferTarget, SFLAG_DS_DISCARDED); surface_modify_ds_location(This->device->depth_stencil, SFLAG_DS_DISCARDED,
This->device->depth_stencil->currentDesc.Width,
This->device->depth_stencil->currentDesc.Height);
if (This->device->depth_stencil == This->device->onscreen_depth_stencil)
{
IWineD3DSurface_Release((IWineD3DSurface *)This->device->onscreen_depth_stencil);
This->device->onscreen_depth_stencil = NULL;
}
} }
} }
if (This->presentParms.PresentationInterval != WINED3DPRESENT_INTERVAL_IMMEDIATE if (This->presentParms.PresentationInterval != WINED3DPRESENT_INTERVAL_IMMEDIATE
&& context->gl_info->supported[SGI_VIDEO_SYNC]) && gl_info->supported[SGI_VIDEO_SYNC])
{ {
retval = GL_EXTCALL(glXGetVideoSyncSGI(&sync)); retval = GL_EXTCALL(glXGetVideoSyncSGI(&sync));
if(retval != 0) { if(retval != 0) {
@ -514,47 +534,16 @@ static HRESULT WINAPI IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO
return WINED3D_OK; return WINED3D_OK;
} }
static HRESULT WINAPI IWineD3DSwapChainImpl_SetDestWindowOverride(IWineD3DSwapChain *iface, HWND window) { static HRESULT WINAPI IWineD3DSwapChainImpl_SetDestWindowOverride(IWineD3DSwapChain *iface, HWND window)
IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface; {
WINED3DLOCKED_RECT r; IWineD3DSwapChainImpl *swapchain = (IWineD3DSwapChainImpl *)iface;
BYTE *mem;
if (!window || window == This->win_handle) return WINED3D_OK; if (!window) window = swapchain->device_window;
if (window == swapchain->win_handle) return WINED3D_OK;
TRACE("Performing dest override of swapchain %p from window %p to %p\n", This, This->win_handle, window); TRACE("Setting swapchain %p window from %p to %p\n", swapchain, swapchain->win_handle, window);
if (This->context[0] == This->device->contexts[0]) swapchain->win_handle = window;
{
/* The primary context 'owns' all the opengl resources. Destroying and recreating that context requires downloading
* all opengl resources, deleting the gl resources, destroying all other contexts, then recreating all other contexts
* and reload the resources
*/
delete_opengl_contexts((IWineD3DDevice *)This->device, iface);
This->win_handle = window;
create_primary_opengl_context((IWineD3DDevice *)This->device, iface);
}
else
{
This->win_handle = window;
/* The old back buffer has to be copied over to the new back buffer. A lockrect - switchcontext - unlockrect
* would suffice in theory, but it is rather nasty and may cause troubles with future changes of the locking code
* So lock read only, copy the surface out, then lock with the discard flag and write back
*/
IWineD3DSurface_LockRect(This->backBuffer[0], &r, NULL, WINED3DLOCK_READONLY);
mem = HeapAlloc(GetProcessHeap(), 0, r.Pitch * ((IWineD3DSurfaceImpl *) This->backBuffer[0])->currentDesc.Height);
memcpy(mem, r.pBits, r.Pitch * ((IWineD3DSurfaceImpl *) This->backBuffer[0])->currentDesc.Height);
IWineD3DSurface_UnlockRect(This->backBuffer[0]);
context_destroy(This->device, This->context[0]);
This->context[0] = context_create(This->device, (IWineD3DSurfaceImpl *)This->frontBuffer,
This->win_handle, FALSE /* pbuffer */, &This->presentParms);
context_release(This->context[0]);
IWineD3DSurface_LockRect(This->backBuffer[0], &r, NULL, WINED3DLOCK_DISCARD);
memcpy(r.pBits, mem, r.Pitch * ((IWineD3DSurfaceImpl *) This->backBuffer[0])->currentDesc.Height);
HeapFree(GetProcessHeap(), 0, mem);
IWineD3DSurface_UnlockRect(This->backBuffer[0]);
}
return WINED3D_OK; return WINED3D_OK;
} }
@ -599,7 +588,7 @@ static LONG fullscreen_exstyle(LONG exstyle)
void swapchain_setup_fullscreen_window(IWineD3DSwapChainImpl *swapchain, UINT w, UINT h) void swapchain_setup_fullscreen_window(IWineD3DSwapChainImpl *swapchain, UINT w, UINT h)
{ {
IWineD3DDeviceImpl *device = swapchain->device; IWineD3DDeviceImpl *device = swapchain->device;
HWND window = swapchain->win_handle; HWND window = swapchain->device_window;
BOOL filter_messages; BOOL filter_messages;
LONG style, exstyle; LONG style, exstyle;
@ -633,7 +622,7 @@ void swapchain_setup_fullscreen_window(IWineD3DSwapChainImpl *swapchain, UINT w,
void swapchain_restore_fullscreen_window(IWineD3DSwapChainImpl *swapchain) void swapchain_restore_fullscreen_window(IWineD3DSwapChainImpl *swapchain)
{ {
IWineD3DDeviceImpl *device = swapchain->device; IWineD3DDeviceImpl *device = swapchain->device;
HWND window = swapchain->win_handle; HWND window = swapchain->device_window;
BOOL filter_messages; BOOL filter_messages;
LONG style, exstyle; LONG style, exstyle;
@ -671,7 +660,7 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
IWineD3DDeviceImpl *device, WINED3DPRESENT_PARAMETERS *present_parameters, IUnknown *parent) IWineD3DDeviceImpl *device, WINED3DPRESENT_PARAMETERS *present_parameters, IUnknown *parent)
{ {
const struct wined3d_adapter *adapter = device->adapter; const struct wined3d_adapter *adapter = device->adapter;
const struct GlPixelFormatDesc *format_desc; const struct wined3d_format_desc *format_desc;
BOOL displaymode_set = FALSE; BOOL displaymode_set = FALSE;
WINED3DDISPLAYMODE mode; WINED3DDISPLAYMODE mode;
RECT client_rect; RECT client_rect;
@ -713,6 +702,7 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
swapchain->parent = parent; swapchain->parent = parent;
swapchain->ref = 1; swapchain->ref = 1;
swapchain->win_handle = window; swapchain->win_handle = window;
swapchain->device_window = window;
if (!present_parameters->Windowed && window) if (!present_parameters->Windowed && window)
{ {
@ -768,18 +758,19 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
hr = IWineD3DDeviceParent_CreateRenderTarget(device->device_parent, parent, hr = IWineD3DDeviceParent_CreateRenderTarget(device->device_parent, parent,
swapchain->presentParms.BackBufferWidth, swapchain->presentParms.BackBufferHeight, swapchain->presentParms.BackBufferWidth, swapchain->presentParms.BackBufferHeight,
swapchain->presentParms.BackBufferFormat, swapchain->presentParms.MultiSampleType, swapchain->presentParms.BackBufferFormat, swapchain->presentParms.MultiSampleType,
swapchain->presentParms.MultiSampleQuality, TRUE /* Lockable */, &swapchain->frontBuffer); swapchain->presentParms.MultiSampleQuality, TRUE /* Lockable */,
(IWineD3DSurface **)&swapchain->front_buffer);
if (FAILED(hr)) if (FAILED(hr))
{ {
WARN("Failed to create front buffer, hr %#x.\n", hr); WARN("Failed to create front buffer, hr %#x.\n", hr);
goto err; goto err;
} }
IWineD3DSurface_SetContainer(swapchain->frontBuffer, (IWineD3DBase *)swapchain); IWineD3DSurface_SetContainer((IWineD3DSurface *)swapchain->front_buffer, (IWineD3DBase *)swapchain);
((IWineD3DSurfaceImpl *)swapchain->frontBuffer)->Flags |= SFLAG_SWAPCHAIN; swapchain->front_buffer->Flags |= SFLAG_SWAPCHAIN;
if (surface_type == SURFACE_OPENGL) if (surface_type == SURFACE_OPENGL)
{ {
IWineD3DSurface_ModifyLocation(swapchain->frontBuffer, SFLAG_INDRAWABLE, TRUE); IWineD3DSurface_ModifyLocation((IWineD3DSurface *)swapchain->front_buffer, SFLAG_INDRAWABLE, TRUE);
} }
/* MSDN says we're only allowed a single fullscreen swapchain per device, /* MSDN says we're only allowed a single fullscreen swapchain per device,
@ -816,14 +807,49 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
if (surface_type == SURFACE_OPENGL) if (surface_type == SURFACE_OPENGL)
{ {
swapchain->context[0] = context_create(device, (IWineD3DSurfaceImpl *)swapchain->frontBuffer, WINED3DFORMAT formats[] =
window, FALSE /* pbuffer */, present_parameters); {
WINED3DFMT_D24_UNORM_S8_UINT,
WINED3DFMT_D32_UNORM,
WINED3DFMT_R24_UNORM_X8_TYPELESS,
WINED3DFMT_D16_UNORM,
WINED3DFMT_S1_UINT_D15_UNORM
};
const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
/* In WGL both color, depth and stencil are features of a pixel format. In case of D3D they are separate.
* You are able to add a depth + stencil surface at a later stage when you need it.
* In order to support this properly in WineD3D we need the ability to recreate the opengl context and
* drawable when this is required. This is very tricky as we need to reapply ALL opengl states for the new
* context, need torecreate shaders, textures and other resources.
*
* The context manager already takes care of the state problem and for the other tasks code from Reset
* can be used. These changes are way to risky during the 1.0 code freeze which is taking place right now.
* Likely a lot of other new bugs will be exposed. For that reason request a depth stencil surface all the
* time. It can cause a slight performance hit but fixes a lot of regressions. A fixme reminds of that this
* issue needs to be fixed. */
for (i = 0; i < (sizeof(formats) / sizeof(*formats)); i++)
{
swapchain->ds_format = getFormatDescEntry(formats[i], gl_info);
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",
debug_d3dformat(formats[i]));
}
if (!swapchain->context[0]) if (!swapchain->context[0])
{ {
WARN("Failed to create context.\n"); WARN("Failed to create context.\n");
hr = WINED3DERR_NOTAVAILABLE; hr = WINED3DERR_NOTAVAILABLE;
goto err; goto err;
} }
if (!present_parameters->EnableAutoDepthStencil
|| swapchain->presentParms.AutoDepthStencilFormat != swapchain->ds_format->format)
{
FIXME("Add OpenGL context recreation support to context_validate_onscreen_formats\n");
}
context_release(swapchain->context[0]); context_release(swapchain->context[0]);
} }
else else
@ -833,9 +859,9 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
if (swapchain->presentParms.BackBufferCount > 0) if (swapchain->presentParms.BackBufferCount > 0)
{ {
swapchain->backBuffer = HeapAlloc(GetProcessHeap(), 0, swapchain->back_buffers = HeapAlloc(GetProcessHeap(), 0,
sizeof(*swapchain->backBuffer) * swapchain->presentParms.BackBufferCount); sizeof(*swapchain->back_buffers) * swapchain->presentParms.BackBufferCount);
if (!swapchain->backBuffer) if (!swapchain->back_buffers)
{ {
ERR("Failed to allocate backbuffer array memory.\n"); ERR("Failed to allocate backbuffer array memory.\n");
hr = E_OUTOFMEMORY; hr = E_OUTOFMEMORY;
@ -848,15 +874,16 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
hr = IWineD3DDeviceParent_CreateRenderTarget(device->device_parent, parent, hr = IWineD3DDeviceParent_CreateRenderTarget(device->device_parent, parent,
swapchain->presentParms.BackBufferWidth, swapchain->presentParms.BackBufferHeight, swapchain->presentParms.BackBufferWidth, swapchain->presentParms.BackBufferHeight,
swapchain->presentParms.BackBufferFormat, swapchain->presentParms.MultiSampleType, swapchain->presentParms.BackBufferFormat, swapchain->presentParms.MultiSampleType,
swapchain->presentParms.MultiSampleQuality, TRUE /* Lockable */, &swapchain->backBuffer[i]); swapchain->presentParms.MultiSampleQuality, TRUE /* Lockable */,
(IWineD3DSurface **)&swapchain->back_buffers[i]);
if (FAILED(hr)) if (FAILED(hr))
{ {
WARN("Failed to create back buffer %u, hr %#x.\n", i, hr); WARN("Failed to create back buffer %u, hr %#x.\n", i, hr);
goto err; goto err;
} }
IWineD3DSurface_SetContainer(swapchain->backBuffer[i], (IWineD3DBase *)swapchain); IWineD3DSurface_SetContainer((IWineD3DSurface *)swapchain->back_buffers[i], (IWineD3DBase *)swapchain);
((IWineD3DSurfaceImpl *)swapchain->backBuffer[i])->Flags |= SFLAG_SWAPCHAIN; swapchain->back_buffers[i]->Flags |= SFLAG_SWAPCHAIN;
} }
} }
@ -864,20 +891,20 @@ HRESULT swapchain_init(IWineD3DSwapChainImpl *swapchain, WINED3DSURFTYPE surface
if (present_parameters->EnableAutoDepthStencil && surface_type == SURFACE_OPENGL) if (present_parameters->EnableAutoDepthStencil && surface_type == SURFACE_OPENGL)
{ {
TRACE("Creating depth/stencil buffer.\n"); TRACE("Creating depth/stencil buffer.\n");
if (!device->auto_depth_stencil_buffer) if (!device->auto_depth_stencil)
{ {
hr = IWineD3DDeviceParent_CreateDepthStencilSurface(device->device_parent, parent, hr = IWineD3DDeviceParent_CreateDepthStencilSurface(device->device_parent, parent,
swapchain->presentParms.BackBufferWidth, swapchain->presentParms.BackBufferHeight, swapchain->presentParms.BackBufferWidth, swapchain->presentParms.BackBufferHeight,
swapchain->presentParms.AutoDepthStencilFormat, swapchain->presentParms.MultiSampleType, swapchain->presentParms.AutoDepthStencilFormat, swapchain->presentParms.MultiSampleType,
swapchain->presentParms.MultiSampleQuality, FALSE /* FIXME: Discard */, swapchain->presentParms.MultiSampleQuality, FALSE /* FIXME: Discard */,
&device->auto_depth_stencil_buffer); (IWineD3DSurface **)&device->auto_depth_stencil);
if (FAILED(hr)) if (FAILED(hr))
{ {
WARN("Failed to create the auto depth stencil, hr %#x.\n", hr); WARN("Failed to create the auto depth stencil, hr %#x.\n", hr);
goto err; goto err;
} }
IWineD3DSurface_SetContainer(device->auto_depth_stencil_buffer, NULL); IWineD3DSurface_SetContainer((IWineD3DSurface *)device->auto_depth_stencil, NULL);
} }
} }
@ -902,13 +929,13 @@ err:
ChangeDisplaySettingsExW(adapter->DeviceName, &devmode, NULL, CDS_FULLSCREEN, NULL); ChangeDisplaySettingsExW(adapter->DeviceName, &devmode, NULL, CDS_FULLSCREEN, NULL);
} }
if (swapchain->backBuffer) if (swapchain->back_buffers)
{ {
for (i = 0; i < swapchain->presentParms.BackBufferCount; ++i) for (i = 0; i < swapchain->presentParms.BackBufferCount; ++i)
{ {
if (swapchain->backBuffer[i]) IWineD3DSurface_Release(swapchain->backBuffer[i]); if (swapchain->back_buffers[i]) IWineD3DSurface_Release((IWineD3DSurface *)swapchain->back_buffers[i]);
} }
HeapFree(GetProcessHeap(), 0, swapchain->backBuffer); HeapFree(GetProcessHeap(), 0, swapchain->back_buffers);
} }
if (swapchain->context) if (swapchain->context)
@ -922,7 +949,7 @@ err:
HeapFree(GetProcessHeap(), 0, swapchain->context); HeapFree(GetProcessHeap(), 0, swapchain->context);
} }
if (swapchain->frontBuffer) IWineD3DSurface_Release(swapchain->frontBuffer); if (swapchain->front_buffer) IWineD3DSurface_Release((IWineD3DSurface *)swapchain->front_buffer);
return hr; return hr;
} }
@ -935,9 +962,7 @@ struct wined3d_context *swapchain_create_context_for_thread(IWineD3DSwapChain *i
TRACE("Creating a new context for swapchain %p, thread %d\n", This, GetCurrentThreadId()); TRACE("Creating a new context for swapchain %p, thread %d\n", This, GetCurrentThreadId());
ctx = context_create(This->device, (IWineD3DSurfaceImpl *)This->frontBuffer, if (!(ctx = context_create(This, This->front_buffer, This->ds_format)))
This->context[0]->win_handle, FALSE /* pbuffer */, &This->presentParms);
if (!ctx)
{ {
ERR("Failed to create a new context for the swapchain\n"); ERR("Failed to create a new context for the swapchain\n");
return NULL; return NULL;
@ -962,9 +987,8 @@ struct wined3d_context *swapchain_create_context_for_thread(IWineD3DSwapChain *i
void get_drawable_size_swapchain(struct wined3d_context *context, UINT *width, UINT *height) void get_drawable_size_swapchain(struct wined3d_context *context, UINT *width, UINT *height)
{ {
IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)context->current_rt;
/* The drawable size of an onscreen drawable is the surface size. /* The drawable size of an onscreen drawable is the surface size.
* (Actually: The window size, but the surface is created in window size) */ * (Actually: The window size, but the surface is created in window size) */
*width = surface->currentDesc.Width; *width = context->current_rt->currentDesc.Width;
*height = surface->currentDesc.Height; *height = context->current_rt->currentDesc.Height;
} }

View file

@ -85,7 +85,7 @@ HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetFrontBufferData(IWineD3DSwapChain *i
MapWindowPoints(This->win_handle, NULL, &start, 1); MapWindowPoints(This->win_handle, NULL, &start, 1);
} }
IWineD3DSurface_BltFast(pDestSurface, start.x, start.y, This->frontBuffer, NULL, 0); IWineD3DSurface_BltFast(pDestSurface, start.x, start.y, (IWineD3DSurface *)This->front_buffer, NULL, 0);
return WINED3D_OK; return WINED3D_OK;
} }
@ -106,12 +106,13 @@ HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetBackBuffer(IWineD3DSwapChain *iface,
* used (there This->backBuffer is always NULL). We need this because this function has * used (there This->backBuffer is always NULL). We need this because this function has
* to be called from IWineD3DStateBlockImpl_InitStartupStateBlock to get the default * to be called from IWineD3DStateBlockImpl_InitStartupStateBlock to get the default
* scissorrect dimensions. */ * scissorrect dimensions. */
if( !This->backBuffer ) { if (!This->back_buffers)
{
*ppBackBuffer = NULL; *ppBackBuffer = NULL;
return WINED3DERR_INVALIDCALL; return WINED3DERR_INVALIDCALL;
} }
*ppBackBuffer = This->backBuffer[iBackBuffer]; *ppBackBuffer = (IWineD3DSurface *)This->back_buffers[iBackBuffer];
TRACE("(%p) : BackBuf %d Type %d returning %p\n", This, iBackBuffer, Type, *ppBackBuffer); TRACE("(%p) : BackBuf %d Type %d returning %p\n", This, iBackBuffer, Type, *ppBackBuffer);
/* Note inc ref on returned surface */ /* Note inc ref on returned surface */
@ -145,15 +146,14 @@ HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetDisplayMode(IWineD3DSwapChain *iface
return hr; return hr;
} }
HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetDevice(IWineD3DSwapChain *iface, IWineD3DDevice**ppDevice) { HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetDevice(IWineD3DSwapChain *iface, IWineD3DDevice **device)
{
IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface; IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface;
*ppDevice = (IWineD3DDevice *)This->device; *device = (IWineD3DDevice *)This->device;
IWineD3DDevice_AddRef(*device);
/* Note Calling this method will increase the internal reference count TRACE("(%p) : returning %p\n", This, *device);
on the IDirect3DDevice9 interface. */
IWineD3DDevice_AddRef(*ppDevice);
TRACE("(%p) : returning %p\n", This, *ppDevice);
return WINED3D_OK; return WINED3D_OK;
} }
@ -171,9 +171,9 @@ HRESULT WINAPI IWineD3DBaseSwapChainImpl_SetGammaRamp(IWineD3DSwapChain *iface,
IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface; IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface;
HDC hDC; HDC hDC;
TRACE("(%p) : pRamp@%p flags(%d)\n", This, pRamp, Flags); TRACE("(%p) : pRamp@%p flags(%d)\n", This, pRamp, Flags);
hDC = GetDC(This->win_handle); hDC = GetDC(This->device_window);
SetDeviceGammaRamp(hDC, (LPVOID)pRamp); SetDeviceGammaRamp(hDC, (LPVOID)pRamp);
ReleaseDC(This->win_handle, hDC); ReleaseDC(This->device_window, hDC);
return WINED3D_OK; return WINED3D_OK;
} }
@ -183,9 +183,9 @@ HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetGammaRamp(IWineD3DSwapChain *iface,
IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface; IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *)iface;
HDC hDC; HDC hDC;
TRACE("(%p) : pRamp@%p\n", This, pRamp); TRACE("(%p) : pRamp@%p\n", This, pRamp);
hDC = GetDC(This->win_handle); hDC = GetDC(This->device_window);
GetDeviceGammaRamp(hDC, pRamp); GetDeviceGammaRamp(hDC, pRamp);
ReleaseDC(This->win_handle, hDC); ReleaseDC(This->device_window, hDC);
return WINED3D_OK; return WINED3D_OK;
} }

View file

@ -37,24 +37,27 @@ static void WINAPI IWineGDISwapChainImpl_Destroy(IWineD3DSwapChain *iface)
IWineD3DSwapChain_SetGammaRamp(iface, 0, &This->orig_gamma); IWineD3DSwapChain_SetGammaRamp(iface, 0, &This->orig_gamma);
/* release the ref to the front and back buffer parents */ /* release the ref to the front and back buffer parents */
if(This->frontBuffer) { if (This->front_buffer)
IWineD3DSurface_SetContainer(This->frontBuffer, 0); {
if (IWineD3DSurface_Release(This->frontBuffer) > 0) IWineD3DSurface_SetContainer((IWineD3DSurface *)This->front_buffer, NULL);
if (IWineD3DSurface_Release((IWineD3DSurface *)This->front_buffer) > 0)
{ {
WARN("(%p) Something's still holding the front buffer\n",This); WARN("(%p) Something's still holding the front buffer\n",This);
} }
} }
if(This->backBuffer) { if (This->back_buffers)
{
UINT i; UINT i;
for(i = 0; i < This->presentParms.BackBufferCount; i++) { for (i = 0; i < This->presentParms.BackBufferCount; ++i)
IWineD3DSurface_SetContainer(This->backBuffer[i], 0); {
if (IWineD3DSurface_Release(This->backBuffer[i]) > 0) IWineD3DSurface_SetContainer((IWineD3DSurface *)This->back_buffers[i], NULL);
if (IWineD3DSurface_Release((IWineD3DSurface *)This->back_buffers[i]))
{ {
WARN("(%p) Something's still holding the back buffer\n",This); WARN("(%p) Something's still holding the back buffer\n",This);
} }
} }
HeapFree(GetProcessHeap(), 0, This->backBuffer); HeapFree(GetProcessHeap(), 0, This->back_buffers);
} }
/* Restore the screen resolution if we rendered in fullscreen /* Restore the screen resolution if we rendered in fullscreen
@ -86,7 +89,7 @@ static void WINAPI IWineGDISwapChainImpl_Destroy(IWineD3DSwapChain *iface)
*****************************************************************************/ *****************************************************************************/
void x11_copy_to_screen(IWineD3DSwapChainImpl *This, const RECT *rc) void x11_copy_to_screen(IWineD3DSwapChainImpl *This, const RECT *rc)
{ {
IWineD3DSurfaceImpl *front = (IWineD3DSurfaceImpl *) This->frontBuffer; IWineD3DSurfaceImpl *front = This->front_buffer;
if(front->resource.usage & WINED3DUSAGE_RENDERTARGET) { if(front->resource.usage & WINED3DUSAGE_RENDERTARGET) {
POINT offset = {0,0}; POINT offset = {0,0};
@ -172,12 +175,13 @@ static HRESULT WINAPI IWineGDISwapChainImpl_Present(IWineD3DSwapChain *iface, CO
IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *) iface; IWineD3DSwapChainImpl *This = (IWineD3DSwapChainImpl *) iface;
IWineD3DSurfaceImpl *front, *back; IWineD3DSurfaceImpl *front, *back;
if(!This->backBuffer) { if (!This->back_buffers)
{
WARN("Swapchain doesn't have a backbuffer, returning WINED3DERR_INVALIDCALL\n"); WARN("Swapchain doesn't have a backbuffer, returning WINED3DERR_INVALIDCALL\n");
return WINED3DERR_INVALIDCALL; return WINED3DERR_INVALIDCALL;
} }
front = (IWineD3DSurfaceImpl *) This->frontBuffer; front = This->front_buffer;
back = (IWineD3DSurfaceImpl *) This->backBuffer[0]; back = This->back_buffers[0];
/* Flip the DC */ /* Flip the DC */
{ {
@ -226,7 +230,7 @@ static HRESULT WINAPI IWineGDISwapChainImpl_Present(IWineD3DSwapChain *iface, CO
/* FPS support */ /* FPS support */
if (TRACE_ON(fps)) if (TRACE_ON(fps))
{ {
static long prev_time, frames; static LONG prev_time, frames;
DWORD time = GetTickCount(); DWORD time = GetTickCount();
frames++; frames++;

View file

@ -63,21 +63,22 @@ static void texture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3DSRG
{ {
/* context_acquire() sets isInDraw to TRUE when loading a pbuffer into a texture, /* context_acquire() sets isInDraw to TRUE when loading a pbuffer into a texture,
* thus no danger of recursive calls. */ * thus no danger of recursive calls. */
context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); context = context_acquire(device, NULL);
} }
if (This->resource.format_desc->format == WINED3DFMT_P8_UINT if (This->resource.format_desc->format == WINED3DFMT_P8_UINT
|| This->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM) || This->resource.format_desc->format == WINED3DFMT_P8_UINT_A8_UNORM)
{ {
for (i = 0; i < This->baseTexture.levels; ++i) for (i = 0; i < This->baseTexture.level_count; ++i)
{ {
if (palette9_changed((IWineD3DSurfaceImpl *)This->surfaces[i])) IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)This->baseTexture.sub_resources[i];
if (palette9_changed(surface))
{ {
TRACE("Reloading surface because the d3d8/9 palette was changed.\n"); TRACE("Reloading surface because the d3d8/9 palette was changed.\n");
/* TODO: This is not necessarily needed with hw palettized texture support. */ /* TODO: This is not necessarily needed with hw palettized texture support. */
IWineD3DSurface_LoadLocation(This->surfaces[i], SFLAG_INSYSMEM, NULL); IWineD3DSurface_LoadLocation((IWineD3DSurface *)surface, SFLAG_INSYSMEM, NULL);
/* Make sure the texture is reloaded because of the palette change, this kills performance though :( */ /* Make sure the texture is reloaded because of the palette change, this kills performance though :( */
IWineD3DSurface_ModifyLocation(This->surfaces[i], SFLAG_INTEXTURE, FALSE); IWineD3DSurface_ModifyLocation((IWineD3DSurface *)surface, SFLAG_INTEXTURE, FALSE);
} }
} }
} }
@ -86,9 +87,9 @@ static void texture_internal_preload(IWineD3DBaseTexture *iface, enum WINED3DSRG
* since the last load then reload the surfaces. */ * since the last load then reload the surfaces. */
if (*dirty) if (*dirty)
{ {
for (i = 0; i < This->baseTexture.levels; ++i) for (i = 0; i < This->baseTexture.level_count; ++i)
{ {
IWineD3DSurface_LoadTexture(This->surfaces[i], srgb_mode); IWineD3DSurface_LoadTexture((IWineD3DSurface *)This->baseTexture.sub_resources[i], srgb_mode);
} }
} }
else else
@ -108,17 +109,18 @@ static void texture_cleanup(IWineD3DTextureImpl *This)
TRACE("(%p) : Cleaning up\n", This); TRACE("(%p) : Cleaning up\n", This);
for (i = 0; i < This->baseTexture.levels; ++i) for (i = 0; i < This->baseTexture.level_count; ++i)
{ {
if (This->surfaces[i]) IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)This->baseTexture.sub_resources[i];
if (surface)
{ {
/* Clean out the texture name we gave to the surface so that the /* Clean out the texture name we gave to the surface so that the
* surface doesn't try and release it */ * surface doesn't try and release it */
surface_set_texture_name(This->surfaces[i], 0, TRUE); surface_set_texture_name(surface, 0, TRUE);
surface_set_texture_name(This->surfaces[i], 0, FALSE); surface_set_texture_name(surface, 0, FALSE);
surface_set_texture_target(This->surfaces[i], 0); surface_set_texture_target(surface, 0);
IWineD3DSurface_SetContainer(This->surfaces[i], 0); IWineD3DSurface_SetContainer((IWineD3DSurface *)surface, NULL);
IWineD3DSurface_Release(This->surfaces[i]); IWineD3DSurface_Release((IWineD3DSurface *)surface);
} }
} }
@ -204,10 +206,12 @@ static void WINAPI IWineD3DTextureImpl_UnLoad(IWineD3DTexture *iface) {
* surface before, this one will be a NOP and vice versa. Unloading an unloaded * surface before, this one will be a NOP and vice versa. Unloading an unloaded
* surface is fine * surface is fine
*/ */
for (i = 0; i < This->baseTexture.levels; i++) { for (i = 0; i < This->baseTexture.level_count; ++i)
IWineD3DSurface_UnLoad(This->surfaces[i]); {
surface_set_texture_name(This->surfaces[i], 0, FALSE); /* Delete rgb name */ IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)This->baseTexture.sub_resources[i];
surface_set_texture_name(This->surfaces[i], 0, TRUE); /* delete srgb name */ IWineD3DSurface_UnLoad((IWineD3DSurface *)surface);
surface_set_texture_name(surface, 0, FALSE); /* Delete rgb name */
surface_set_texture_name(surface, 0, TRUE); /* delete srgb name */
} }
basetexture_unload((IWineD3DBaseTexture *)iface); basetexture_unload((IWineD3DBaseTexture *)iface);
@ -276,14 +280,20 @@ static HRESULT WINAPI IWineD3DTextureImpl_BindTexture(IWineD3DTexture *iface, BO
gl_tex = &This->baseTexture.texture_rgb; gl_tex = &This->baseTexture.texture_rgb;
} }
for (i = 0; i < This->baseTexture.levels; ++i) { for (i = 0; i < This->baseTexture.level_count; ++i)
surface_set_texture_name(This->surfaces[i], gl_tex->name, This->baseTexture.is_srgb); {
IWineD3DSurfaceImpl *surface = (IWineD3DSurfaceImpl *)This->baseTexture.sub_resources[i];
surface_set_texture_name(surface, gl_tex->name, This->baseTexture.is_srgb);
} }
/* Conditinal non power of two textures use a different clamping default. If we're using the GL_WINE_normalized_texrect
* partial driver emulation, we're dealing with a GL_TEXTURE_2D texture which has the address mode set to repeat - something /* Conditinal non power of two textures use a different clamping
* that prevents us from hitting the accelerated codepath. Thus manually set the GL state. The same applies to filtering. * default. If we're using the GL_WINE_normalized_texrect partial
* Even if the texture has only one mip level, the default LINEAR_MIPMAP_LINEAR filter causes a SW fallback on macos. * driver emulation, we're dealing with a GL_TEXTURE_2D texture which
*/ * has the address mode set to repeat - something that prevents us
* from hitting the accelerated codepath. Thus manually set the GL
* 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)) {
ENTER_GL(); ENTER_GL();
glTexParameteri(IWineD3DTexture_GetTextureDimensions(iface), GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(IWineD3DTexture_GetTextureDimensions(iface), GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
@ -323,72 +333,94 @@ static BOOL WINAPI IWineD3DTextureImpl_IsCondNP2(IWineD3DTexture *iface) {
/* ******************************************* /* *******************************************
IWineD3DTexture IWineD3DTexture parts follow IWineD3DTexture IWineD3DTexture parts follow
******************************************* */ ******************************************* */
static HRESULT WINAPI IWineD3DTextureImpl_GetLevelDesc(IWineD3DTexture *iface, UINT Level, WINED3DSURFACE_DESC* pDesc) { static HRESULT WINAPI IWineD3DTextureImpl_GetLevelDesc(IWineD3DTexture *iface, UINT level, WINED3DSURFACE_DESC *desc)
IWineD3DTextureImpl *This = (IWineD3DTextureImpl *)iface; {
IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DSurface *surface;
if (Level < This->baseTexture.levels) { TRACE("iface %p, level %u, desc %p.\n", iface, level, desc);
TRACE("(%p) Level (%d)\n", This, Level);
return IWineD3DSurface_GetDesc(This->surfaces[Level], pDesc); if (!(surface = (IWineD3DSurface *)basetexture_get_sub_resource(texture, 0, level)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
WARN("(%p) level(%d) overflow Levels(%d)\n", This, Level, This->baseTexture.levels);
return WINED3DERR_INVALIDCALL; return IWineD3DSurface_GetDesc(surface, desc);
} }
static HRESULT WINAPI IWineD3DTextureImpl_GetSurfaceLevel(IWineD3DTexture *iface, UINT Level, IWineD3DSurface** ppSurfaceLevel) { static HRESULT WINAPI IWineD3DTextureImpl_GetSurfaceLevel(IWineD3DTexture *iface,
IWineD3DTextureImpl *This = (IWineD3DTextureImpl *)iface; UINT level, IWineD3DSurface **surface)
HRESULT hr = WINED3DERR_INVALIDCALL; {
IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DSurface *s;
if (Level < This->baseTexture.levels) { TRACE("iface %p, level %u, surface %p.\n", iface, level, surface);
*ppSurfaceLevel = This->surfaces[Level];
IWineD3DSurface_AddRef(This->surfaces[Level]); if (!(s = (IWineD3DSurface *)basetexture_get_sub_resource(texture, 0, level)))
hr = WINED3D_OK; {
TRACE("(%p) : returning %p for level %d\n", This, *ppSurfaceLevel, Level); WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
if (WINED3D_OK != hr) {
WARN("(%p) level(%d) overflow Levels(%d)\n", This, Level, This->baseTexture.levels); IWineD3DSurface_AddRef(s);
*ppSurfaceLevel = NULL; /* Just to be on the safe side.. */ *surface = s;
}
return hr; TRACE("Returning surface %p.\n", *surface);
return WINED3D_OK;
} }
static HRESULT WINAPI IWineD3DTextureImpl_LockRect(IWineD3DTexture *iface, UINT Level, WINED3DLOCKED_RECT *pLockedRect, static HRESULT WINAPI IWineD3DTextureImpl_LockRect(IWineD3DTexture *iface,
CONST RECT *pRect, DWORD Flags) { UINT level, WINED3DLOCKED_RECT *locked_rect, const RECT *rect, DWORD flags)
IWineD3DTextureImpl *This = (IWineD3DTextureImpl *)iface; {
HRESULT hr = WINED3DERR_INVALIDCALL; IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DSurface *surface;
if (Level < This->baseTexture.levels) { TRACE("iface %p, level %u, locked_rect %p, rect %s, flags %#x.\n",
hr = IWineD3DSurface_LockRect(This->surfaces[Level], pLockedRect, pRect, Flags); iface, level, locked_rect, wine_dbgstr_rect(rect), flags);
}
if (WINED3D_OK == hr) { if (!(surface = (IWineD3DSurface *)basetexture_get_sub_resource(texture, 0, level)))
TRACE("(%p) Level (%d) success\n", This, Level); {
} else { WARN("Failed to get sub-resource.\n");
WARN("(%p) level(%d) overflow Levels(%d)\n", This, Level, This->baseTexture.levels); return WINED3DERR_INVALIDCALL;
} }
return hr; return IWineD3DSurface_LockRect(surface, locked_rect, rect, flags);
} }
static HRESULT WINAPI IWineD3DTextureImpl_UnlockRect(IWineD3DTexture *iface, UINT Level) { static HRESULT WINAPI IWineD3DTextureImpl_UnlockRect(IWineD3DTexture *iface, UINT level)
IWineD3DTextureImpl *This = (IWineD3DTextureImpl *)iface; {
HRESULT hr = WINED3DERR_INVALIDCALL; IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DSurface *surface;
if (Level < This->baseTexture.levels) { TRACE("iface %p, level %u.\n", iface, level);
hr = IWineD3DSurface_UnlockRect(This->surfaces[Level]);
if (!(surface = (IWineD3DSurface *)basetexture_get_sub_resource(texture, 0, level)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
if ( WINED3D_OK == hr) {
TRACE("(%p) Level (%d) success\n", This, Level); return IWineD3DSurface_UnlockRect(surface);
} else {
WARN("(%p) level(%d) overflow Levels(%d)\n", This, Level, This->baseTexture.levels);
}
return hr;
} }
static HRESULT WINAPI IWineD3DTextureImpl_AddDirtyRect(IWineD3DTexture *iface, CONST RECT* pDirtyRect) { static HRESULT WINAPI IWineD3DTextureImpl_AddDirtyRect(IWineD3DTexture *iface, const RECT *dirty_rect)
IWineD3DTextureImpl *This = (IWineD3DTextureImpl *)iface; {
This->baseTexture.texture_rgb.dirty = TRUE; IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
This->baseTexture.texture_srgb.dirty = TRUE; IWineD3DSurfaceImpl *surface;
TRACE("(%p) : dirtyfication of surface Level (0)\n", This);
surface_add_dirty_rect(This->surfaces[0], pDirtyRect); TRACE("iface %p, dirty_rect %s.\n", iface, wine_dbgstr_rect(dirty_rect));
if (!(surface = (IWineD3DSurfaceImpl *)basetexture_get_sub_resource(texture, 0, 0)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
}
texture->baseTexture.texture_rgb.dirty = TRUE;
texture->baseTexture.texture_srgb.dirty = TRUE;
surface_add_dirty_rect(surface, dirty_rect);
return WINED3D_OK; return WINED3D_OK;
} }
@ -434,7 +466,7 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
IUnknown *parent, const struct wined3d_parent_ops *parent_ops) IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
{ {
const struct wined3d_gl_info *gl_info = &device->adapter->gl_info; const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
const struct GlPixelFormatDesc *format_desc = getFormatDescEntry(format, gl_info); const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, gl_info);
UINT pow2_width, pow2_height; UINT pow2_width, pow2_height;
UINT tmp_w, tmp_h; UINT tmp_w, tmp_h;
unsigned int i; unsigned int i;
@ -497,8 +529,8 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
texture->lpVtbl = &IWineD3DTexture_Vtbl; texture->lpVtbl = &IWineD3DTexture_Vtbl;
hr = basetexture_init((IWineD3DBaseTextureImpl *)texture, levels, WINED3DRTYPE_TEXTURE, hr = basetexture_init((IWineD3DBaseTextureImpl *)texture, 1, levels,
device, 0, usage, format_desc, pool, parent, parent_ops); WINED3DRTYPE_TEXTURE, device, 0, usage, format_desc, pool, parent, parent_ops);
if (FAILED(hr)) if (FAILED(hr))
{ {
WARN("Failed to initialize basetexture, returning %#x.\n", hr); WARN("Failed to initialize basetexture, returning %#x.\n", hr);
@ -565,22 +597,24 @@ HRESULT texture_init(IWineD3DTextureImpl *texture, UINT width, UINT height, UINT
/* Generate all the surfaces. */ /* Generate all the surfaces. */
tmp_w = width; tmp_w = width;
tmp_h = height; tmp_h = height;
for (i = 0; i < texture->baseTexture.levels; ++i) for (i = 0; i < texture->baseTexture.level_count; ++i)
{ {
IWineD3DSurface *surface;
/* Use the callback to create the texture surface. */ /* Use the callback to create the texture surface. */
hr = IWineD3DDeviceParent_CreateSurface(device->device_parent, parent, tmp_w, tmp_h, format_desc->format, hr = IWineD3DDeviceParent_CreateSurface(device->device_parent, parent, tmp_w, tmp_h, format_desc->format,
usage, pool, i, WINED3DCUBEMAP_FACE_POSITIVE_X, &texture->surfaces[i]); usage, pool, i, 0, &surface);
if (FAILED(hr) || ((IWineD3DSurfaceImpl *)texture->surfaces[i])->Flags & SFLAG_OVERSIZE) if (FAILED(hr))
{ {
FIXME("Failed to create surface %p, hr %#x\n", texture, hr); FIXME("Failed to create surface %p, hr %#x\n", texture, hr);
texture->surfaces[i] = NULL;
texture_cleanup(texture); texture_cleanup(texture);
return hr; return hr;
} }
IWineD3DSurface_SetContainer(texture->surfaces[i], (IWineD3DBase *)texture); IWineD3DSurface_SetContainer(surface, (IWineD3DBase *)texture);
TRACE("Created surface level %u @ %p.\n", i, texture->surfaces[i]); surface_set_texture_target((IWineD3DSurfaceImpl *)surface, texture->target);
surface_set_texture_target(texture->surfaces[i], texture->target); texture->baseTexture.sub_resources[i] = (IWineD3DResourceImpl *)surface;
TRACE("Created surface level %u @ %p.\n", i, surface);
/* Calculate the next mipmap level. */ /* Calculate the next mipmap level. */
tmp_w = max(1, tmp_w >> 1); tmp_w = max(1, tmp_w >> 1);
tmp_h = max(1, tmp_h >> 1); tmp_h = max(1, tmp_h >> 1);

File diff suppressed because it is too large Load diff

View file

@ -97,7 +97,7 @@ static HRESULT STDMETHODCALLTYPE rendertarget_view_GetResource(IWineD3DRendertar
return WINED3D_OK; return WINED3D_OK;
} }
const struct IWineD3DRendertargetViewVtbl wined3d_rendertarget_view_vtbl = static const struct IWineD3DRendertargetViewVtbl wined3d_rendertarget_view_vtbl =
{ {
/* IUnknown methods */ /* IUnknown methods */
rendertarget_view_QueryInterface, rendertarget_view_QueryInterface,
@ -108,3 +108,13 @@ const struct IWineD3DRendertargetViewVtbl wined3d_rendertarget_view_vtbl =
/* IWineD3DRendertargetView methods */ /* IWineD3DRendertargetView methods */
rendertarget_view_GetResource, rendertarget_view_GetResource,
}; };
void wined3d_rendertarget_view_init(struct wined3d_rendertarget_view *view,
IWineD3DResource *resource, IUnknown *parent)
{
view->vtbl = &wined3d_rendertarget_view_vtbl;
view->refcount = 1;
IWineD3DResource_AddRef(resource);
view->resource = resource;
view->parent = parent;
}

View file

@ -25,7 +25,6 @@
#include "wined3d_private.h" #include "wined3d_private.h"
WINE_DEFAULT_DEBUG_CHANNEL(d3d_surface); WINE_DEFAULT_DEBUG_CHANNEL(d3d_surface);
#define GLINFO_LOCATION This->resource.device->adapter->gl_info
/* Context activation is done by the caller. */ /* Context activation is done by the caller. */
static void volume_bind_and_dirtify(IWineD3DVolume *iface) { static void volume_bind_and_dirtify(IWineD3DVolume *iface) {
@ -313,9 +312,11 @@ static HRESULT WINAPI IWineD3DVolumeImpl_SetContainer(IWineD3DVolume *iface, IWi
} }
/* Context activation is done by the caller. */ /* Context activation is done by the caller. */
static HRESULT WINAPI IWineD3DVolumeImpl_LoadTexture(IWineD3DVolume *iface, int gl_level, BOOL srgb_mode) { static HRESULT WINAPI IWineD3DVolumeImpl_LoadTexture(IWineD3DVolume *iface, int gl_level, BOOL srgb_mode)
IWineD3DVolumeImpl *This = (IWineD3DVolumeImpl *)iface; {
const struct GlPixelFormatDesc *glDesc = This->resource.format_desc; 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;
TRACE("(%p) : level %u, format %s (0x%08x)\n", This, gl_level, debug_d3dformat(glDesc->format), glDesc->format); TRACE("(%p) : level %u, format %s (0x%08x)\n", This, gl_level, debug_d3dformat(glDesc->format), glDesc->format);
@ -386,7 +387,7 @@ HRESULT volume_init(IWineD3DVolumeImpl *volume, IWineD3DDeviceImpl *device, UINT
IUnknown *parent, const struct wined3d_parent_ops *parent_ops) IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
{ {
const struct wined3d_gl_info *gl_info = &device->adapter->gl_info; const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
const struct GlPixelFormatDesc *format_desc = getFormatDescEntry(format, gl_info); const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, gl_info);
HRESULT hr; HRESULT hr;
if (!gl_info->supported[EXT_TEXTURE3D]) if (!gl_info->supported[EXT_TEXTURE3D])

View file

@ -39,7 +39,7 @@ static void volumetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINE
TRACE("(%p) : About to load texture.\n", This); TRACE("(%p) : About to load texture.\n", This);
if (!device->isInDraw) context = context_acquire(device, NULL, CTXUSAGE_RESOURCELOAD); if (!device->isInDraw) context = context_acquire(device, NULL);
else if (gl_info->supported[EXT_TEXTURE_SRGB] && This->baseTexture.bindCount > 0) 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->samplerState[This->baseTexture.sampler][WINED3DSAMP_SRGBTEXTURE];
@ -51,17 +51,19 @@ static void volumetexture_internal_preload(IWineD3DBaseTexture *iface, enum WINE
* since the last load then reload the volumes. */ * since the last load then reload the volumes. */
if (This->baseTexture.texture_rgb.dirty) if (This->baseTexture.texture_rgb.dirty)
{ {
for (i = 0; i < This->baseTexture.levels; ++i) for (i = 0; i < This->baseTexture.level_count; ++i)
{ {
IWineD3DVolume_LoadTexture(This->volumes[i], i, srgb_mode); IWineD3DVolume *volume = (IWineD3DVolume *)This->baseTexture.sub_resources[i];
IWineD3DVolume_LoadTexture(volume, i, srgb_mode);
} }
} }
else if (srgb_was_toggled) else if (srgb_was_toggled)
{ {
for (i = 0; i < This->baseTexture.levels; ++i) for (i = 0; i < This->baseTexture.level_count; ++i)
{ {
volume_add_dirty_box(This->volumes[i], NULL); IWineD3DVolume *volume = (IWineD3DVolume *)This->baseTexture.sub_resources[i];
IWineD3DVolume_LoadTexture(This->volumes[i], i, srgb_mode); volume_add_dirty_box(volume, NULL);
IWineD3DVolume_LoadTexture(volume, i, srgb_mode);
} }
} }
else else
@ -81,9 +83,9 @@ static void volumetexture_cleanup(IWineD3DVolumeTextureImpl *This)
TRACE("(%p) : Cleaning up.\n", This); TRACE("(%p) : Cleaning up.\n", This);
for (i = 0; i < This->baseTexture.levels; ++i) for (i = 0; i < This->baseTexture.level_count; ++i)
{ {
IWineD3DVolume *volume = This->volumes[i]; IWineD3DVolume *volume = (IWineD3DVolume *)This->baseTexture.sub_resources[i];
if (volume) if (volume)
{ {
@ -172,8 +174,9 @@ static void WINAPI IWineD3DVolumeTextureImpl_UnLoad(IWineD3DVolumeTexture *iface
* surface before, this one will be a NOP and vice versa. Unloading an unloaded * surface before, this one will be a NOP and vice versa. Unloading an unloaded
* surface is fine * surface is fine
*/ */
for (i = 0; i < This->baseTexture.levels; i++) { for (i = 0; i < This->baseTexture.level_count; ++i)
IWineD3DVolume_UnLoad(This->volumes[i]); {
IWineD3DVolume_UnLoad((IWineD3DVolume *)This->baseTexture.sub_resources[i]);
} }
basetexture_unload((IWineD3DBaseTexture *)iface); basetexture_unload((IWineD3DBaseTexture *)iface);
@ -250,65 +253,95 @@ static BOOL WINAPI IWineD3DVolumeTextureImpl_IsCondNP2(IWineD3DVolumeTexture *if
/* ******************************************* /* *******************************************
IWineD3DVolumeTexture IWineD3DVolumeTexture parts follow IWineD3DVolumeTexture IWineD3DVolumeTexture parts follow
******************************************* */ ******************************************* */
static HRESULT WINAPI IWineD3DVolumeTextureImpl_GetLevelDesc(IWineD3DVolumeTexture *iface, UINT Level,WINED3DVOLUME_DESC *pDesc) { static HRESULT WINAPI IWineD3DVolumeTextureImpl_GetLevelDesc(IWineD3DVolumeTexture *iface,
IWineD3DVolumeTextureImpl *This = (IWineD3DVolumeTextureImpl *)iface; UINT level, WINED3DVOLUME_DESC *desc)
if (Level < This->baseTexture.levels) { {
TRACE("(%p) Level (%d)\n", This, Level); IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
return IWineD3DVolume_GetDesc(This->volumes[Level], pDesc); IWineD3DVolume *volume;
} else {
WARN("(%p) Level (%d)\n", This, Level); TRACE("iface %p, level %u, desc %p.\n", iface, level, desc);
if (!(volume = (IWineD3DVolume *)basetexture_get_sub_resource(texture, 0, level)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
return IWineD3DVolume_GetDesc(volume, desc);
}
static HRESULT WINAPI IWineD3DVolumeTextureImpl_GetVolumeLevel(IWineD3DVolumeTexture *iface,
UINT level, IWineD3DVolume **volume)
{
IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DVolume *v;
TRACE("iface %p, level %u, volume %p.\n", iface, level, volume);
if (!(v = (IWineD3DVolume *)basetexture_get_sub_resource(texture, 0, level)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
}
IWineD3DVolume_AddRef(v);
*volume = v;
TRACE("Returning volume %p.\n", *volume);
return WINED3D_OK; return WINED3D_OK;
} }
static HRESULT WINAPI IWineD3DVolumeTextureImpl_GetVolumeLevel(IWineD3DVolumeTexture *iface, UINT Level, IWineD3DVolume** ppVolumeLevel) {
IWineD3DVolumeTextureImpl *This = (IWineD3DVolumeTextureImpl *)iface; static HRESULT WINAPI IWineD3DVolumeTextureImpl_LockBox(IWineD3DVolumeTexture *iface,
if (Level < This->baseTexture.levels) { UINT level, WINED3DLOCKED_BOX *locked_box, const WINED3DBOX *box, DWORD flags)
*ppVolumeLevel = This->volumes[Level]; {
IWineD3DVolume_AddRef(*ppVolumeLevel); IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
TRACE("(%p) -> level(%d) returning volume@%p\n", This, Level, *ppVolumeLevel); IWineD3DVolume *volume;
} else {
WARN("(%p) Level(%d) overflow Levels(%d)\n", This, Level, This->baseTexture.levels); TRACE("iface %p, level %u, locked_box %p, box %p, flags %#x.\n",
return WINED3DERR_INVALIDCALL; iface, level, locked_box, box, flags);
if (!(volume = (IWineD3DVolume *)basetexture_get_sub_resource(texture, 0, level)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
return WINED3D_OK;
} return IWineD3DVolume_LockBox(volume, locked_box, box, flags);
static HRESULT WINAPI IWineD3DVolumeTextureImpl_LockBox(IWineD3DVolumeTexture *iface, UINT Level, WINED3DLOCKED_BOX* pLockedVolume, CONST WINED3DBOX* pBox, DWORD Flags) {
HRESULT hr;
IWineD3DVolumeTextureImpl *This = (IWineD3DVolumeTextureImpl *)iface;
if (Level < This->baseTexture.levels) {
hr = IWineD3DVolume_LockBox(This->volumes[Level], pLockedVolume, pBox, Flags);
TRACE("(%p) Level (%d) success(%u)\n", This, Level, hr);
} else {
FIXME("(%p) level(%d) overflow Levels(%d)\n", This, Level, This->baseTexture.levels);
return WINED3DERR_INVALIDCALL;
}
return hr;
} }
static HRESULT WINAPI IWineD3DVolumeTextureImpl_UnlockBox(IWineD3DVolumeTexture *iface, UINT Level) { static HRESULT WINAPI IWineD3DVolumeTextureImpl_UnlockBox(IWineD3DVolumeTexture *iface, UINT level)
HRESULT hr; {
IWineD3DVolumeTextureImpl *This = (IWineD3DVolumeTextureImpl *)iface; IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
IWineD3DVolume *volume;
if (Level < This->baseTexture.levels) { TRACE("iface %p, level %u.\n", iface, level);
hr = IWineD3DVolume_UnlockBox(This->volumes[Level]);
TRACE("(%p) -> level(%d) success(%u)\n", This, Level, hr);
} else { if (!(volume = (IWineD3DVolume *)basetexture_get_sub_resource(texture, 0, level)))
FIXME("(%p) level(%d) overflow Levels(%d)\n", This, Level, This->baseTexture.levels); {
return WINED3DERR_INVALIDCALL; WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
} }
return hr;
return IWineD3DVolume_UnlockBox(volume);
} }
static HRESULT WINAPI IWineD3DVolumeTextureImpl_AddDirtyBox(IWineD3DVolumeTexture *iface, CONST WINED3DBOX* pDirtyBox) { static HRESULT WINAPI IWineD3DVolumeTextureImpl_AddDirtyBox(IWineD3DVolumeTexture *iface, const WINED3DBOX *dirty_box)
IWineD3DVolumeTextureImpl *This = (IWineD3DVolumeTextureImpl *)iface; {
This->baseTexture.texture_rgb.dirty = TRUE; IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *)iface;
This->baseTexture.texture_srgb.dirty = TRUE; IWineD3DVolume *volume;
TRACE("(%p) : dirtyfication of volume Level (0)\n", This);
volume_add_dirty_box(This->volumes[0], pDirtyBox); TRACE("iface %p, dirty_box %p.\n", iface, dirty_box);
if (!(volume = (IWineD3DVolume *)basetexture_get_sub_resource(texture, 0, 0)))
{
WARN("Failed to get sub-resource.\n");
return WINED3DERR_INVALIDCALL;
}
texture->baseTexture.texture_rgb.dirty = TRUE;
texture->baseTexture.texture_srgb.dirty = TRUE;
volume_add_dirty_box(volume, dirty_box);
return WINED3D_OK; return WINED3D_OK;
} }
@ -355,7 +388,7 @@ HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT
WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops)
{ {
const struct wined3d_gl_info *gl_info = &device->adapter->gl_info; const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
const struct GlPixelFormatDesc *format_desc = getFormatDescEntry(format, gl_info); const struct wined3d_format_desc *format_desc = getFormatDescEntry(format, gl_info);
UINT tmp_w, tmp_h, tmp_d; UINT tmp_w, tmp_h, tmp_d;
unsigned int i; unsigned int i;
HRESULT hr; HRESULT hr;
@ -399,8 +432,8 @@ HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT
texture->lpVtbl = &IWineD3DVolumeTexture_Vtbl; texture->lpVtbl = &IWineD3DVolumeTexture_Vtbl;
hr = basetexture_init((IWineD3DBaseTextureImpl *)texture, levels, WINED3DRTYPE_VOLUMETEXTURE, hr = basetexture_init((IWineD3DBaseTextureImpl *)texture, 1, levels,
device, 0, usage, format_desc, pool, parent, parent_ops); WINED3DRTYPE_VOLUMETEXTURE, device, 0, usage, format_desc, pool, parent, parent_ops);
if (FAILED(hr)) if (FAILED(hr))
{ {
WARN("Failed to initialize basetexture, returning %#x.\n", hr); WARN("Failed to initialize basetexture, returning %#x.\n", hr);
@ -418,21 +451,23 @@ HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT
tmp_h = height; tmp_h = height;
tmp_d = depth; tmp_d = depth;
for (i = 0; i < texture->baseTexture.levels; ++i) for (i = 0; i < texture->baseTexture.level_count; ++i)
{ {
IWineD3DVolume *volume;
/* Create the volume. */ /* Create the volume. */
hr = IWineD3DDeviceParent_CreateVolume(device->device_parent, parent, hr = IWineD3DDeviceParent_CreateVolume(device->device_parent, parent,
tmp_w, tmp_h, tmp_d, format, pool, usage, &texture->volumes[i]); tmp_w, tmp_h, tmp_d, format, pool, usage, &volume);
if (FAILED(hr)) if (FAILED(hr))
{ {
ERR("Creating a volume for the volume texture failed, hr %#x.\n", hr); ERR("Creating a volume for the volume texture failed, hr %#x.\n", hr);
texture->volumes[i] = NULL;
volumetexture_cleanup(texture); volumetexture_cleanup(texture);
return hr; return hr;
} }
/* Set its container to this texture. */ /* Set its container to this texture. */
IWineD3DVolume_SetContainer(texture->volumes[i], (IWineD3DBase *)texture); IWineD3DVolume_SetContainer(volume, (IWineD3DBase *)texture);
texture->baseTexture.sub_resources[i] = (IWineD3DResourceImpl *)volume;
/* Calculate the next mipmap level. */ /* Calculate the next mipmap level. */
tmp_w = max(1, tmp_w >> 1); tmp_w = max(1, tmp_w >> 1);

View file

@ -1754,6 +1754,7 @@ typedef enum wined3d_gl_extension
ARB_SHADER_OBJECTS, ARB_SHADER_OBJECTS,
ARB_SHADER_TEXTURE_LOD, ARB_SHADER_TEXTURE_LOD,
ARB_SHADING_LANGUAGE_100, ARB_SHADING_LANGUAGE_100,
ARB_SHADOW,
ARB_SYNC, ARB_SYNC,
ARB_TEXTURE_BORDER_CLAMP, ARB_TEXTURE_BORDER_CLAMP,
ARB_TEXTURE_COMPRESSION, ARB_TEXTURE_COMPRESSION,
@ -1782,6 +1783,7 @@ typedef enum wined3d_gl_extension
EXT_BLEND_EQUATION_SEPARATE, EXT_BLEND_EQUATION_SEPARATE,
EXT_BLEND_FUNC_SEPARATE, EXT_BLEND_FUNC_SEPARATE,
EXT_BLEND_MINMAX, EXT_BLEND_MINMAX,
EXT_DRAW_BUFFERS2,
EXT_FOG_COORD, EXT_FOG_COORD,
EXT_FRAMEBUFFER_BLIT, EXT_FRAMEBUFFER_BLIT,
EXT_FRAMEBUFFER_MULTISAMPLE, EXT_FRAMEBUFFER_MULTISAMPLE,
@ -1829,7 +1831,6 @@ typedef enum wined3d_gl_extension
SGIS_GENERATE_MIPMAP, SGIS_GENERATE_MIPMAP,
SGI_VIDEO_SYNC, SGI_VIDEO_SYNC,
/* WGL extensions */ /* WGL extensions */
WGL_ARB_PBUFFER,
WGL_ARB_PIXEL_FORMAT, WGL_ARB_PIXEL_FORMAT,
WGL_WINE_PIXEL_FORMAT_PASSTHROUGH, WGL_WINE_PIXEL_FORMAT_PASSTHROUGH,
/* Internally used */ /* Internally used */
@ -2404,6 +2405,14 @@ typedef unsigned int GLhandleARB;
#define GL_SHADING_LANGUAGE_VERSION_ARB 0x8b8c #define GL_SHADING_LANGUAGE_VERSION_ARB 0x8b8c
#endif #endif
/* GL_ARB_shadow */
#ifndef GL_ARB_shadow
#define GL_ARB_shadow 1
#define GL_TEXTURE_COMPARE_MODE_ARB 0x884c
#define GL_TEXTURE_COMPARE_FUNC_ARB 0x884d
#define GL_COMPARE_R_TO_TEXTURE_ARB 0x884e
#endif
/* GL_ARB_sync */ /* GL_ARB_sync */
#ifndef GL_ARB_sync #ifndef GL_ARB_sync
#define GL_ARB_sync 1 #define GL_ARB_sync 1
@ -2959,6 +2968,15 @@ typedef void (WINE_GLAPI *PGLFNBLENDEQUATIONSEPARATEEXTPROC)(GLenum modeRGB, GLe
typedef void (WINE_GLAPI *PGLFNBLENDFUNCSEPARATEEXTPROC)(GLenum sfactorRGB, GLenum dfactorRGB, typedef void (WINE_GLAPI *PGLFNBLENDFUNCSEPARATEEXTPROC)(GLenum sfactorRGB, GLenum dfactorRGB,
GLenum sfactorAlpha, GLenum dfactorAlpha); GLenum sfactorAlpha, GLenum dfactorAlpha);
/* GL_EXT_draw_buffers2 */
typedef GLvoid (WINE_GLAPI *PGLFNCOLORMASKINDEXEDEXTPROC)(GLuint buffer_idx, GLboolean r, GLboolean g,
GLboolean b, GLboolean a);
typedef GLvoid (WINE_GLAPI *PGLFNGETBOOLEANINDEXEDVEXTPROC)(GLenum param, GLuint index, GLboolean *value);
typedef GLvoid (WINE_GLAPI *PGLFNGETINTEGERINDEXEDVEXTPROC)(GLenum param, GLuint index, GLint *value);
typedef GLvoid (WINE_GLAPI *PGLFNENABLEINDEXEDEXTPROC)(GLenum target, GLuint index);
typedef GLvoid (WINE_GLAPI *PGLFNDISABLEINDEXEDEXTPROC)(GLenum target, GLuint index);
typedef GLboolean (WINE_GLAPI *PGLFNISENABLEDINDEXEDEXTPROC)(GLenum target, GLuint index);
/* GL_EXT_fog_coord */ /* GL_EXT_fog_coord */
#ifndef GL_EXT_fog_coord #ifndef GL_EXT_fog_coord
#define GL_EXT_fog_coord 1 #define GL_EXT_fog_coord 1
@ -3680,26 +3698,6 @@ typedef const char *(WINAPI *WINED3D_PFNWGLGETEXTENSIONSSTRINGARBPROC)(HDC hdc);
#define WGL_SAMPLES_ARB 0x2042 #define WGL_SAMPLES_ARB 0x2042
#endif #endif
/* WGL_ARB_pbuffer */
#ifndef WGL_ARB_pbuffer
#define WGL_ARB_pbuffer 1
#define WGL_DRAW_TO_PBUFFER_ARB 0x202d
#define WGL_MAX_PBUFFER_PIXELS_ARB 0x202e
#define WGL_MAX_PBUFFER_WIDTH_ARB 0x202f
#define WGL_MAX_PBUFFER_HEIGHT_ARB 0x2030
#define WGL_PBUFFER_LARGEST_ARB 0x2033
#define WGL_PBUFFER_WIDTH_ARB 0x2034
#define WGL_PBUFFER_HEIGHT_ARB 0x2035
#define WGL_PBUFFER_LOST_ARB 0x2036
#endif
DECLARE_HANDLE(HPBUFFERARB);
typedef HPBUFFERARB (WINAPI *WINED3D_PFNWGLCREATEPBUFFERARBPROC)(HDC hDC, int iPixelFormat,
int iWidth, int iHeight, const int *piAttribList);
typedef HDC (WINAPI *WINED3D_PFNWGLGETPBUFFERDCARBPROC)(HPBUFFERARB hPbuffer);
typedef int (WINAPI *WINED3D_PFNWGLRELEASEPBUFFERDCARBPROC)(HPBUFFERARB hPbuffer, HDC hDC);
typedef BOOL (WINAPI *WINED3D_PFNWGLDESTROYPBUFFERARBPROC)(HPBUFFERARB hPbuffer);
typedef BOOL (WINAPI *WINED3D_PFNWGLQUERYPBUFFERARBPROC)(HPBUFFERARB hPbuffer, int iAttribute, int *piValue);
/* WGL_ARB_pixel_format */ /* WGL_ARB_pixel_format */
#ifndef WGL_ARB_pixel_format #ifndef WGL_ARB_pixel_format
#define WGL_ARB_pixel_format 1 #define WGL_ARB_pixel_format 1
@ -3930,7 +3928,7 @@ typedef BOOL (WINAPI *WINED3D_PFNWGLSETPIXELFORMATWINE)(HDC hdc, int iPixelForma
glUniform3iARB, ARB_SHADER_OBJECTS, NULL) \ glUniform3iARB, ARB_SHADER_OBJECTS, NULL) \
USE_GL_FUNC(WINED3D_PFNGLUNIFORM4IARBPROC, \ USE_GL_FUNC(WINED3D_PFNGLUNIFORM4IARBPROC, \
glUniform4iARB, ARB_SHADER_OBJECTS, NULL) \ glUniform4iARB, ARB_SHADER_OBJECTS, NULL) \
USE_GL_FUNC(WINED3D_PFNGLUNIFORM1IARBPROC, \ USE_GL_FUNC(WINED3D_PFNGLUNIFORM1FARBPROC, \
glUniform1fARB, ARB_SHADER_OBJECTS, NULL) \ glUniform1fARB, ARB_SHADER_OBJECTS, NULL) \
USE_GL_FUNC(WINED3D_PFNGLUNIFORM2FARBPROC, \ USE_GL_FUNC(WINED3D_PFNGLUNIFORM2FARBPROC, \
glUniform2fARB, ARB_SHADER_OBJECTS, NULL) \ glUniform2fARB, ARB_SHADER_OBJECTS, NULL) \
@ -4199,6 +4197,19 @@ typedef BOOL (WINAPI *WINED3D_PFNWGLSETPIXELFORMATWINE)(HDC hdc, int iPixelForma
/* GL_EXT_blend_func_separate */ \ /* GL_EXT_blend_func_separate */ \
USE_GL_FUNC(PGLFNBLENDEQUATIONSEPARATEEXTPROC, \ USE_GL_FUNC(PGLFNBLENDEQUATIONSEPARATEEXTPROC, \
glBlendEquationSeparateEXT, EXT_BLEND_EQUATION_SEPARATE, NULL) \ glBlendEquationSeparateEXT, EXT_BLEND_EQUATION_SEPARATE, NULL) \
/* GL_EXT_draw_buffers2 */ \
USE_GL_FUNC(PGLFNCOLORMASKINDEXEDEXTPROC, \
glColorMaskIndexedEXT, EXT_DRAW_BUFFERS2, NULL) \
USE_GL_FUNC(PGLFNGETBOOLEANINDEXEDVEXTPROC, \
glGetBooleanIndexedvEXT, EXT_DRAW_BUFFERS2, NULL) \
USE_GL_FUNC(PGLFNGETINTEGERINDEXEDVEXTPROC, \
glGetIntegerIndexedvEXT, EXT_DRAW_BUFFERS2, NULL) \
USE_GL_FUNC(PGLFNENABLEINDEXEDEXTPROC, \
glEnableIndexedEXT, EXT_DRAW_BUFFERS2, NULL) \
USE_GL_FUNC(PGLFNDISABLEINDEXEDEXTPROC, \
glDisableIndexedEXT, EXT_DRAW_BUFFERS2, NULL) \
USE_GL_FUNC(PGLFNISENABLEDINDEXEDEXTPROC, \
glIsEnabledIndexedEXT, EXT_DRAW_BUFFERS2, NULL) \
/* GL_EXT_fog_coord */ \ /* GL_EXT_fog_coord */ \
USE_GL_FUNC(PGLFNGLFOGCOORDFEXTPROC, \ USE_GL_FUNC(PGLFNGLFOGCOORDFEXTPROC, \
glFogCoordfEXT, EXT_FOG_COORD, NULL) \ glFogCoordfEXT, EXT_FOG_COORD, NULL) \
@ -4489,11 +4500,6 @@ typedef BOOL (WINAPI *WINED3D_PFNWGLSETPIXELFORMATWINE)(HDC hdc, int iPixelForma
USE_GL_FUNC(WINED3D_PFNWGLGETPIXELFORMATATTRIBIVARBPROC, wglGetPixelFormatAttribivARB, 0, NULL) \ USE_GL_FUNC(WINED3D_PFNWGLGETPIXELFORMATATTRIBIVARBPROC, wglGetPixelFormatAttribivARB, 0, NULL) \
USE_GL_FUNC(WINED3D_PFNWGLGETPIXELFORMATATTRIBFVARBPROC, wglGetPixelFormatAttribfvARB, 0, NULL) \ USE_GL_FUNC(WINED3D_PFNWGLGETPIXELFORMATATTRIBFVARBPROC, wglGetPixelFormatAttribfvARB, 0, NULL) \
USE_GL_FUNC(WINED3D_PFNWGLCHOOSEPIXELFORMATARBPROC, wglChoosePixelFormatARB, 0, NULL) \ USE_GL_FUNC(WINED3D_PFNWGLCHOOSEPIXELFORMATARBPROC, wglChoosePixelFormatARB, 0, NULL) \
USE_GL_FUNC(WINED3D_PFNWGLCREATEPBUFFERARBPROC, wglCreatePbufferARB, 0, NULL) \
USE_GL_FUNC(WINED3D_PFNWGLGETPBUFFERDCARBPROC, wglGetPbufferDCARB, 0, NULL) \
USE_GL_FUNC(WINED3D_PFNWGLRELEASEPBUFFERDCARBPROC, wglReleasePbufferDCARB, 0, NULL) \
USE_GL_FUNC(WINED3D_PFNWGLDESTROYPBUFFERARBPROC, wglDestroyPbufferARB, 0, NULL) \
USE_GL_FUNC(WINED3D_PFNWGLQUERYPBUFFERARBPROC, wglQueryPbufferARB, 0, NULL) \
USE_GL_FUNC(WINED3D_PFNWGLSETPIXELFORMATWINE, wglSetPixelFormatWINE, 0, NULL) USE_GL_FUNC(WINED3D_PFNWGLSETPIXELFORMATWINE, wglSetPixelFormatWINE, 0, NULL)
#endif /* __WINE_WINED3D_GL */ #endif /* __WINE_WINED3D_GL */

View file

@ -72,30 +72,31 @@ wined3d_settings_t wined3d_settings =
PCI_DEVICE_NONE,/* PCI Device ID */ PCI_DEVICE_NONE,/* PCI Device ID */
0, /* The default of memory is set in FillGLCaps */ 0, /* The default of memory is set in FillGLCaps */
NULL, /* No wine logo by default */ NULL, /* No wine logo by default */
FALSE /* Disable multisampling for now due to Nvidia driver bugs which happens for some users */ FALSE, /* Disable multisampling for now due to Nvidia driver bugs which happens for some users */
FALSE, /* No strict draw ordering. */
}; };
IWineD3D* WINAPI WineDirect3DCreate(UINT dxVersion, IUnknown *parent) { IWineD3D * WINAPI WineDirect3DCreate(UINT version, IUnknown *parent)
IWineD3DImpl* object; {
IWineD3DImpl *object;
HRESULT hr;
object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IWineD3DImpl)); object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
object->lpVtbl = &IWineD3D_Vtbl; if (!object)
object->dxVersion = dxVersion;
object->ref = 1;
object->parent = parent;
if (!InitAdapters(object))
{ {
WARN("Failed to initialize direct3d adapters, Direct3D will not be available\n"); ERR("Failed to allocate wined3d object memory.\n");
if (dxVersion > 7) return NULL;
{
ERR("Direct3D%d is not available without opengl\n", dxVersion);
HeapFree(GetProcessHeap(), 0, object);
return NULL;
}
} }
TRACE("Created WineD3D object @ %p for d3d%d support\n", object, dxVersion); hr = wined3d_init(object, version, parent);
if (FAILED(hr))
{
WARN("Failed to initialize wined3d object, hr %#x.\n", hr);
HeapFree(GetProcessHeap(), 0, object);
return NULL;
}
TRACE("Created wined3d object %p for d3d%d support.\n", object, version);
return (IWineD3D *)object; return (IWineD3D *)object;
} }
@ -120,7 +121,7 @@ static void CDECL wined3d_do_nothing(void)
{ {
} }
static BOOL wined3d_init(HINSTANCE hInstDLL) static BOOL wined3d_dll_init(HINSTANCE hInstDLL)
{ {
DWORD wined3d_context_tls_idx; DWORD wined3d_context_tls_idx;
HMODULE mod; HMODULE mod;
@ -236,11 +237,6 @@ static BOOL wined3d_init(HINSTANCE hInstDLL)
TRACE("Using the backbuffer for offscreen rendering\n"); TRACE("Using the backbuffer for offscreen rendering\n");
wined3d_settings.offscreen_rendering_mode = ORM_BACKBUFFER; wined3d_settings.offscreen_rendering_mode = ORM_BACKBUFFER;
} }
else if (!strcmp(buffer,"pbuffer"))
{
TRACE("Using PBuffers for offscreen rendering\n");
wined3d_settings.offscreen_rendering_mode = ORM_PBUFFER;
}
else if (!strcmp(buffer,"fbo")) else if (!strcmp(buffer,"fbo"))
{ {
TRACE("Using FBOs for offscreen rendering\n"); TRACE("Using FBOs for offscreen rendering\n");
@ -324,6 +320,12 @@ static BOOL wined3d_init(HINSTANCE hInstDLL)
wined3d_settings.allow_multisampling = TRUE; wined3d_settings.allow_multisampling = TRUE;
} }
} }
if (!get_config_key(hkey, appkey, "StrictDrawOrdering", buffer, size)
&& !strcmp(buffer,"enabled"))
{
TRACE("Enforcing strict draw ordering.\n");
wined3d_settings.strict_draw_ordering = TRUE;
}
} }
if (wined3d_settings.vs_mode == VS_HW) if (wined3d_settings.vs_mode == VS_HW)
TRACE("Allow HW vertex shaders\n"); TRACE("Allow HW vertex shaders\n");
@ -338,7 +340,7 @@ static BOOL wined3d_init(HINSTANCE hInstDLL)
return TRUE; return TRUE;
} }
static BOOL wined3d_destroy(HINSTANCE hInstDLL) static BOOL wined3d_dll_destroy(HINSTANCE hInstDLL)
{ {
DWORD wined3d_context_tls_idx = context_get_tls_idx(); DWORD wined3d_context_tls_idx = context_get_tls_idx();
unsigned int i; unsigned int i;
@ -478,10 +480,10 @@ BOOL WINAPI DllMain(HINSTANCE hInstDLL, DWORD fdwReason, LPVOID lpv)
switch (fdwReason) switch (fdwReason)
{ {
case DLL_PROCESS_ATTACH: case DLL_PROCESS_ATTACH:
return wined3d_init(hInstDLL); return wined3d_dll_init(hInstDLL);
case DLL_PROCESS_DETACH: case DLL_PROCESS_DETACH:
return wined3d_destroy(hInstDLL); return wined3d_dll_destroy(hInstDLL);
case DLL_THREAD_DETACH: case DLL_THREAD_DETACH:
{ {

View file

@ -50,6 +50,7 @@
#define WINED3D_QUIRK_GLSL_CLIP_VARYING 0x00000004 #define WINED3D_QUIRK_GLSL_CLIP_VARYING 0x00000004
#define WINED3D_QUIRK_ALLOWS_SPECULAR_ALPHA 0x00000008 #define WINED3D_QUIRK_ALLOWS_SPECULAR_ALPHA 0x00000008
#define WINED3D_QUIRK_NV_CLIP_BROKEN 0x00000010 #define WINED3D_QUIRK_NV_CLIP_BROKEN 0x00000010
#define WINED3D_QUIRK_FBO_TEX_UPDATE 0x00000020
/* Texture format fixups */ /* Texture format fixups */
@ -67,10 +68,11 @@ enum fixup_channel_source
enum complex_fixup enum complex_fixup
{ {
COMPLEX_FIXUP_YUY2 = 0, COMPLEX_FIXUP_NONE = 0,
COMPLEX_FIXUP_UYVY = 1, COMPLEX_FIXUP_YUY2 = 1,
COMPLEX_FIXUP_YV12 = 2, COMPLEX_FIXUP_UYVY = 2,
COMPLEX_FIXUP_P8 = 3, COMPLEX_FIXUP_YV12 = 3,
COMPLEX_FIXUP_P8 = 4,
}; };
#include <pshpack2.h> #include <pshpack2.h>
@ -234,8 +236,7 @@ static inline float float_24_to_32(DWORD in)
#define VBO_HW 1 #define VBO_HW 1
#define ORM_BACKBUFFER 0 #define ORM_BACKBUFFER 0
#define ORM_PBUFFER 1 #define ORM_FBO 1
#define ORM_FBO 2
#define SHADER_ARB 1 #define SHADER_ARB 1
#define SHADER_GLSL 2 #define SHADER_GLSL 2
@ -267,6 +268,7 @@ typedef struct wined3d_settings_s {
unsigned int emulated_textureram; unsigned int emulated_textureram;
char *logo; char *logo;
int allow_multisampling; int allow_multisampling;
BOOL strict_draw_ordering;
} wined3d_settings_t; } wined3d_settings_t;
extern wined3d_settings_t wined3d_settings DECLSPEC_HIDDEN; extern wined3d_settings_t wined3d_settings DECLSPEC_HIDDEN;
@ -539,7 +541,8 @@ typedef struct shader_reg_maps
WORD usestexldl : 1; WORD usestexldl : 1;
WORD usesifc : 1; WORD usesifc : 1;
WORD usescall : 1; WORD usescall : 1;
WORD padding : 4; WORD usesrcp : 1;
WORD padding : 3;
/* Whether or not loops are used in this shader, and nesting depth */ /* Whether or not loops are used in this shader, and nesting depth */
unsigned loop_depth; unsigned loop_depth;
@ -643,14 +646,6 @@ struct shader_caps {
float PixelShader1xMaxValue; float PixelShader1xMaxValue;
DWORD MaxPixelShaderConst; DWORD MaxPixelShaderConst;
WINED3DVSHADERCAPS2_0 VS20Caps;
WINED3DPSHADERCAPS2_0 PS20Caps;
DWORD MaxVShaderInstructionsExecuted;
DWORD MaxPShaderInstructionsExecuted;
DWORD MaxVertexShader30InstructionSlots;
DWORD MaxPixelShader30InstructionSlots;
BOOL VSClipping; BOOL VSClipping;
}; };
@ -693,6 +688,7 @@ struct ps_compile_args {
/* Bitmap for NP2 texcoord fixups (16 samplers max currently). /* Bitmap for NP2 texcoord fixups (16 samplers max currently).
D3D9 has a limit of 16 samplers and the fixup is superfluous D3D9 has a limit of 16 samplers and the fixup is superfluous
in D3D10 (unconditional NP2 support mandatory). */ in D3D10 (unconditional NP2 support mandatory). */
WORD shadow; /* MAX_FRAGMENT_SAMPLERS, 16 */
}; };
enum fog_src_type { enum fog_src_type {
@ -711,7 +707,7 @@ struct wined3d_context;
typedef struct { typedef struct {
void (*shader_handle_instruction)(const struct wined3d_shader_instruction *); void (*shader_handle_instruction)(const struct wined3d_shader_instruction *);
void (*shader_select)(const struct wined3d_context *context, BOOL usePS, BOOL useVS); void (*shader_select)(const struct wined3d_context *context, BOOL usePS, BOOL useVS);
void (*shader_select_depth_blt)(IWineD3DDevice *iface, enum tex_types tex_type); void (*shader_select_depth_blt)(IWineD3DDevice *iface, enum tex_types tex_type, const SIZE *ds_mask_size);
void (*shader_deselect_depth_blt)(IWineD3DDevice *iface); void (*shader_deselect_depth_blt)(IWineD3DDevice *iface);
void (*shader_update_float_vertex_constants)(IWineD3DDevice *iface, UINT start, UINT count); void (*shader_update_float_vertex_constants)(IWineD3DDevice *iface, UINT start, UINT count);
void (*shader_update_float_pixel_constants)(IWineD3DDevice *iface, UINT start, UINT count); void (*shader_update_float_pixel_constants)(IWineD3DDevice *iface, UINT start, UINT count);
@ -752,7 +748,7 @@ extern int num_lock DECLSPEC_HIDDEN;
/* GL related defines */ /* GL related defines */
/* ------------------ */ /* ------------------ */
#define GL_EXTCALL(FuncName) (GLINFO_LOCATION.FuncName) #define GL_EXTCALL(f) (gl_info->f)
#define D3DCOLOR_B_R(dw) (((dw) >> 16) & 0xFF) #define D3DCOLOR_B_R(dw) (((dw) >> 16) & 0xFF)
#define D3DCOLOR_B_G(dw) (((dw) >> 8) & 0xFF) #define D3DCOLOR_B_G(dw) (((dw) >> 8) & 0xFF)
@ -771,9 +767,6 @@ extern int num_lock DECLSPEC_HIDDEN;
(vec)[3] = D3DCOLOR_A(dw); \ (vec)[3] = D3DCOLOR_A(dw); \
} while(0) } while(0)
/* DirectX Device Limits */
/* --------------------- */
#define MAX_MIP_LEVELS 32 /* Maximum number of mipmap levels. */
#define HIGHEST_TRANSFORMSTATE WINED3DTS_WORLDMATRIX(255) /* Highest value in WINED3DTRANSFORMSTATETYPE */ #define HIGHEST_TRANSFORMSTATE WINED3DTS_WORLDMATRIX(255) /* Highest value in WINED3DTRANSFORMSTATETYPE */
/* Checking of API calls */ /* Checking of API calls */
@ -788,7 +781,7 @@ do { \
TRACE("%s call ok %s / %d\n", A, __FILE__, __LINE__); \ TRACE("%s call ok %s / %d\n", A, __FILE__, __LINE__); \
\ \
} else do { \ } else do { \
FIXME(">>>>>>>>>>>>>>>>> %s (%#x) from %s @ %s / %d\n", \ ERR(">>>>>>>>>>>>>>>>> %s (%#x) from %s @ %s / %d\n", \
debug_glerror(err), err, A, __FILE__, __LINE__); \ debug_glerror(err), err, A, __FILE__, __LINE__); \
err = glGetError(); \ err = glGetError(); \
} while (err != GL_NO_ERROR); \ } while (err != GL_NO_ERROR); \
@ -830,13 +823,6 @@ extern const float identity[16] DECLSPEC_HIDDEN;
* Compilable extra diagnostics * Compilable extra diagnostics
*/ */
/* Trace information per-vertex: (extremely high amount of trace) */
#if 0 /* NOTE: Must be 0 in cvs */
# define VTRACE(A) TRACE A
#else
# define VTRACE(A)
#endif
/* TODO: Confirm each of these works when wined3d move completed */ /* TODO: Confirm each of these works when wined3d move completed */
#if 0 /* NOTE: Must be 0 in cvs */ #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 /* To avoid having to get gigabytes of trace, the following can be compiled in, and at the start
@ -910,7 +896,7 @@ enum wined3d_ffp_emit_idx
struct wined3d_stream_info_element struct wined3d_stream_info_element
{ {
const struct GlPixelFormatDesc *format_desc; const struct wined3d_format_desc *format_desc;
GLsizei stride; GLsizei stride;
const BYTE *data; const BYTE *data;
UINT stream_idx; UINT stream_idx;
@ -1039,6 +1025,12 @@ enum wined3d_event_query_result
WINED3D_EVENT_QUERY_ERROR WINED3D_EVENT_QUERY_ERROR
}; };
void wined3d_event_query_destroy(struct wined3d_event_query *query) DECLSPEC_HIDDEN;
enum wined3d_event_query_result wined3d_event_query_test(struct wined3d_event_query *query, IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN;
enum wined3d_event_query_result wined3d_event_query_finish(struct wined3d_event_query *query, IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN;
void wined3d_event_query_issue(struct wined3d_event_query *query, IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN;
HRESULT wined3d_event_query_supported(const struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN;
struct wined3d_context struct wined3d_context
{ {
const struct wined3d_gl_info *gl_info; const struct wined3d_gl_info *gl_info;
@ -1052,8 +1044,8 @@ struct wined3d_context
DWORD numDirtyEntries; DWORD numDirtyEntries;
DWORD isStateDirty[STATE_HIGHEST / (sizeof(DWORD) * CHAR_BIT) + 1]; /* Bitmap to find out quickly if a state is dirty */ DWORD isStateDirty[STATE_HIGHEST / (sizeof(DWORD) * CHAR_BIT) + 1]; /* Bitmap to find out quickly if a state is dirty */
IWineD3DSurface *surface; IWineD3DSwapChainImpl *swapchain;
IWineD3DSurface *current_rt; IWineD3DSurfaceImpl *current_rt;
DWORD tid; /* Thread ID which owns this context at the moment */ DWORD tid; /* Thread ID which owns this context at the moment */
/* Stores some information about the context state for optimization */ /* Stores some information about the context state for optimization */
@ -1089,7 +1081,7 @@ struct wined3d_context
HGLRC glCtx; HGLRC glCtx;
HWND win_handle; HWND win_handle;
HDC hdc; HDC hdc;
HPBUFFERARB pbuffer; int pixel_format;
GLint aux_buffers; GLint aux_buffers;
/* FBOs */ /* FBOs */
@ -1097,10 +1089,11 @@ struct wined3d_context
struct list fbo_list; struct list fbo_list;
struct list fbo_destroy_list; struct list fbo_destroy_list;
struct fbo_entry *current_fbo; struct fbo_entry *current_fbo;
GLuint src_fbo;
GLuint dst_fbo; GLuint dst_fbo;
GLuint fbo_read_binding; GLuint fbo_read_binding;
GLuint fbo_draw_binding; GLuint fbo_draw_binding;
BOOL rebind_fbo;
IWineD3DSurfaceImpl **blit_targets;
/* Queries */ /* Queries */
GLuint *free_occlusion_queries; GLuint *free_occlusion_queries;
@ -1167,60 +1160,69 @@ HRESULT compile_state_table(struct StateEntry *StateTable, APPLYSTATEFUNC **dev_
const struct wined3d_gl_info *gl_info, const struct StateEntryTemplate *vertex, const struct wined3d_gl_info *gl_info, const struct StateEntryTemplate *vertex,
const struct fragment_pipeline *fragment, const struct StateEntryTemplate *misc) DECLSPEC_HIDDEN; const struct fragment_pipeline *fragment, const struct StateEntryTemplate *misc) DECLSPEC_HIDDEN;
enum blit_operation
{
BLIT_OP_BLIT,
BLIT_OP_COLOR_FILL
};
/* Shaders for color conversions in blits */ /* Shaders for color conversions in blits */
struct blit_shader struct blit_shader
{ {
HRESULT (*alloc_private)(IWineD3DDevice *iface); HRESULT (*alloc_private)(IWineD3DDevice *iface);
void (*free_private)(IWineD3DDevice *iface); void (*free_private)(IWineD3DDevice *iface);
HRESULT (*set_shader)(IWineD3DDevice *iface, const struct GlPixelFormatDesc *format_desc, HRESULT (*set_shader)(IWineD3DDevice *iface, IWineD3DSurfaceImpl *surface);
GLenum textype, UINT width, UINT height);
void (*unset_shader)(IWineD3DDevice *iface); void (*unset_shader)(IWineD3DDevice *iface);
BOOL (*color_fixup_supported)(struct color_fixup_desc fixup); 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);
}; };
extern const struct blit_shader ffp_blit DECLSPEC_HIDDEN; extern const struct blit_shader ffp_blit DECLSPEC_HIDDEN;
extern const struct blit_shader arbfp_blit DECLSPEC_HIDDEN; extern const struct blit_shader arbfp_blit DECLSPEC_HIDDEN;
extern const struct blit_shader cpu_blit DECLSPEC_HIDDEN;
typedef enum ContextUsage { /* Temporary blit_shader helper functions */
CTXUSAGE_RESOURCELOAD = 1, /* Only loads textures: No State is applied */ HRESULT arbfp_blit_surface(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *src_surface, const RECT *src_rect,
CTXUSAGE_DRAWPRIM = 2, /* OpenGL states are set up for blitting DirectDraw surfaces */ IWineD3DSurfaceImpl *dst_surface, const RECT *dst_rect_in, enum blit_operation blit_op,
CTXUSAGE_BLIT = 3, /* OpenGL states are set up 3D drawing */ DWORD Filter) DECLSPEC_HIDDEN;
CTXUSAGE_CLEAR = 4, /* Drawable and states are set up for clearing */
} ContextUsage;
struct wined3d_context *context_acquire(IWineD3DDeviceImpl *This, struct wined3d_context *context_acquire(IWineD3DDeviceImpl *This, IWineD3DSurfaceImpl *target) DECLSPEC_HIDDEN;
IWineD3DSurface *target, enum ContextUsage usage) DECLSPEC_HIDDEN;
void context_alloc_event_query(struct wined3d_context *context, void context_alloc_event_query(struct wined3d_context *context,
struct wined3d_event_query *query) DECLSPEC_HIDDEN; struct wined3d_event_query *query) DECLSPEC_HIDDEN;
void context_alloc_occlusion_query(struct wined3d_context *context, void context_alloc_occlusion_query(struct wined3d_context *context,
struct wined3d_occlusion_query *query) DECLSPEC_HIDDEN; struct wined3d_occlusion_query *query) DECLSPEC_HIDDEN;
void context_resource_released(IWineD3DDevice *iface, void context_apply_blit_state(struct wined3d_context *context, IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN;
IWineD3DResource *resource, WINED3DRESOURCETYPE type) DECLSPEC_HIDDEN; void context_apply_clear_state(struct wined3d_context *context, IWineD3DDeviceImpl *device,
void context_bind_fbo(struct wined3d_context *context, GLenum target, GLuint *fbo) DECLSPEC_HIDDEN; IWineD3DSurfaceImpl *render_target, 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;
void context_attach_depth_stencil_fbo(struct wined3d_context *context, void context_attach_depth_stencil_fbo(struct wined3d_context *context,
GLenum fbo_target, IWineD3DSurface *depth_stencil, BOOL use_render_buffer) DECLSPEC_HIDDEN; GLenum fbo_target, IWineD3DSurfaceImpl *depth_stencil, BOOL use_render_buffer) DECLSPEC_HIDDEN;
void context_attach_surface_fbo(const struct wined3d_context *context, void context_bind_fbo(struct wined3d_context *context, GLenum target, GLuint *fbo) DECLSPEC_HIDDEN;
GLenum fbo_target, DWORD idx, IWineD3DSurface *surface) DECLSPEC_HIDDEN; struct wined3d_context *context_create(IWineD3DSwapChainImpl *swapchain, IWineD3DSurfaceImpl *target,
struct wined3d_context *context_create(IWineD3DDeviceImpl *This, IWineD3DSurfaceImpl *target, HWND win, const struct wined3d_format_desc *ds_format_desc) DECLSPEC_HIDDEN;
BOOL create_pbuffer, const WINED3DPRESENT_PARAMETERS *present_parameters) DECLSPEC_HIDDEN;
void context_destroy(IWineD3DDeviceImpl *This, struct wined3d_context *context) 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_event_query(struct wined3d_event_query *query) DECLSPEC_HIDDEN;
void context_free_occlusion_query(struct wined3d_occlusion_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; struct wined3d_context *context_get_current(void) DECLSPEC_HIDDEN;
DWORD context_get_tls_idx(void) DECLSPEC_HIDDEN; DWORD context_get_tls_idx(void) DECLSPEC_HIDDEN;
void context_release(struct wined3d_context *context) DECLSPEC_HIDDEN; void context_release(struct wined3d_context *context) DECLSPEC_HIDDEN;
void context_resource_released(IWineD3DDevice *iface,
IWineD3DResource *resource, WINED3DRESOURCETYPE type) DECLSPEC_HIDDEN;
BOOL context_set_current(struct wined3d_context *ctx) 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; void context_set_draw_buffer(struct wined3d_context *context, GLenum buffer) DECLSPEC_HIDDEN;
void context_set_tls_idx(DWORD idx) DECLSPEC_HIDDEN; void context_set_tls_idx(DWORD idx) DECLSPEC_HIDDEN;
void context_surface_update(struct wined3d_context *context, IWineD3DSurfaceImpl *surface) DECLSPEC_HIDDEN;
void delete_opengl_contexts(IWineD3DDevice *iface, IWineD3DSwapChain *swapchain) DECLSPEC_HIDDEN;
HRESULT create_primary_opengl_context(IWineD3DDevice *iface, IWineD3DSwapChain *swapchain) DECLSPEC_HIDDEN;
/* Macros for doing basic GPU detection based on opengl capabilities */ /* Macros for doing basic GPU detection based on opengl capabilities */
#define WINE_D3D6_CAPABLE(gl_info) (gl_info->supported[ARB_MULTITEXTURE]) #define WINE_D3D6_CAPABLE(gl_info) (gl_info->supported[ARB_MULTITEXTURE])
#define WINE_D3D7_CAPABLE(gl_info) (gl_info->supported[ARB_TEXTURE_COMPRESSION] && gl_info->supported[ARB_TEXTURE_CUBE_MAP] && gl_info->supported[ARB_TEXTURE_ENV_DOT3]) #define WINE_D3D7_CAPABLE(gl_info) (gl_info->supported[ARB_TEXTURE_COMPRESSION] && gl_info->supported[ARB_TEXTURE_CUBE_MAP] && gl_info->supported[ARB_TEXTURE_ENV_DOT3])
#define WINE_D3D8_CAPABLE(gl_info) WINE_D3D7_CAPABLE(gl_info) && (gl_info->supported[ARB_MULTISAMPLE] && gl_info->supported[ARB_TEXTURE_BORDER_CLAMP]) #define WINE_D3D8_CAPABLE(gl_info) WINE_D3D7_CAPABLE(gl_info) && (gl_info->supported[ARB_MULTISAMPLE] && gl_info->supported[ARB_TEXTURE_BORDER_CLAMP])
#define WINE_D3D9_CAPABLE(gl_info) WINE_D3D8_CAPABLE(gl_info) && (gl_info->supported[ARB_FRAGMENT_PROGRAM] && gl_info->supported[ARB_VERTEX_SHADER]) #define WINE_D3D9_CAPABLE(gl_info) WINE_D3D8_CAPABLE(gl_info) && (gl_info->supported[ARB_FRAGMENT_PROGRAM] && gl_info->supported[ARB_VERTEX_SHADER])
#define WINE_D3D10_CAPABLE(gl_info) WINE_D3D9_CAPABLE(gl_info) && (gl_info->supported[EXT_GPU_SHADER4])
/***************************************************************************** /*****************************************************************************
* Internal representation of a light * Internal representation of a light
@ -1251,7 +1253,6 @@ typedef struct WineD3D_PixelFormat
int redSize, greenSize, blueSize, alphaSize, colorSize; int redSize, greenSize, blueSize, alphaSize, colorSize;
int depthSize, stencilSize; int depthSize, stencilSize;
BOOL windowDrawable; BOOL windowDrawable;
BOOL pbufferDrawable;
BOOL doubleBuffer; BOOL doubleBuffer;
int auxBuffers; int auxBuffers;
int numSamples; int numSamples;
@ -1259,9 +1260,9 @@ typedef struct WineD3D_PixelFormat
enum wined3d_gl_vendor enum wined3d_gl_vendor
{ {
GL_VENDOR_WINE, GL_VENDOR_UNKNOWN,
GL_VENDOR_APPLE, GL_VENDOR_APPLE,
GL_VENDOR_ATI, GL_VENDOR_FGLRX,
GL_VENDOR_INTEL, GL_VENDOR_INTEL,
GL_VENDOR_MESA, GL_VENDOR_MESA,
GL_VENDOR_NVIDIA, GL_VENDOR_NVIDIA,
@ -1270,7 +1271,7 @@ enum wined3d_gl_vendor
enum wined3d_pci_vendor enum wined3d_pci_vendor
{ {
HW_VENDOR_WINE = 0x0000, HW_VENDOR_SOFTWARE = 0x0000,
HW_VENDOR_ATI = 0x1002, HW_VENDOR_ATI = 0x1002,
HW_VENDOR_NVIDIA = 0x10de, HW_VENDOR_NVIDIA = 0x10de,
HW_VENDOR_INTEL = 0x8086, HW_VENDOR_INTEL = 0x8086,
@ -1287,7 +1288,7 @@ enum wined3d_pci_device
CARD_ATI_RADEON_XPRESS_200M = 0x5955, CARD_ATI_RADEON_XPRESS_200M = 0x5955,
CARD_ATI_RADEON_X700 = 0x5e4c, CARD_ATI_RADEON_X700 = 0x5e4c,
CARD_ATI_RADEON_X1600 = 0x71c2, CARD_ATI_RADEON_X1600 = 0x71c2,
CARD_ATI_RADEON_HD2300 = 0x7210, CARD_ATI_RADEON_HD2350 = 0x94c7,
CARD_ATI_RADEON_HD2600 = 0x9581, CARD_ATI_RADEON_HD2600 = 0x9581,
CARD_ATI_RADEON_HD2900 = 0x9400, CARD_ATI_RADEON_HD2900 = 0x9400,
CARD_ATI_RADEON_HD3200 = 0x9620, CARD_ATI_RADEON_HD3200 = 0x9620,
@ -1418,6 +1419,7 @@ struct wined3d_gl_limits
struct wined3d_gl_info struct wined3d_gl_info
{ {
DWORD glsl_version;
UINT vidmem; UINT vidmem;
struct wined3d_gl_limits limits; struct wined3d_gl_limits limits;
DWORD reserved_glsl_constants; DWORD reserved_glsl_constants;
@ -1433,7 +1435,7 @@ struct wined3d_gl_info
WGL_EXT_FUNCS_GEN WGL_EXT_FUNCS_GEN
#undef USE_GL_FUNC #undef USE_GL_FUNC
struct GlPixelFormatDesc *gl_formats; struct wined3d_format_desc *gl_formats;
}; };
struct wined3d_driver_info struct wined3d_driver_info
@ -1469,7 +1471,7 @@ struct wined3d_adapter
BOOL initPixelFormats(struct wined3d_gl_info *gl_info, enum wined3d_pci_vendor vendor) DECLSPEC_HIDDEN; BOOL initPixelFormats(struct wined3d_gl_info *gl_info, enum wined3d_pci_vendor vendor) DECLSPEC_HIDDEN;
BOOL initPixelFormatsNoGL(struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN; BOOL initPixelFormatsNoGL(struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN;
extern long WineD3DAdapterChangeGLRam(IWineD3DDeviceImpl *D3DDevice, long glram) DECLSPEC_HIDDEN; extern unsigned int WineD3DAdapterChangeGLRam(IWineD3DDeviceImpl *D3DDevice, unsigned int glram) DECLSPEC_HIDDEN;
extern void add_gl_compat_wrappers(struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN; extern void add_gl_compat_wrappers(struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN;
/***************************************************************************** /*****************************************************************************
@ -1564,14 +1566,9 @@ typedef struct IWineD3DImpl
struct wined3d_adapter adapters[1]; struct wined3d_adapter adapters[1];
} IWineD3DImpl; } IWineD3DImpl;
extern const IWineD3DVtbl IWineD3D_Vtbl DECLSPEC_HIDDEN; HRESULT wined3d_init(IWineD3DImpl *wined3d, UINT version, IUnknown *parent) DECLSPEC_HIDDEN;
BOOL wined3d_register_window(HWND window, struct IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN; BOOL wined3d_register_window(HWND window, struct IWineD3DDeviceImpl *device) DECLSPEC_HIDDEN;
void wined3d_unregister_window(HWND window) DECLSPEC_HIDDEN; void wined3d_unregister_window(HWND window) DECLSPEC_HIDDEN;
BOOL InitAdapters(IWineD3DImpl *This) DECLSPEC_HIDDEN;
/* A helper function that dumps a resource list */
void dumpResources(struct list *list) DECLSPEC_HIDDEN;
/***************************************************************************** /*****************************************************************************
* IWineD3DDevice implementation structure * IWineD3DDevice implementation structure
@ -1656,9 +1653,10 @@ struct IWineD3DDeviceImpl
unsigned int highest_dirty_ps_const, highest_dirty_vs_const; unsigned int highest_dirty_ps_const, highest_dirty_vs_const;
/* Render Target Support */ /* Render Target Support */
IWineD3DSurface **render_targets; IWineD3DSurfaceImpl **render_targets;
IWineD3DSurface *auto_depth_stencil_buffer; IWineD3DSurfaceImpl *auto_depth_stencil;
IWineD3DSurface *stencilBufferTarget; IWineD3DSurfaceImpl *onscreen_depth_stencil;
IWineD3DSurfaceImpl *depth_stencil;
/* palettes texture management */ /* palettes texture management */
UINT NumberOfPalettes; UINT NumberOfPalettes;
@ -1701,12 +1699,12 @@ struct IWineD3DDeviceImpl
/* Stream source management */ /* Stream source management */
struct wined3d_stream_info strided_streams; struct wined3d_stream_info strided_streams;
const WineDirect3DVertexStridedData *up_strided; const WineDirect3DVertexStridedData *up_strided;
struct wined3d_event_query *buffer_queries[MAX_ATTRIBS];
unsigned int num_buffer_queries;
/* Context management */ /* Context management */
struct wined3d_context **contexts; struct wined3d_context **contexts;
UINT numContexts; UINT numContexts;
struct wined3d_context *pbufferContext; /* The context that has a pbuffer as drawable */
DWORD pbufferWidth, pbufferHeight; /* Size of the buffer drawable */
/* High level patch management */ /* High level patch management */
#define PATCHMAP_SIZE 43 #define PATCHMAP_SIZE 43
@ -1715,6 +1713,9 @@ struct IWineD3DDeviceImpl
struct WineD3DRectPatch *currentPatch; struct WineD3DRectPatch *currentPatch;
}; };
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, HRESULT device_init(IWineD3DDeviceImpl *device, IWineD3DImpl *wined3d,
UINT adapter_idx, WINED3DDEVTYPE device_type, HWND focus_window, DWORD flags, UINT adapter_idx, WINED3DDEVTYPE device_type, HWND focus_window, DWORD flags,
IUnknown *parent, IWineD3DDeviceParent *device_parent) DECLSPEC_HIDDEN; IUnknown *parent, IWineD3DDeviceParent *device_parent) DECLSPEC_HIDDEN;
@ -1725,6 +1726,8 @@ void device_resource_add(IWineD3DDeviceImpl *This, IWineD3DResource *resource) D
void device_resource_released(IWineD3DDeviceImpl *This, IWineD3DResource *resource) DECLSPEC_HIDDEN; void device_resource_released(IWineD3DDeviceImpl *This, IWineD3DResource *resource) DECLSPEC_HIDDEN;
void device_stream_info_from_declaration(IWineD3DDeviceImpl *This, void device_stream_info_from_declaration(IWineD3DDeviceImpl *This,
BOOL use_vshader, struct wined3d_stream_info *stream_info, BOOL *fixup) DECLSPEC_HIDDEN; BOOL use_vshader, struct wined3d_stream_info *stream_info, BOOL *fixup) DECLSPEC_HIDDEN;
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; 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, HRESULT IWineD3DDeviceImpl_ClearSurface(IWineD3DDeviceImpl *This, IWineD3DSurfaceImpl *target, DWORD Count,
const WINED3DRECT *pRects, DWORD Flags, WINED3DCOLOR Color, float Z, DWORD Stencil) DECLSPEC_HIDDEN; const WINED3DRECT *pRects, DWORD Flags, WINED3DCOLOR Color, float Z, DWORD Stencil) DECLSPEC_HIDDEN;
@ -1770,7 +1773,7 @@ typedef struct IWineD3DResourceClass
WINED3DPOOL pool; WINED3DPOOL pool;
UINT size; UINT size;
DWORD usage; DWORD usage;
const struct GlPixelFormatDesc *format_desc; const struct wined3d_format_desc *format_desc;
DWORD priority; DWORD priority;
BYTE *allocatedMemory; /* Pointer to the real data location */ BYTE *allocatedMemory; /* Pointer to the real data location */
BYTE *heapMemory; /* Pointer to the HeapAlloced block of memory */ BYTE *heapMemory; /* Pointer to the HeapAlloced block of memory */
@ -1793,7 +1796,7 @@ DWORD resource_get_priority(IWineD3DResource *iface) DECLSPEC_HIDDEN;
HRESULT resource_get_private_data(IWineD3DResource *iface, REFGUID guid, HRESULT resource_get_private_data(IWineD3DResource *iface, REFGUID guid,
void *data, DWORD *data_size) DECLSPEC_HIDDEN; void *data, DWORD *data_size) DECLSPEC_HIDDEN;
HRESULT resource_init(IWineD3DResource *iface, WINED3DRESOURCETYPE resource_type, HRESULT resource_init(IWineD3DResource *iface, WINED3DRESOURCETYPE resource_type,
IWineD3DDeviceImpl *device, UINT size, DWORD usage, const struct GlPixelFormatDesc *format_desc, 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; WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
WINED3DRESOURCETYPE resource_get_type(IWineD3DResource *iface) DECLSPEC_HIDDEN; WINED3DRESOURCETYPE resource_get_type(IWineD3DResource *iface) DECLSPEC_HIDDEN;
DWORD resource_set_priority(IWineD3DResource *iface, DWORD new_priority) DECLSPEC_HIDDEN; DWORD resource_set_priority(IWineD3DResource *iface, DWORD new_priority) DECLSPEC_HIDDEN;
@ -1801,7 +1804,7 @@ HRESULT resource_set_private_data(IWineD3DResource *iface, REFGUID guid,
const void *data, DWORD data_size, DWORD flags) DECLSPEC_HIDDEN; const void *data, DWORD data_size, DWORD flags) DECLSPEC_HIDDEN;
/* Tests show that the start address of resources is 32 byte aligned */ /* Tests show that the start address of resources is 32 byte aligned */
#define RESOURCE_ALIGNMENT 32 #define RESOURCE_ALIGNMENT 16
/***************************************************************************** /*****************************************************************************
* IWineD3DBaseTexture D3D- > openGL state map lookups * IWineD3DBaseTexture D3D- > openGL state map lookups
@ -1818,10 +1821,8 @@ typedef enum winetexturestates {
WINED3DTEXSTA_MAXMIPLEVEL = 7, WINED3DTEXSTA_MAXMIPLEVEL = 7,
WINED3DTEXSTA_MAXANISOTROPY = 8, WINED3DTEXSTA_MAXANISOTROPY = 8,
WINED3DTEXSTA_SRGBTEXTURE = 9, WINED3DTEXSTA_SRGBTEXTURE = 9,
WINED3DTEXSTA_ELEMENTINDEX = 10, WINED3DTEXSTA_SHADOW = 10,
WINED3DTEXSTA_DMAPOFFSET = 11, MAX_WINETEXTURESTATES = 11,
WINED3DTEXSTA_TSSADDRESSW = 12,
MAX_WINETEXTURESTATES = 13,
} winetexturestates; } winetexturestates;
enum WINED3DSRGB enum WINED3DSRGB
@ -1845,7 +1846,9 @@ struct gl_texture
typedef struct IWineD3DBaseTextureClass typedef struct IWineD3DBaseTextureClass
{ {
struct gl_texture texture_rgb, texture_srgb; struct gl_texture texture_rgb, texture_srgb;
UINT levels; IWineD3DResourceImpl **sub_resources;
UINT layer_count;
UINT level_count;
float pow2Matrix[16]; float pow2Matrix[16];
UINT LOD; UINT LOD;
WINED3DTEXTUREFILTERTYPE filterType; WINED3DTEXTUREFILTERTYPE filterType;
@ -1858,10 +1861,11 @@ typedef struct IWineD3DBaseTextureClass
void (*internal_preload)(IWineD3DBaseTexture *iface, enum WINED3DSRGB srgb); void (*internal_preload)(IWineD3DBaseTexture *iface, enum WINED3DSRGB srgb);
} IWineD3DBaseTextureClass; } IWineD3DBaseTextureClass;
void surface_internal_preload(IWineD3DSurface *iface, enum WINED3DSRGB srgb) DECLSPEC_HIDDEN; void surface_internal_preload(IWineD3DSurfaceImpl *surface, enum WINED3DSRGB srgb) DECLSPEC_HIDDEN;
BOOL surface_init_sysmem(IWineD3DSurface *iface) DECLSPEC_HIDDEN; BOOL surface_init_sysmem(IWineD3DSurfaceImpl *surface) DECLSPEC_HIDDEN;
BOOL surface_is_offscreen(IWineD3DSurface *iface) DECLSPEC_HIDDEN; BOOL surface_is_offscreen(IWineD3DSurfaceImpl *iface) DECLSPEC_HIDDEN;
void surface_prepare_texture(IWineD3DSurfaceImpl *surface, BOOL srgb) DECLSPEC_HIDDEN; void surface_prepare_texture(IWineD3DSurfaceImpl *surface,
const struct wined3d_gl_info *gl_info, BOOL srgb) DECLSPEC_HIDDEN;
typedef struct IWineD3DBaseTextureImpl typedef struct IWineD3DBaseTextureImpl
{ {
@ -1883,9 +1887,12 @@ WINED3DTEXTUREFILTERTYPE basetexture_get_autogen_filter_type(IWineD3DBaseTexture
BOOL basetexture_get_dirty(IWineD3DBaseTexture *iface) DECLSPEC_HIDDEN; BOOL basetexture_get_dirty(IWineD3DBaseTexture *iface) DECLSPEC_HIDDEN;
DWORD basetexture_get_level_count(IWineD3DBaseTexture *iface) DECLSPEC_HIDDEN; DWORD basetexture_get_level_count(IWineD3DBaseTexture *iface) DECLSPEC_HIDDEN;
DWORD basetexture_get_lod(IWineD3DBaseTexture *iface) DECLSPEC_HIDDEN; DWORD basetexture_get_lod(IWineD3DBaseTexture *iface) DECLSPEC_HIDDEN;
HRESULT basetexture_init(IWineD3DBaseTextureImpl *texture, UINT levels, WINED3DRESOURCETYPE resource_type, IWineD3DResourceImpl *basetexture_get_sub_resource(IWineD3DBaseTextureImpl *texture,
IWineD3DDeviceImpl *device, UINT size, DWORD usage, const struct GlPixelFormatDesc *format_desc, UINT layer, UINT level) DECLSPEC_HIDDEN;
WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) 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_parent_ops *parent_ops) DECLSPEC_HIDDEN;
HRESULT basetexture_set_autogen_filter_type(IWineD3DBaseTexture *iface, HRESULT basetexture_set_autogen_filter_type(IWineD3DBaseTexture *iface,
WINED3DTEXTUREFILTERTYPE filter_type) DECLSPEC_HIDDEN; WINED3DTEXTUREFILTERTYPE filter_type) DECLSPEC_HIDDEN;
BOOL basetexture_set_dirty(IWineD3DBaseTexture *iface, BOOL dirty) DECLSPEC_HIDDEN; BOOL basetexture_set_dirty(IWineD3DBaseTexture *iface, BOOL dirty) DECLSPEC_HIDDEN;
@ -1903,7 +1910,6 @@ typedef struct IWineD3DTextureImpl
IWineD3DBaseTextureClass baseTexture; IWineD3DBaseTextureClass baseTexture;
/* IWineD3DTexture */ /* IWineD3DTexture */
IWineD3DSurface *surfaces[MAX_MIP_LEVELS];
UINT target; UINT target;
BOOL cond_np2; BOOL cond_np2;
@ -1922,9 +1928,6 @@ typedef struct IWineD3DCubeTextureImpl
const IWineD3DCubeTextureVtbl *lpVtbl; const IWineD3DCubeTextureVtbl *lpVtbl;
IWineD3DResourceClass resource; IWineD3DResourceClass resource;
IWineD3DBaseTextureClass baseTexture; IWineD3DBaseTextureClass baseTexture;
/* IWineD3DCubeTexture */
IWineD3DSurface *surfaces[6][MAX_MIP_LEVELS];
} IWineD3DCubeTextureImpl; } IWineD3DCubeTextureImpl;
HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UINT levels, HRESULT cubetexture_init(IWineD3DCubeTextureImpl *texture, UINT edge_length, UINT levels,
@ -1971,9 +1974,6 @@ typedef struct IWineD3DVolumeTextureImpl
const IWineD3DVolumeTextureVtbl *lpVtbl; const IWineD3DVolumeTextureVtbl *lpVtbl;
IWineD3DResourceClass resource; IWineD3DResourceClass resource;
IWineD3DBaseTextureClass baseTexture; IWineD3DBaseTextureClass baseTexture;
/* IWineD3DVolumeTexture */
IWineD3DVolume *volumes[MAX_MIP_LEVELS];
} IWineD3DVolumeTextureImpl; } IWineD3DVolumeTextureImpl;
HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT height, HRESULT volumetexture_init(IWineD3DVolumeTextureImpl *texture, UINT width, UINT height,
@ -2009,8 +2009,8 @@ typedef struct {
struct fbo_entry struct fbo_entry
{ {
struct list entry; struct list entry;
IWineD3DSurface **render_targets; IWineD3DSurfaceImpl **render_targets;
IWineD3DSurface *depth_stencil; IWineD3DSurfaceImpl *depth_stencil;
BOOL attached; BOOL attached;
GLuint id; GLuint id;
}; };
@ -2052,9 +2052,6 @@ struct IWineD3DSurfaceImpl
/* A method to retrieve the drawable size. Not in the Vtable to make it changeable */ /* A method to retrieve the drawable size. Not in the Vtable to make it changeable */
void (*get_drawable_size)(struct wined3d_context *context, UINT *width, UINT *height); void (*get_drawable_size)(struct wined3d_context *context, UINT *width, UINT *height);
/* Oversized texture */
RECT glRect;
/* PBO */ /* PBO */
GLuint pbo; GLuint pbo;
GLuint texture_name; GLuint texture_name;
@ -2082,6 +2079,7 @@ struct IWineD3DSurfaceImpl
struct list renderbuffers; struct list renderbuffers;
renderbuffer_entry_t *current_renderbuffer; renderbuffer_entry_t *current_renderbuffer;
SIZE ds_current_size;
/* DirectDraw clippers */ /* DirectDraw clippers */
IWineD3DClipper *clipper; IWineD3DClipper *clipper;
@ -2097,13 +2095,14 @@ struct IWineD3DSurfaceImpl
extern const IWineD3DSurfaceVtbl IWineD3DSurface_Vtbl DECLSPEC_HIDDEN; extern const IWineD3DSurfaceVtbl IWineD3DSurface_Vtbl DECLSPEC_HIDDEN;
extern const IWineD3DSurfaceVtbl IWineGDISurface_Vtbl DECLSPEC_HIDDEN; extern const IWineD3DSurfaceVtbl IWineGDISurface_Vtbl DECLSPEC_HIDDEN;
UINT surface_calculate_size(const struct GlPixelFormatDesc *format_desc, UINT surface_calculate_size(const struct wined3d_format_desc *format_desc,
UINT alignment, UINT width, UINT height) DECLSPEC_HIDDEN; UINT alignment, UINT width, UINT height) DECLSPEC_HIDDEN;
void surface_gdi_cleanup(IWineD3DSurfaceImpl *This) DECLSPEC_HIDDEN; void surface_gdi_cleanup(IWineD3DSurfaceImpl *This) DECLSPEC_HIDDEN;
HRESULT surface_init(IWineD3DSurfaceImpl *surface, WINED3DSURFTYPE surface_type, UINT alignment, 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 width, UINT height, UINT level, BOOL lockable, BOOL discard, WINED3DMULTISAMPLE_TYPE multisample_type,
UINT multisample_quality, IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format, UINT multisample_quality, IWineD3DDeviceImpl *device, DWORD usage, WINED3DFORMAT format,
WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN; WINED3DPOOL pool, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
void surface_translate_frontbuffer_coords(IWineD3DSurfaceImpl *surface, HWND window, RECT *rect) DECLSPEC_HIDDEN;
/* Predeclare the shared Surface functions */ /* Predeclare the shared Surface functions */
HRESULT WINAPI IWineD3DBaseSurfaceImpl_QueryInterface(IWineD3DSurface *iface, HRESULT WINAPI IWineD3DBaseSurfaceImpl_QueryInterface(IWineD3DSurface *iface,
@ -2153,13 +2152,13 @@ const void *WINAPI IWineD3DBaseSurfaceImpl_GetData(IWineD3DSurface *iface) DECLS
void get_drawable_size_swapchain(struct wined3d_context *context, UINT *width, UINT *height) DECLSPEC_HIDDEN; void get_drawable_size_swapchain(struct wined3d_context *context, UINT *width, UINT *height) DECLSPEC_HIDDEN;
void get_drawable_size_backbuffer(struct wined3d_context *context, UINT *width, UINT *height) DECLSPEC_HIDDEN; void get_drawable_size_backbuffer(struct wined3d_context *context, UINT *width, UINT *height) DECLSPEC_HIDDEN;
void get_drawable_size_pbuffer(struct wined3d_context *context, UINT *width, UINT *height) DECLSPEC_HIDDEN;
void get_drawable_size_fbo(struct wined3d_context *context, UINT *width, UINT *height) DECLSPEC_HIDDEN; void get_drawable_size_fbo(struct wined3d_context *context, UINT *width, UINT *height) DECLSPEC_HIDDEN;
void draw_textured_quad(IWineD3DSurfaceImpl *src_surface, const RECT *src_rect,
const RECT *dst_rect, WINED3DTEXTUREFILTERTYPE Filter) DECLSPEC_HIDDEN;
void flip_surface(IWineD3DSurfaceImpl *front, IWineD3DSurfaceImpl *back) DECLSPEC_HIDDEN; void flip_surface(IWineD3DSurfaceImpl *front, IWineD3DSurfaceImpl *back) DECLSPEC_HIDDEN;
/* Surface flags: */ /* Surface flags: */
#define SFLAG_OVERSIZE 0x00000001 /* Surface is bigger than gl size, blts only */
#define SFLAG_CONVERTED 0x00000002 /* Converted for color keying or Palettized */ #define SFLAG_CONVERTED 0x00000002 /* Converted for color keying or Palettized */
#define SFLAG_DIBSECTION 0x00000004 /* Has a DIB section attached for GetDC */ #define SFLAG_DIBSECTION 0x00000004 /* Has a DIB section attached for GetDC */
#define SFLAG_LOCKABLE 0x00000008 /* Surface can be locked */ #define SFLAG_LOCKABLE 0x00000008 /* Surface can be locked */
@ -2186,7 +2185,6 @@ void flip_surface(IWineD3DSurfaceImpl *front, IWineD3DSurfaceImpl *back) DECLSPE
#define SFLAG_SWAPCHAIN 0x01000000 /* The surface is part of a swapchain */ #define SFLAG_SWAPCHAIN 0x01000000 /* The surface is part of a swapchain */
/* In some conditions the surface memory must not be freed: /* In some conditions the surface memory must not be freed:
* SFLAG_OVERSIZE: Not all data can be kept in GL
* SFLAG_CONVERTED: Converting the data back would take too long * SFLAG_CONVERTED: Converting the data back would take too long
* SFLAG_DIBSECTION: The dib code manages the memory * SFLAG_DIBSECTION: The dib code manages the memory
* SFLAG_LOCKED: The app requires access to the surface data * SFLAG_LOCKED: The app requires access to the surface data
@ -2194,8 +2192,7 @@ void flip_surface(IWineD3DSurfaceImpl *front, IWineD3DSurfaceImpl *back) DECLSPE
* SFLAG_PBO: PBOs don't use 'normal' memory. It is either allocated by the driver or must be NULL. * SFLAG_PBO: PBOs don't use 'normal' memory. It is either allocated by the driver or must be NULL.
* SFLAG_CLIENT: OpenGL uses our memory as backup * SFLAG_CLIENT: OpenGL uses our memory as backup
*/ */
#define SFLAG_DONOTFREE (SFLAG_OVERSIZE | \ #define SFLAG_DONOTFREE (SFLAG_CONVERTED | \
SFLAG_CONVERTED | \
SFLAG_DIBSECTION | \ SFLAG_DIBSECTION | \
SFLAG_LOCKED | \ SFLAG_LOCKED | \
SFLAG_DYNLOCK | \ SFLAG_DYNLOCK | \
@ -2212,38 +2209,19 @@ void flip_surface(IWineD3DSurfaceImpl *front, IWineD3DSurfaceImpl *back) DECLSPE
SFLAG_DS_OFFSCREEN) SFLAG_DS_OFFSCREEN)
#define SFLAG_DS_DISCARDED SFLAG_DS_LOCATIONS #define SFLAG_DS_DISCARDED SFLAG_DS_LOCATIONS
BOOL CalculateTexRect(IWineD3DSurfaceImpl *This, RECT *Rect, float glTexCoord[4]) DECLSPEC_HIDDEN;
typedef enum { typedef enum {
NO_CONVERSION, NO_CONVERSION,
CONVERT_PALETTED, CONVERT_PALETTED,
CONVERT_PALETTED_CK, CONVERT_PALETTED_CK,
CONVERT_CK_565, CONVERT_CK_565,
CONVERT_CK_5551, CONVERT_CK_5551,
CONVERT_CK_4444,
CONVERT_CK_4444_ARGB,
CONVERT_CK_1555,
CONVERT_555,
CONVERT_CK_RGB24, CONVERT_CK_RGB24,
CONVERT_CK_8888, CONVERT_RGB32_888
CONVERT_CK_8888_ARGB,
CONVERT_RGB32_888,
CONVERT_V8U8,
CONVERT_L6V5U5,
CONVERT_X8L8V8U8,
CONVERT_Q8W8V8U8,
CONVERT_V16U16,
CONVERT_A4L4,
CONVERT_G16R16,
CONVERT_R16G16F,
CONVERT_R32G32F,
CONVERT_D15S1,
CONVERT_D24X4S4,
CONVERT_D24FS8,
} CONVERT_TYPES; } CONVERT_TYPES;
HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *This, BOOL need_alpha_ck, BOOL use_texturing, GLenum *format, HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *This, BOOL need_alpha_ck, BOOL use_texturing,
GLenum *internal, GLenum *type, CONVERT_TYPES *convert, int *target_bpp, BOOL srgb_mode) DECLSPEC_HIDDEN; 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;
BOOL palette9_changed(IWineD3DSurfaceImpl *This) DECLSPEC_HIDDEN; BOOL palette9_changed(IWineD3DSurfaceImpl *This) DECLSPEC_HIDDEN;
@ -2253,7 +2231,7 @@ BOOL palette9_changed(IWineD3DSurfaceImpl *This) DECLSPEC_HIDDEN;
struct wined3d_vertex_declaration_element struct wined3d_vertex_declaration_element
{ {
const struct GlPixelFormatDesc *format_desc; const struct wined3d_format_desc *format_desc;
BOOL ffp_valid; BOOL ffp_valid;
WORD input_slot; WORD input_slot;
WORD offset; WORD offset;
@ -2432,6 +2410,14 @@ HRESULT stateblock_init(IWineD3DStateBlockImpl *stateblock,
IWineD3DDeviceImpl *device, WINED3DSTATEBLOCKTYPE type) DECLSPEC_HIDDEN; IWineD3DDeviceImpl *device, WINED3DSTATEBLOCKTYPE type) DECLSPEC_HIDDEN;
void stateblock_init_contained_states(IWineD3DStateBlockImpl *object) DECLSPEC_HIDDEN; void stateblock_init_contained_states(IWineD3DStateBlockImpl *object) DECLSPEC_HIDDEN;
static inline void stateblock_apply_state(DWORD state, IWineD3DStateBlockImpl *stateblock,
struct wined3d_context *context)
{
const struct StateEntry *statetable = stateblock->device->StateTable;
DWORD rep = statetable[state].representative;
statetable[rep].apply(rep, stateblock, context);
}
/* Direct3D terminology with little modifications. We do not have an issued state /* Direct3D terminology with little modifications. We do not have an issued state
* because only the driver knows about it, but we have a created state because d3d * because only the driver knows about it, but we have a created state because d3d
* allows GetData on a created issue, but opengl doesn't * allows GetData on a created issue, but opengl doesn't
@ -2485,6 +2471,9 @@ struct wined3d_map_range
#define WINED3D_BUFFER_CREATEBO 0x04 /* Attempt to create a buffer object next PreLoad */ #define WINED3D_BUFFER_CREATEBO 0x04 /* Attempt to create a buffer object next PreLoad */
#define WINED3D_BUFFER_DOUBLEBUFFER 0x08 /* Use a vbo and local allocated memory */ #define WINED3D_BUFFER_DOUBLEBUFFER 0x08 /* Use a vbo and local allocated memory */
#define WINED3D_BUFFER_FLUSH 0x10 /* Manual unmap flushing */ #define WINED3D_BUFFER_FLUSH 0x10 /* Manual unmap flushing */
#define WINED3D_BUFFER_DISCARD 0x20 /* A DISCARD lock has occurred since the last PreLoad */
#define WINED3D_BUFFER_NOSYNC 0x40 /* All locks since the last PreLoad had NOOVERWRITE set */
#define WINED3D_BUFFER_APPLESYNC 0x80 /* Using sync as in GL_APPLE_flush_buffer_range */
struct wined3d_buffer struct wined3d_buffer
{ {
@ -2503,6 +2492,7 @@ struct wined3d_buffer
LONG lock_count; LONG lock_count;
struct wined3d_map_range *maps; struct wined3d_map_range *maps;
ULONG maps_size, modified_areas; ULONG maps_size, modified_areas;
struct wined3d_event_query *query;
/* conversion stuff */ /* conversion stuff */
UINT decl_change_count, full_conversion_count; UINT decl_change_count, full_conversion_count;
@ -2514,8 +2504,9 @@ struct wined3d_buffer
UINT *conversion_shift; /* NULL if no shifted conversion */ UINT *conversion_shift; /* NULL if no shifted conversion */
}; };
const BYTE *buffer_get_memory(IWineD3DBuffer *iface, UINT offset, GLuint *buffer_object) DECLSPEC_HIDDEN; const BYTE *buffer_get_memory(IWineD3DBuffer *iface, const struct wined3d_gl_info *gl_info,
BYTE *buffer_get_sysmem(struct wined3d_buffer *This) DECLSPEC_HIDDEN; 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, HRESULT buffer_init(struct wined3d_buffer *buffer, IWineD3DDeviceImpl *device,
UINT size, DWORD usage, WINED3DFORMAT format, WINED3DPOOL pool, GLenum bind_hint, 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; const char *data, IUnknown *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN;
@ -2530,7 +2521,8 @@ struct wined3d_rendertarget_view
IUnknown *parent; IUnknown *parent;
}; };
extern const IWineD3DRendertargetViewVtbl wined3d_rendertarget_view_vtbl DECLSPEC_HIDDEN; void wined3d_rendertarget_view_init(struct wined3d_rendertarget_view *view,
IWineD3DResource *resource, IUnknown *parent) DECLSPEC_HIDDEN;
/***************************************************************************** /*****************************************************************************
* IWineD3DSwapChainImpl implementation structure (extends IUnknown) * IWineD3DSwapChainImpl implementation structure (extends IUnknown)
@ -2546,21 +2538,23 @@ struct IWineD3DSwapChainImpl
IWineD3DDeviceImpl *device; IWineD3DDeviceImpl *device;
/* IWineD3DSwapChain fields */ /* IWineD3DSwapChain fields */
IWineD3DSurface **backBuffer; IWineD3DSurfaceImpl **back_buffers;
IWineD3DSurface *frontBuffer; IWineD3DSurfaceImpl *front_buffer;
WINED3DPRESENT_PARAMETERS presentParms; WINED3DPRESENT_PARAMETERS presentParms;
DWORD orig_width, orig_height; DWORD orig_width, orig_height;
WINED3DFORMAT orig_fmt; WINED3DFORMAT orig_fmt;
WINED3DGAMMARAMP orig_gamma; WINED3DGAMMARAMP orig_gamma;
BOOL render_to_fbo; BOOL render_to_fbo;
const struct wined3d_format_desc *ds_format;
long prev_time, frames; /* Performance tracking */ LONG prev_time, frames; /* Performance tracking */
unsigned int vSyncCounter; unsigned int vSyncCounter;
struct wined3d_context **context; struct wined3d_context **context;
unsigned int num_contexts; unsigned int num_contexts;
HWND win_handle; HWND win_handle;
HWND device_window;
}; };
const IWineD3DSwapChainVtbl IWineGDISwapChain_Vtbl DECLSPEC_HIDDEN; const IWineD3DSwapChainVtbl IWineGDISwapChain_Vtbl DECLSPEC_HIDDEN;
@ -2580,7 +2574,7 @@ HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetRasterStatus(IWineD3DSwapChain *ifac
HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetDisplayMode(IWineD3DSwapChain *iface, HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetDisplayMode(IWineD3DSwapChain *iface,
WINED3DDISPLAYMODE *pMode) DECLSPEC_HIDDEN; WINED3DDISPLAYMODE *pMode) DECLSPEC_HIDDEN;
HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetDevice(IWineD3DSwapChain *iface, HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetDevice(IWineD3DSwapChain *iface,
IWineD3DDevice **ppDevice) DECLSPEC_HIDDEN; IWineD3DDevice **device) DECLSPEC_HIDDEN;
HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetPresentParameters(IWineD3DSwapChain *iface, HRESULT WINAPI IWineD3DBaseSwapChainImpl_GetPresentParameters(IWineD3DSwapChain *iface,
WINED3DPRESENT_PARAMETERS *pPresentationParameters) DECLSPEC_HIDDEN; WINED3DPRESENT_PARAMETERS *pPresentationParameters) DECLSPEC_HIDDEN;
HRESULT WINAPI IWineD3DBaseSwapChainImpl_SetGammaRamp(IWineD3DSwapChain *iface, HRESULT WINAPI IWineD3DBaseSwapChainImpl_SetGammaRamp(IWineD3DSwapChain *iface,
@ -2624,6 +2618,9 @@ const char *debug_d3dtop(WINED3DTEXTUREOP d3dtop) DECLSPEC_HIDDEN;
void dump_color_fixup_desc(struct color_fixup_desc fixup) DECLSPEC_HIDDEN; void dump_color_fixup_desc(struct color_fixup_desc fixup) DECLSPEC_HIDDEN;
const char *debug_surflocation(DWORD flag) 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 */ /* Routines for GL <-> D3D values */
GLenum StencilOp(DWORD op) DECLSPEC_HIDDEN; GLenum StencilOp(DWORD op) DECLSPEC_HIDDEN;
GLenum CompareFunc(DWORD func) DECLSPEC_HIDDEN; GLenum CompareFunc(DWORD func) DECLSPEC_HIDDEN;
@ -2650,18 +2647,19 @@ void state_fogstartend(DWORD state, IWineD3DStateBlockImpl *stateblock,
void state_fog_fragpart(DWORD state, IWineD3DStateBlockImpl *stateblock, void state_fog_fragpart(DWORD state, IWineD3DStateBlockImpl *stateblock,
struct wined3d_context *context) DECLSPEC_HIDDEN; struct wined3d_context *context) DECLSPEC_HIDDEN;
void surface_add_dirty_rect(IWineD3DSurface *iface, const RECT *dirty_rect) DECLSPEC_HIDDEN; void surface_add_dirty_rect(IWineD3DSurfaceImpl *surface, const RECT *dirty_rect) DECLSPEC_HIDDEN;
GLenum surface_get_gl_buffer(IWineD3DSurface *iface) DECLSPEC_HIDDEN; GLenum surface_get_gl_buffer(IWineD3DSurfaceImpl *surface) DECLSPEC_HIDDEN;
void surface_load_ds_location(IWineD3DSurface *iface, struct wined3d_context *context, DWORD location) DECLSPEC_HIDDEN; void surface_load_ds_location(IWineD3DSurfaceImpl *surface,
void surface_modify_ds_location(IWineD3DSurface *iface, DWORD location) DECLSPEC_HIDDEN; struct wined3d_context *context, DWORD location) DECLSPEC_HIDDEN;
void surface_set_compatible_renderbuffer(IWineD3DSurface *iface, 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; unsigned int width, unsigned int height) DECLSPEC_HIDDEN;
void surface_set_texture_name(IWineD3DSurface *iface, GLuint name, BOOL srgb_name) DECLSPEC_HIDDEN; void surface_set_texture_name(IWineD3DSurfaceImpl *surface, GLuint name, BOOL srgb_name) DECLSPEC_HIDDEN;
void surface_set_texture_target(IWineD3DSurface *iface, GLenum target) DECLSPEC_HIDDEN; void surface_set_texture_target(IWineD3DSurfaceImpl *surface, GLenum target) DECLSPEC_HIDDEN;
BOOL getColorBits(const struct GlPixelFormatDesc *format_desc, BOOL getColorBits(const struct wined3d_format_desc *format_desc,
short *redSize, short *greenSize, short *blueSize, short *alphaSize, short *totalSize) DECLSPEC_HIDDEN; short *redSize, short *greenSize, short *blueSize, short *alphaSize, short *totalSize) DECLSPEC_HIDDEN;
BOOL getDepthStencilBits(const struct GlPixelFormatDesc *format_desc, BOOL getDepthStencilBits(const struct wined3d_format_desc *format_desc,
short *depthSize, short *stencilSize) DECLSPEC_HIDDEN; short *depthSize, short *stencilSize) DECLSPEC_HIDDEN;
/* Math utils */ /* Math utils */
@ -2941,8 +2939,8 @@ struct IWineD3DPaletteImpl {
DWORD Flags; DWORD Flags;
}; };
extern const IWineD3DPaletteVtbl IWineD3DPalette_Vtbl DECLSPEC_HIDDEN; HRESULT wined3d_palette_init(IWineD3DPaletteImpl *palette, IWineD3DDeviceImpl *device,
DWORD IWineD3DPaletteImpl_Size(DWORD dwFlags) DECLSPEC_HIDDEN; DWORD flags, const PALETTEENTRY *entries, IUnknown *parent) DECLSPEC_HIDDEN;
/* DirectDraw utility functions */ /* DirectDraw utility functions */
extern WINED3DFORMAT pixelformat_for_depth(DWORD depth) DECLSPEC_HIDDEN; extern WINED3DFORMAT pixelformat_for_depth(DWORD depth) DECLSPEC_HIDDEN;
@ -2952,17 +2950,23 @@ extern WINED3DFORMAT pixelformat_for_depth(DWORD depth) DECLSPEC_HIDDEN;
*/ */
/* WineD3D pixel format flags */ /* WineD3D pixel format flags */
#define WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING 0x1 #define WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING 0x00000001
#define WINED3DFMT_FLAG_FILTERING 0x2 #define WINED3DFMT_FLAG_FILTERING 0x00000002
#define WINED3DFMT_FLAG_DEPTH 0x4 #define WINED3DFMT_FLAG_DEPTH 0x00000004
#define WINED3DFMT_FLAG_STENCIL 0x8 #define WINED3DFMT_FLAG_STENCIL 0x00000008
#define WINED3DFMT_FLAG_RENDERTARGET 0x10 #define WINED3DFMT_FLAG_RENDERTARGET 0x00000010
#define WINED3DFMT_FLAG_FOURCC 0x20 #define WINED3DFMT_FLAG_FOURCC 0x00000020
#define WINED3DFMT_FLAG_FBO_ATTACHABLE 0x40 #define WINED3DFMT_FLAG_FBO_ATTACHABLE 0x00000040
#define WINED3DFMT_FLAG_COMPRESSED 0x80 #define WINED3DFMT_FLAG_COMPRESSED 0x00000080
#define WINED3DFMT_FLAG_GETDC 0x100 #define WINED3DFMT_FLAG_GETDC 0x00000100
#define WINED3DFMT_FLAG_FLOAT 0x00000200
#define WINED3DFMT_FLAG_BUMPMAP 0x00000400
#define WINED3DFMT_FLAG_SRGB_READ 0x00000800
#define WINED3DFMT_FLAG_SRGB_WRITE 0x00001000
#define WINED3DFMT_FLAG_VTF 0x00002000
#define WINED3DFMT_FLAG_SHADOW 0x00004000
struct GlPixelFormatDesc struct wined3d_format_desc
{ {
WINED3DFORMAT format; WINED3DFORMAT format;
DWORD red_mask; DWORD red_mask;
@ -2989,12 +2993,14 @@ struct GlPixelFormatDesc
GLint rtInternal; GLint rtInternal;
GLint glFormat; GLint glFormat;
GLint glType; GLint glType;
UINT conv_byte_count;
unsigned int Flags; unsigned int Flags;
float heightscale; float heightscale;
struct color_fixup_desc color_fixup; struct color_fixup_desc color_fixup;
void (*convert)(const BYTE *src, BYTE *dst, UINT pitch, UINT width, UINT height);
}; };
const struct GlPixelFormatDesc *getFormatDescEntry(WINED3DFORMAT fmt, const struct wined3d_format_desc *getFormatDescEntry(WINED3DFORMAT fmt,
const struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN; const struct wined3d_gl_info *gl_info) DECLSPEC_HIDDEN;
static inline BOOL use_vs(IWineD3DStateBlockImpl *stateblock) static inline BOOL use_vs(IWineD3DStateBlockImpl *stateblock)
@ -3013,9 +3019,9 @@ static inline BOOL use_ps(IWineD3DStateBlockImpl *stateblock)
return (stateblock->pixelShader && stateblock->device->ps_selected_mode != SHADER_NONE); return (stateblock->pixelShader && stateblock->device->ps_selected_mode != SHADER_NONE);
} }
void stretch_rect_fbo(IWineD3DDevice *iface, IWineD3DSurface *src_surface, void stretch_rect_fbo(IWineD3DDeviceImpl *device, IWineD3DSurfaceImpl *src_surface,
WINED3DRECT *src_rect, IWineD3DSurface *dst_surface, WINED3DRECT *dst_rect, const RECT *src_rect, IWineD3DSurfaceImpl *dst_surface, const RECT *dst_rect,
const WINED3DTEXTUREFILTERTYPE filter, BOOL flip) DECLSPEC_HIDDEN; const WINED3DTEXTUREFILTERTYPE filter) DECLSPEC_HIDDEN;
/* The WNDCLASS-Name for the fake window which we use to retrieve the GL capabilities */ /* The WNDCLASS-Name for the fake window which we use to retrieve the GL capabilities */
#define WINED3D_OPENGL_WINDOW_CLASS_NAME "WineD3D_OpenGL" #define WINED3D_OPENGL_WINDOW_CLASS_NAME "WineD3D_OpenGL"
@ -3024,4 +3030,6 @@ void stretch_rect_fbo(IWineD3DDevice *iface, IWineD3DSurface *src_surface,
((DWORD)(BYTE)(ch0) | ((DWORD)(BYTE)(ch1) << 8) | \ ((DWORD)(BYTE)(ch0) | ((DWORD)(BYTE)(ch1) << 8) | \
((DWORD)(BYTE)(ch2) << 16) | ((DWORD)(BYTE)(ch3) << 24 )) ((DWORD)(BYTE)(ch2) << 16) | ((DWORD)(BYTE)(ch3) << 24 ))
#define MAKEDWORD_VERSION(maj, min) (((maj & 0xffff) << 16) | (min & 0xffff))
#endif #endif

View file

@ -275,9 +275,7 @@ typedef enum _WINED3DFORMAT
typedef enum _WINED3DRENDERSTATETYPE typedef enum _WINED3DRENDERSTATETYPE
{ {
WINED3DRS_TEXTUREHANDLE = 1, /* d3d7 */
WINED3DRS_ANTIALIAS = 2, /* d3d7 */ WINED3DRS_ANTIALIAS = 2, /* d3d7 */
WINED3DRS_TEXTUREADDRESS = 3, /* d3d7 */
WINED3DRS_TEXTUREPERSPECTIVE = 4, /* d3d7 */ WINED3DRS_TEXTUREPERSPECTIVE = 4, /* d3d7 */
WINED3DRS_WRAPU = 5, /* d3d7 */ WINED3DRS_WRAPU = 5, /* d3d7 */
WINED3DRS_WRAPV = 6, /* d3d7 */ WINED3DRS_WRAPV = 6, /* d3d7 */
@ -291,11 +289,8 @@ typedef enum _WINED3DRENDERSTATETYPE
WINED3DRS_ZWRITEENABLE = 14, WINED3DRS_ZWRITEENABLE = 14,
WINED3DRS_ALPHATESTENABLE = 15, WINED3DRS_ALPHATESTENABLE = 15,
WINED3DRS_LASTPIXEL = 16, WINED3DRS_LASTPIXEL = 16,
WINED3DRS_TEXTUREMAG = 17, /* d3d7 */
WINED3DRS_TEXTUREMIN = 18, /* d3d7 */
WINED3DRS_SRCBLEND = 19, WINED3DRS_SRCBLEND = 19,
WINED3DRS_DESTBLEND = 20, WINED3DRS_DESTBLEND = 20,
WINED3DRS_TEXTUREMAPBLEND = 21, /* d3d7 */
WINED3DRS_CULLMODE = 22, WINED3DRS_CULLMODE = 22,
WINED3DRS_ZFUNC = 23, WINED3DRS_ZFUNC = 23,
WINED3DRS_ALPHAREF = 24, WINED3DRS_ALPHAREF = 24,
@ -316,9 +311,6 @@ typedef enum _WINED3DRENDERSTATETYPE
WINED3DRS_STIPPLEENABLE = 39, /* d3d7 */ WINED3DRS_STIPPLEENABLE = 39, /* d3d7 */
WINED3DRS_EDGEANTIALIAS = 40, /* d3d7, d3d8 */ WINED3DRS_EDGEANTIALIAS = 40, /* d3d7, d3d8 */
WINED3DRS_COLORKEYENABLE = 41, /* d3d7 */ WINED3DRS_COLORKEYENABLE = 41, /* d3d7 */
WINED3DRS_BORDERCOLOR = 43, /* d3d7 */
WINED3DRS_TEXTUREADDRESSU = 44, /* d3d7 */
WINED3DRS_TEXTUREADDRESSV = 45, /* d3d7 */
WINED3DRS_MIPMAPLODBIAS = 46, /* d3d7 */ WINED3DRS_MIPMAPLODBIAS = 46, /* d3d7 */
WINED3DRS_ZBIAS = 47, /* d3d7, d3d8 */ WINED3DRS_ZBIAS = 47, /* d3d7, d3d8 */
WINED3DRS_RANGEFOGENABLE = 48, WINED3DRS_RANGEFOGENABLE = 48,
@ -334,38 +326,6 @@ typedef enum _WINED3DRENDERSTATETYPE
WINED3DRS_STENCILMASK = 58, WINED3DRS_STENCILMASK = 58,
WINED3DRS_STENCILWRITEMASK = 59, WINED3DRS_STENCILWRITEMASK = 59,
WINED3DRS_TEXTUREFACTOR = 60, WINED3DRS_TEXTUREFACTOR = 60,
WINED3DRS_STIPPLEPATTERN00 = 64,
WINED3DRS_STIPPLEPATTERN01 = 65,
WINED3DRS_STIPPLEPATTERN02 = 66,
WINED3DRS_STIPPLEPATTERN03 = 67,
WINED3DRS_STIPPLEPATTERN04 = 68,
WINED3DRS_STIPPLEPATTERN05 = 69,
WINED3DRS_STIPPLEPATTERN06 = 70,
WINED3DRS_STIPPLEPATTERN07 = 71,
WINED3DRS_STIPPLEPATTERN08 = 72,
WINED3DRS_STIPPLEPATTERN09 = 73,
WINED3DRS_STIPPLEPATTERN10 = 74,
WINED3DRS_STIPPLEPATTERN11 = 75,
WINED3DRS_STIPPLEPATTERN12 = 76,
WINED3DRS_STIPPLEPATTERN13 = 77,
WINED3DRS_STIPPLEPATTERN14 = 78,
WINED3DRS_STIPPLEPATTERN15 = 79,
WINED3DRS_STIPPLEPATTERN16 = 80,
WINED3DRS_STIPPLEPATTERN17 = 81,
WINED3DRS_STIPPLEPATTERN18 = 82,
WINED3DRS_STIPPLEPATTERN19 = 83,
WINED3DRS_STIPPLEPATTERN20 = 84,
WINED3DRS_STIPPLEPATTERN21 = 85,
WINED3DRS_STIPPLEPATTERN22 = 86,
WINED3DRS_STIPPLEPATTERN23 = 87,
WINED3DRS_STIPPLEPATTERN24 = 88,
WINED3DRS_STIPPLEPATTERN25 = 89,
WINED3DRS_STIPPLEPATTERN26 = 90,
WINED3DRS_STIPPLEPATTERN27 = 91,
WINED3DRS_STIPPLEPATTERN28 = 92,
WINED3DRS_STIPPLEPATTERN29 = 93,
WINED3DRS_STIPPLEPATTERN30 = 94,
WINED3DRS_STIPPLEPATTERN31 = 95,
WINED3DRS_WRAP0 = 128, WINED3DRS_WRAP0 = 128,
WINED3DRS_WRAP1 = 129, WINED3DRS_WRAP1 = 129,
WINED3DRS_WRAP2 = 130, WINED3DRS_WRAP2 = 130,
@ -407,8 +367,6 @@ typedef enum _WINED3DRENDERSTATETYPE
WINED3DRS_COLORWRITEENABLE = 168, WINED3DRS_COLORWRITEENABLE = 168,
WINED3DRS_TWEENFACTOR = 170, WINED3DRS_TWEENFACTOR = 170,
WINED3DRS_BLENDOP = 171, WINED3DRS_BLENDOP = 171,
WINED3DRS_POSITIONORDER = 172,
WINED3DRS_NORMALORDER = 173,
WINED3DRS_POSITIONDEGREE = 172, WINED3DRS_POSITIONDEGREE = 172,
WINED3DRS_NORMALDEGREE = 173, WINED3DRS_NORMALDEGREE = 173,
WINED3DRS_SCISSORTESTENABLE = 174, WINED3DRS_SCISSORTESTENABLE = 174,
@ -3452,6 +3410,15 @@ interface IWineD3DDevice : IWineD3DBase
[in] D3DCB_ENUMRESOURCES callback, [in] D3DCB_ENUMRESOURCES callback,
[in] void *data [in] void *data
); );
HRESULT GetSurfaceFromDC(
[in] HDC dc,
[out] IWineD3DSurface **surface
);
HRESULT AcquireFocusWindow(
[in] HWND window
);
void ReleaseFocusWindow(
);
} }
IWineD3D *WineDirect3DCreate(UINT dxVersion, IUnknown *parent); IWineD3D *WineDirect3DCreate(UINT dxVersion, IUnknown *parent);