/* Direct3D Device
 * Copyright (c) 1998 Lionel ULMER
 *
 * This file contains the MESA implementation of all the D3D devices that
 * Wine supports.
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */

#include "config.h"
#include "wine/port.h"

#include <string.h>
#include <math.h>

#define NONAMELESSUNION
#define NONAMELESSSTRUCT
#include "windef.h"
#include "winerror.h"
#include "objbase.h"
#include "ddraw.h"
#include "d3d.h"
#include "wine/debug.h"
#include "wine/library.h"

#include "mesa_private.h"
#include "main.h"

WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
WINE_DECLARE_DEBUG_CHANNEL(ddraw_geom);
WINE_DECLARE_DEBUG_CHANNEL(ddraw_fps);

/* x11drv GDI escapes */
#define X11DRV_ESCAPE 6789
enum x11drv_escape_codes
{
    X11DRV_GET_DISPLAY,   /* get X11 display for a DC */
    X11DRV_GET_DRAWABLE,  /* get current drawable for a DC */
    X11DRV_GET_FONT,      /* get current X font for a DC */
};

/* They are non-static as they are used by Direct3D in the creation function */
const GUID IID_D3DDEVICE_OpenGL = {
  0x31416d44,
  0x86ae,
  0x11d2,
  { 0x82,0x2d,0xa8,0xd5,0x31,0x87,0xca,0xfa }
};

const float id_mat[16] = {
    1.0, 0.0, 0.0, 0.0,
    0.0, 1.0, 0.0, 0.0,
    0.0, 0.0, 1.0, 0.0,
    0.0, 0.0, 0.0, 1.0
};

/* This is filled at DLL loading time */
static D3DDEVICEDESC7 opengl_device_caps;
GL_EXTENSIONS_LIST GL_extensions;

static void draw_primitive_strided(IDirect3DDeviceImpl *This,
				   D3DPRIMITIVETYPE d3dptPrimitiveType,
				   DWORD d3dvtVertexType,
				   LPD3DDRAWPRIMITIVESTRIDEDDATA lpD3DDrawPrimStrideData,
				   DWORD dwVertexCount,
				   LPWORD dwIndices,
				   DWORD dwIndexCount,
				   DWORD dwFlags) ;

static DWORD draw_primitive_handle_textures(IDirect3DDeviceImpl *This);

/* retrieve the X display to use on a given DC */
inline static Display *get_display( HDC hdc )
{
    Display *display;
    enum x11drv_escape_codes escape = X11DRV_GET_DISPLAY;

    if (!ExtEscape( hdc, X11DRV_ESCAPE, sizeof(escape), (LPCSTR)&escape,
                    sizeof(display), (LPSTR)&display )) display = NULL;

    return display;
}

#define UNLOCK_TEX_SIZE 256

#define DEPTH_RANGE_BIT (0x00000001 << 0)
#define VIEWPORT_BIT    (0x00000001 << 1)

static DWORD d3ddevice_set_state_for_flush(IDirect3DDeviceImpl *d3d_dev, LPCRECT pRect, BOOLEAN use_alpha, BOOLEAN *initial) {
    IDirect3DDeviceGLImpl* gl_d3d_dev = (IDirect3DDeviceGLImpl*) d3d_dev;
    DWORD opt_bitmap = 0x00000000;
    
    if (gl_d3d_dev->unlock_tex == 0) {
        glGenTextures(1, &gl_d3d_dev->unlock_tex);
	glBindTexture(GL_TEXTURE_2D, gl_d3d_dev->unlock_tex);
	*initial = TRUE;
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
    } else {
        glBindTexture(GL_TEXTURE_2D, gl_d3d_dev->unlock_tex);
	*initial = FALSE;
    }
    if (d3d_dev->tex_mat_is_identity[0] == FALSE) {
	glMatrixMode(GL_TEXTURE);
	glLoadIdentity();
    }
    
    if (gl_d3d_dev->transform_state != GL_TRANSFORM_ORTHO) {
	gl_d3d_dev->transform_state = GL_TRANSFORM_ORTHO;
	d3ddevice_set_ortho(d3d_dev);
    }
    
    if (gl_d3d_dev->depth_test != FALSE) glDisable(GL_DEPTH_TEST);
    if ((gl_d3d_dev->current_bound_texture[0] == NULL) ||
	(d3d_dev->state_block.texture_stage_state[0][D3DTSS_COLOROP - 1] == D3DTOP_DISABLE))
	glEnable(GL_TEXTURE_2D);
    glEnable(GL_SCISSOR_TEST);
    if ((d3d_dev->active_viewport.dvMinZ != 0.0) ||
	(d3d_dev->active_viewport.dvMaxZ != 1.0)) {
	glDepthRange(0.0, 1.0);
	opt_bitmap |= DEPTH_RANGE_BIT;
    }
    if ((d3d_dev->active_viewport.dwX != 0) ||
	(d3d_dev->active_viewport.dwY != 0) ||
	(d3d_dev->active_viewport.dwWidth != d3d_dev->surface->surface_desc.dwWidth) ||
	(d3d_dev->active_viewport.dwHeight != d3d_dev->surface->surface_desc.dwHeight)) {
	glViewport(0, 0, d3d_dev->surface->surface_desc.dwWidth, d3d_dev->surface->surface_desc.dwHeight);
	opt_bitmap |= VIEWPORT_BIT;
    }
    glScissor(pRect->left, d3d_dev->surface->surface_desc.dwHeight - pRect->bottom,
	      pRect->right - pRect->left, pRect->bottom - pRect->top);
    if (gl_d3d_dev->lighting != FALSE) glDisable(GL_LIGHTING);
    if (gl_d3d_dev->cull_face != FALSE) glDisable(GL_CULL_FACE);
    if (use_alpha) {
	if (gl_d3d_dev->alpha_test == FALSE) glEnable(GL_ALPHA_TEST);
	if (((d3d_dev->state_block.render_state[D3DRENDERSTATE_ALPHAREF - 1] & 0x000000FF) != 0x00) ||
	    ((d3d_dev->state_block.render_state[D3DRENDERSTATE_ALPHAFUNC - 1]) != D3DCMP_GREATER)) {
	    glAlphaFunc(GL_GREATER, 0.0);
	}
    } else {
	if (gl_d3d_dev->alpha_test != FALSE) glDisable(GL_ALPHA_TEST);
    }
    if (gl_d3d_dev->stencil_test != FALSE) glDisable(GL_STENCIL_TEST);
    if (gl_d3d_dev->blending != FALSE) glDisable(GL_BLEND);
    if (gl_d3d_dev->fogging != FALSE) glDisable(GL_FOG);
    if (gl_d3d_dev->current_tex_env != GL_REPLACE)
	glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
    
    return opt_bitmap;
}

static void d3ddevice_restore_state_after_flush(IDirect3DDeviceImpl *d3d_dev, DWORD opt_bitmap, BOOLEAN use_alpha) {
    IDirect3DDeviceGLImpl* gl_d3d_dev = (IDirect3DDeviceGLImpl*) d3d_dev;

    /* And restore all the various states modified by this code */
    if (gl_d3d_dev->depth_test != 0) glEnable(GL_DEPTH_TEST);
    if (gl_d3d_dev->lighting != 0) glEnable(GL_LIGHTING);
    if ((gl_d3d_dev->alpha_test != 0) && (use_alpha == 0))
	glEnable(GL_ALPHA_TEST);
    else if ((gl_d3d_dev->alpha_test == 0) && (use_alpha != 0))
	glDisable(GL_ALPHA_TEST);
    if (use_alpha) {
	if (((d3d_dev->state_block.render_state[D3DRENDERSTATE_ALPHAREF - 1] & 0x000000FF) != 0x00) ||
	    ((d3d_dev->state_block.render_state[D3DRENDERSTATE_ALPHAFUNC - 1]) != D3DCMP_GREATER)) {
	    glAlphaFunc(convert_D3D_compare_to_GL(d3d_dev->state_block.render_state[D3DRENDERSTATE_ALPHAFUNC - 1]),
			(d3d_dev->state_block.render_state[D3DRENDERSTATE_ALPHAREF - 1] & 0x000000FF) / 255.0);
	}
    }
    if (gl_d3d_dev->stencil_test != 0) glEnable(GL_STENCIL_TEST);
    if (gl_d3d_dev->cull_face != 0) glEnable(GL_CULL_FACE);
    if (gl_d3d_dev->blending != 0) glEnable(GL_BLEND);
    if (gl_d3d_dev->fogging != 0) glEnable(GL_FOG);
    glDisable(GL_SCISSOR_TEST);
    glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, gl_d3d_dev->current_tex_env);
    if (opt_bitmap & DEPTH_RANGE_BIT) {
	glDepthRange(d3d_dev->active_viewport.dvMinZ, d3d_dev->active_viewport.dvMaxZ);
    }
    if (opt_bitmap & VIEWPORT_BIT) {
	glViewport(d3d_dev->active_viewport.dwX,
		   d3d_dev->surface->surface_desc.dwHeight - (d3d_dev->active_viewport.dwHeight + d3d_dev->active_viewport.dwY),
		   d3d_dev->active_viewport.dwWidth, d3d_dev->active_viewport.dwHeight);
    }
    if (d3d_dev->tex_mat_is_identity[0] == FALSE) {
	d3d_dev->matrices_updated(d3d_dev, TEXMAT0_CHANGED);
    }
    
    /* This is a hack to prevent querying the current texture from GL. Basically, at the next
       DrawPrimitive call, this will bind the correct texture to this stage. */
    gl_d3d_dev->current_bound_texture[0] = (IDirectDrawSurfaceImpl *) 0x00000001;
    if (d3d_dev->state_block.texture_stage_state[0][D3DTSS_COLOROP - 1] == D3DTOP_DISABLE) glDisable(GL_TEXTURE_2D);
}

/* retrieve the X drawable to use on a given DC */
inline static Drawable get_drawable( HDC hdc )
{
    Drawable drawable;
    enum x11drv_escape_codes escape = X11DRV_GET_DRAWABLE;

    if (!ExtEscape( hdc, X11DRV_ESCAPE, sizeof(escape), (LPCSTR)&escape,
                    sizeof(drawable), (LPSTR)&drawable )) drawable = 0;

    return drawable;
}

/* This is unnecessarely complicated :-) */
#define MEASUREMENT_WINDOW 5
#define NUMBER_OF_WINDOWS 10

static LONGLONG perf_freq;
static LONGLONG perf_storage[NUMBER_OF_WINDOWS];
static LONGLONG prev_time = 0;
static unsigned int current_window;
static unsigned int measurements_in_window;
static unsigned int valid_windows;

static BOOL opengl_flip( LPVOID dev, LPVOID drawable)
{
    IDirect3DDeviceImpl *d3d_dev = (IDirect3DDeviceImpl *) dev;
    IDirect3DDeviceGLImpl *gl_d3d_dev = (IDirect3DDeviceGLImpl *) dev;

    TRACE("(%p, %ld)\n", gl_d3d_dev->display,(Drawable)drawable);
    ENTER_GL();
    if (gl_d3d_dev->state[WINE_GL_BUFFER_BACK] == SURFACE_MEMORY_DIRTY) {
        d3d_dev->flush_to_framebuffer(d3d_dev, &(gl_d3d_dev->lock_rect[WINE_GL_BUFFER_BACK]), gl_d3d_dev->lock_surf[WINE_GL_BUFFER_BACK]);
    }
    gl_d3d_dev->state[WINE_GL_BUFFER_BACK] = SURFACE_GL;
    gl_d3d_dev->state[WINE_GL_BUFFER_FRONT] = SURFACE_GL;
    glXSwapBuffers(gl_d3d_dev->display, (Drawable)drawable);
    LEAVE_GL();

    if (TRACE_ON(ddraw_fps)) {
	LONGLONG current_time;
	LONGLONG frame_duration;
	QueryPerformanceCounter((LARGE_INTEGER *) &current_time);

	if (prev_time != 0) {
	    LONGLONG total_time = 0;
	    int tot_meas;
	    
	    frame_duration = current_time - prev_time;
	    prev_time = current_time;
	    
	    perf_storage[current_window] += frame_duration;
	    measurements_in_window++;
	    
	    if (measurements_in_window >= MEASUREMENT_WINDOW) {
		current_window++;
		valid_windows++;

		if (valid_windows < NUMBER_OF_WINDOWS) {
		    int i;
		    tot_meas = valid_windows * MEASUREMENT_WINDOW;
		    for (i = 0; i < valid_windows; i++) {
			total_time += perf_storage[i];
		    }
		} else {
		    int i;
		    tot_meas = NUMBER_OF_WINDOWS * MEASUREMENT_WINDOW;
		    for (i = 0; i < NUMBER_OF_WINDOWS; i++) {
			total_time += perf_storage[i];
		    }
		}

		TRACE_(ddraw_fps)(" %9.5f\n", (double) (perf_freq * tot_meas) / (double) total_time);
		
		if (current_window >= NUMBER_OF_WINDOWS) {
		    current_window = 0;
		}
		perf_storage[current_window] = 0;
		measurements_in_window = 0;
	    }
	} else {
	    prev_time = current_time;
	    memset(perf_storage, 0, sizeof(perf_storage));
	    current_window = 0;
	    valid_windows = 0;
	    measurements_in_window = 0;
	    QueryPerformanceFrequency((LARGE_INTEGER *) &perf_freq);
	}
    }
    
    return TRUE;
}


/*******************************************************************************
 *				OpenGL static functions
 */
static void set_context(IDirect3DDeviceImpl* This)
{
    IDirect3DDeviceGLImpl* glThis = (IDirect3DDeviceGLImpl*) This;
   
    TRACE("glxMakeCurrent %p, %ld, %p\n",glThis->display,glThis->drawable, glThis->gl_context);
    ENTER_GL();
    if (glXMakeCurrent(glThis->display, glThis->drawable, glThis->gl_context) == False) {
	ERR("Error in setting current context (context %p drawable %ld)!\n",
	    glThis->gl_context, glThis->drawable);
    }
    LEAVE_GL();
}

static void fill_opengl_caps(D3DDEVICEDESC *d1)
{
    d1->dwSize  = sizeof(*d1);
    d1->dwFlags = D3DDD_COLORMODEL | D3DDD_DEVCAPS | D3DDD_TRANSFORMCAPS | D3DDD_BCLIPPING | D3DDD_LIGHTINGCAPS |
	D3DDD_LINECAPS | D3DDD_TRICAPS | D3DDD_DEVICERENDERBITDEPTH | D3DDD_DEVICEZBUFFERBITDEPTH |
	D3DDD_MAXBUFFERSIZE | D3DDD_MAXVERTEXCOUNT;
    d1->dcmColorModel = D3DCOLOR_RGB;
    d1->dwDevCaps = opengl_device_caps.dwDevCaps;
    d1->dtcTransformCaps.dwSize = sizeof(D3DTRANSFORMCAPS);
    d1->dtcTransformCaps.dwCaps = D3DTRANSFORMCAPS_CLIP;
    d1->bClipping = TRUE;
    d1->dlcLightingCaps.dwSize = sizeof(D3DLIGHTINGCAPS);
    d1->dlcLightingCaps.dwCaps = D3DLIGHTCAPS_DIRECTIONAL | D3DLIGHTCAPS_PARALLELPOINT | D3DLIGHTCAPS_POINT | D3DLIGHTCAPS_SPOT;
    d1->dlcLightingCaps.dwLightingModel = D3DLIGHTINGMODEL_RGB;
    d1->dlcLightingCaps.dwNumLights = opengl_device_caps.dwMaxActiveLights;
    d1->dpcLineCaps = opengl_device_caps.dpcLineCaps;
    d1->dpcTriCaps = opengl_device_caps.dpcTriCaps;
    d1->dwDeviceRenderBitDepth  = opengl_device_caps.dwDeviceRenderBitDepth;
    d1->dwDeviceZBufferBitDepth = opengl_device_caps.dwDeviceZBufferBitDepth;
    d1->dwMaxBufferSize = 0;
    d1->dwMaxVertexCount = 65536;
    d1->dwMinTextureWidth  = opengl_device_caps.dwMinTextureWidth;
    d1->dwMinTextureHeight = opengl_device_caps.dwMinTextureHeight;
    d1->dwMaxTextureWidth  = opengl_device_caps.dwMaxTextureWidth;
    d1->dwMaxTextureHeight = opengl_device_caps.dwMaxTextureHeight;
    d1->dwMinStippleWidth  = 1;
    d1->dwMinStippleHeight = 1;
    d1->dwMaxStippleWidth  = 32;
    d1->dwMaxStippleHeight = 32;
    d1->dwMaxTextureRepeat = opengl_device_caps.dwMaxTextureRepeat;
    d1->dwMaxTextureAspectRatio = opengl_device_caps.dwMaxTextureAspectRatio;
    d1->dwMaxAnisotropy = opengl_device_caps.dwMaxAnisotropy;
    d1->dvGuardBandLeft = opengl_device_caps.dvGuardBandLeft;
    d1->dvGuardBandRight = opengl_device_caps.dvGuardBandRight;
    d1->dvGuardBandTop = opengl_device_caps.dvGuardBandTop;
    d1->dvGuardBandBottom = opengl_device_caps.dvGuardBandBottom;
    d1->dvExtentsAdjust = opengl_device_caps.dvExtentsAdjust;
    d1->dwStencilCaps = opengl_device_caps.dwStencilCaps;
    d1->dwFVFCaps = opengl_device_caps.dwFVFCaps;
    d1->dwTextureOpCaps = opengl_device_caps.dwTextureOpCaps;
    d1->wMaxTextureBlendStages = opengl_device_caps.wMaxTextureBlendStages;
    d1->wMaxSimultaneousTextures = opengl_device_caps.wMaxSimultaneousTextures;
}

static void fill_opengl_caps_7(D3DDEVICEDESC7 *d)
{
    *d = opengl_device_caps;
}

HRESULT d3ddevice_enumerate(LPD3DENUMDEVICESCALLBACK cb, LPVOID context, DWORD version)
{
    D3DDEVICEDESC dref, d1, d2;
    HRESULT ret_value;

    /* Some games (Motoracer 2 demo) have the bad idea to modify the device name string.
       Let's put the string in a sufficiently sized array in writable memory. */
    char device_name[50];
    strcpy(device_name,"direct3d");

    fill_opengl_caps(&dref);

    if (version > 1) {
        /* It seems that enumerating the reference IID on Direct3D 1 games (AvP / Motoracer2) breaks them */
        TRACE(" enumerating OpenGL D3DDevice interface using reference IID (IID %s).\n", debugstr_guid(&IID_IDirect3DRefDevice));
	d1 = dref;
	d2 = dref;
	ret_value = cb((LPIID) &IID_IDirect3DRefDevice, "WINE Reference Direct3DX using OpenGL", device_name, &d1, &d2, context);
	if (ret_value != D3DENUMRET_OK)
	    return ret_value;
    }
    
    TRACE(" enumerating OpenGL D3DDevice interface (IID %s).\n", debugstr_guid(&IID_D3DDEVICE_OpenGL));
    d1 = dref;
    d2 = dref;
    ret_value = cb((LPIID) &IID_D3DDEVICE_OpenGL, "WINE Direct3DX using OpenGL", device_name, &d1, &d2, context);
    if (ret_value != D3DENUMRET_OK)
        return ret_value;

    return D3DENUMRET_OK;
}

HRESULT d3ddevice_enumerate7(LPD3DENUMDEVICESCALLBACK7 cb, LPVOID context)
{
    D3DDEVICEDESC7 ddesc;

    fill_opengl_caps_7(&ddesc);
    
    TRACE(" enumerating OpenGL D3DDevice7 interface.\n");
    
    return cb("WINE Direct3D7 using OpenGL", "Wine D3D7 device", &ddesc, context);
}

ULONG WINAPI
GL_IDirect3DDeviceImpl_7_3T_2T_1T_Release(LPDIRECT3DDEVICE7 iface)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    IDirect3DDeviceGLImpl *glThis = (IDirect3DDeviceGLImpl *) This;
    
    TRACE("(%p/%p)->() decrementing from %lu.\n", This, iface, This->ref);
    if (!--(This->ref)) {
        int i;
	IDirectDrawSurfaceImpl *surface = This->surface, *surf;
	
	/* Release texture associated with the device */ 
	for (i = 0; i < MAX_TEXTURES; i++) {
	    if (This->current_texture[i] != NULL)
	        IDirectDrawSurface7_Release(ICOM_INTERFACE(This->current_texture[i], IDirectDrawSurface7));
	    HeapFree(GetProcessHeap(), 0, This->tex_mat[i]);
	}

	/* Look for the front buffer and override its surface's Flip method (if in double buffering) */
	for (surf = surface; surf != NULL; surf = surf->surface_owner) {
	    if ((surf->surface_desc.ddsCaps.dwCaps&(DDSCAPS_FLIP|DDSCAPS_FRONTBUFFER)) == (DDSCAPS_FLIP|DDSCAPS_FRONTBUFFER)) {
	        surf->aux_ctx  = NULL;
		surf->aux_data = NULL;
		surf->aux_flip = NULL;
		break;
	    }
	}
	for (surf = surface; surf != NULL; surf = surf->surface_owner) {
	    IDirectDrawSurfaceImpl *surf2;
	    for (surf2 = surf; surf2->prev_attached != NULL; surf2 = surf2->prev_attached) ;
	    for (; surf2 != NULL; surf2 = surf2->next_attached) {
	        if (((surf2->surface_desc.ddsCaps.dwCaps & (DDSCAPS_3DDEVICE)) == (DDSCAPS_3DDEVICE)) &&
		    ((surf2->surface_desc.ddsCaps.dwCaps & (DDSCAPS_ZBUFFER)) != (DDSCAPS_ZBUFFER))) {
		    /* Override the Lock / Unlock function for all these surfaces */
		    surf2->lock_update = surf2->lock_update_prev;
		    surf2->unlock_update = surf2->unlock_update_prev;
		    /* And install also the blt / bltfast overrides */
		    surf2->aux_blt = NULL;
		    surf2->aux_bltfast = NULL;
		}
		surf2->d3ddevice = NULL;
	    }
	}
	
	/* And warn the D3D object that this device is no longer active... */
	This->d3d->d3d_removed_device(This->d3d, This);

	HeapFree(GetProcessHeap(), 0, This->world_mat);
	HeapFree(GetProcessHeap(), 0, This->view_mat);
	HeapFree(GetProcessHeap(), 0, This->proj_mat);

	if (glThis->surface_ptr)
	    HeapFree(GetProcessHeap(), 0, glThis->surface_ptr);

	DeleteCriticalSection(&(This->crit));
	
	ENTER_GL();
	if (glThis->unlock_tex)
	    glDeleteTextures(1, &(glThis->unlock_tex));
	glXDestroyContext(glThis->display, glThis->gl_context);
	LEAVE_GL();
	HeapFree(GetProcessHeap(), 0, This->clipping_planes);

	HeapFree(GetProcessHeap(), 0, This);
	return 0;
    }
    return This->ref;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_3_2T_1T_GetCaps(LPDIRECT3DDEVICE3 iface,
				       LPD3DDEVICEDESC lpD3DHWDevDesc,
				       LPD3DDEVICEDESC lpD3DHELDevDesc)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice3, iface);
    D3DDEVICEDESC desc;
    DWORD dwSize;

    TRACE("(%p/%p)->(%p,%p)\n", This, iface, lpD3DHWDevDesc, lpD3DHELDevDesc);

    fill_opengl_caps(&desc);
    dwSize = lpD3DHWDevDesc->dwSize;
    memset(lpD3DHWDevDesc, 0, dwSize);
    memcpy(lpD3DHWDevDesc, &desc, (dwSize <= desc.dwSize ? dwSize : desc.dwSize));

    dwSize = lpD3DHELDevDesc->dwSize;
    memset(lpD3DHELDevDesc, 0, dwSize);
    memcpy(lpD3DHELDevDesc, &desc, (dwSize <= desc.dwSize ? dwSize : desc.dwSize));

    TRACE(" returning caps : (no dump function yet)\n");

    return DD_OK;
}

static HRESULT enum_texture_format_OpenGL(LPD3DENUMTEXTUREFORMATSCALLBACK cb_1,
					  LPD3DENUMPIXELFORMATSCALLBACK cb_2,
					  LPVOID context)
{
    DDSURFACEDESC sdesc;
    LPDDPIXELFORMAT pformat;

    /* Do the texture enumeration */
    sdesc.dwSize = sizeof(DDSURFACEDESC);
    sdesc.dwFlags = DDSD_PIXELFORMAT | DDSD_CAPS;
    sdesc.ddsCaps.dwCaps = DDSCAPS_TEXTURE;
    pformat = &(sdesc.ddpfPixelFormat);
    pformat->dwSize = sizeof(DDPIXELFORMAT);
    pformat->dwFourCC = 0;

    TRACE("Enumerating GL_RGBA unpacked (32)\n");
    pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS;
    pformat->u1.dwRGBBitCount = 32;
    pformat->u2.dwRBitMask =        0x00FF0000;
    pformat->u3.dwGBitMask =        0x0000FF00;
    pformat->u4.dwBBitMask =        0x000000FF;
    pformat->u5.dwRGBAlphaBitMask = 0xFF000000;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;

    TRACE("Enumerating GL_RGB unpacked (32)\n");
    pformat->dwFlags = DDPF_RGB;
    pformat->u1.dwRGBBitCount = 32;
    pformat->u2.dwRBitMask =        0x00FF0000;
    pformat->u3.dwGBitMask =        0x0000FF00;
    pformat->u4.dwBBitMask =        0x000000FF;
    pformat->u5.dwRGBAlphaBitMask = 0x00000000;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;
    
    TRACE("Enumerating GL_RGB unpacked (24)\n");
    pformat->dwFlags = DDPF_RGB;
    pformat->u1.dwRGBBitCount = 24;
    pformat->u2.dwRBitMask = 0x00FF0000;
    pformat->u3.dwGBitMask = 0x0000FF00;
    pformat->u4.dwBBitMask = 0x000000FF;
    pformat->u5.dwRGBAlphaBitMask = 0x00000000;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;

    /* Note : even if this is an 'emulated' texture format, it needs to be first
              as some dumb applications seem to rely on that. */
    TRACE("Enumerating GL_RGBA packed GL_UNSIGNED_SHORT_1_5_5_5 (ARGB) (16)\n");
    pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS;
    pformat->u1.dwRGBBitCount = 16;
    pformat->u2.dwRBitMask =        0x00007C00;
    pformat->u3.dwGBitMask =        0x000003E0;
    pformat->u4.dwBBitMask =        0x0000001F;
    pformat->u5.dwRGBAlphaBitMask = 0x00008000;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;

    TRACE("Enumerating GL_RGBA packed GL_UNSIGNED_SHORT_4_4_4_4 (ARGB) (16)\n");
    pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS;
    pformat->u1.dwRGBBitCount = 16;
    pformat->u2.dwRBitMask =        0x00000F00;
    pformat->u3.dwGBitMask =        0x000000F0;
    pformat->u4.dwBBitMask =        0x0000000F;
    pformat->u5.dwRGBAlphaBitMask = 0x0000F000;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;

    TRACE("Enumerating GL_RGB packed GL_UNSIGNED_SHORT_5_6_5 (16)\n");
    pformat->dwFlags = DDPF_RGB;
    pformat->u1.dwRGBBitCount = 16;
    pformat->u2.dwRBitMask = 0x0000F800;
    pformat->u3.dwGBitMask = 0x000007E0;
    pformat->u4.dwBBitMask = 0x0000001F;
    pformat->u5.dwRGBAlphaBitMask = 0x00000000;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;

    TRACE("Enumerating GL_RGB packed GL_UNSIGNED_SHORT_5_5_5 (16)\n");
    pformat->dwFlags = DDPF_RGB;
    pformat->u1.dwRGBBitCount = 16;
    pformat->u2.dwRBitMask = 0x00007C00;
    pformat->u3.dwGBitMask = 0x000003E0;
    pformat->u4.dwBBitMask = 0x0000001F;
    pformat->u5.dwRGBAlphaBitMask = 0x00000000;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;
    
#if 0
    /* This is a compromise : some games choose the first 16 bit texture format with alpha they
       find enumerated, others the last one. And both want to have the ARGB one.
       
       So basically, forget our OpenGL roots and do not even enumerate our RGBA ones.
    */
    /* See argument about the RGBA format for 'packed' texture formats */
    TRACE("Enumerating GL_RGBA unpacked (32)\n");
    pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS;
    pformat->u1.dwRGBBitCount = 32;
    pformat->u2.dwRBitMask =        0xFF000000;
    pformat->u3.dwGBitMask =        0x00FF0000;
    pformat->u4.dwBBitMask =        0x0000FF00;
    pformat->u5.dwRGBAlphaBitMask = 0x000000FF;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;
    
    TRACE("Enumerating GL_RGBA packed GL_UNSIGNED_SHORT_4_4_4_4 (16)\n");
    pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS;
    pformat->u1.dwRGBBitCount = 16;
    pformat->u2.dwRBitMask =        0x0000F000;
    pformat->u3.dwGBitMask =        0x00000F00;
    pformat->u4.dwBBitMask =        0x000000F0;
    pformat->u5.dwRGBAlphaBitMask = 0x0000000F;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;

    TRACE("Enumerating GL_RGBA packed GL_UNSIGNED_SHORT_5_5_5_1 (16)\n");
    pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS;
    pformat->u1.dwRGBBitCount = 16;
    pformat->u2.dwRBitMask =        0x0000F800;
    pformat->u3.dwGBitMask =        0x000007C0;
    pformat->u4.dwBBitMask =        0x0000003E;
    pformat->u5.dwRGBAlphaBitMask = 0x00000001;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;
#endif

    TRACE("Enumerating GL_RGB packed GL_UNSIGNED_BYTE_3_3_2 (8)\n");
    pformat->dwFlags = DDPF_RGB;
    pformat->u1.dwRGBBitCount = 8;
    pformat->u2.dwRBitMask =        0x000000E0;
    pformat->u3.dwGBitMask =        0x0000001C;
    pformat->u4.dwBBitMask =        0x00000003;
    pformat->u5.dwRGBAlphaBitMask = 0x00000000;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;

    TRACE("Enumerating Paletted (8)\n");
    pformat->dwFlags = DDPF_PALETTEINDEXED8;
    pformat->u1.dwRGBBitCount = 8;
    pformat->u2.dwRBitMask =        0x00000000;
    pformat->u3.dwGBitMask =        0x00000000;
    pformat->u4.dwBBitMask =        0x00000000;
    pformat->u5.dwRGBAlphaBitMask = 0x00000000;
    if (cb_1) if (cb_1(&sdesc , context) == 0) return DD_OK;
    if (cb_2) if (cb_2(pformat, context) == 0) return DD_OK;

    TRACE("End of enumeration\n");
    return DD_OK;
}


HRESULT
d3ddevice_find(IDirectDrawImpl *d3d,
	       LPD3DFINDDEVICESEARCH lpD3DDFS,
	       LPD3DFINDDEVICERESULT lplpD3DDevice)
{
    D3DDEVICEDESC desc;
  
    if ((lpD3DDFS->dwFlags & D3DFDS_COLORMODEL) &&
	(lpD3DDFS->dcmColorModel != D3DCOLOR_RGB)) {
        TRACE(" trying to request a non-RGB D3D color model. Not supported.\n");
	return DDERR_INVALIDPARAMS; /* No real idea what to return here :-) */
    }
    if (lpD3DDFS->dwFlags & D3DFDS_GUID) {
        TRACE(" trying to match guid %s.\n", debugstr_guid(&(lpD3DDFS->guid)));
	if ((IsEqualGUID(&IID_D3DDEVICE_OpenGL, &(lpD3DDFS->guid)) == 0) &&
	    (IsEqualGUID(&IID_IDirect3DHALDevice, &(lpD3DDFS->guid)) == 0) &&
	    (IsEqualGUID(&IID_IDirect3DRefDevice, &(lpD3DDFS->guid)) == 0)) {
	    TRACE(" no match for this GUID.\n");
	    return DDERR_INVALIDPARAMS;
	}
    }

    /* Now return our own GUID */
    lplpD3DDevice->guid = IID_D3DDEVICE_OpenGL;
    fill_opengl_caps(&desc);
    lplpD3DDevice->ddHwDesc = desc;
    lplpD3DDevice->ddSwDesc = desc;

    TRACE(" returning Wine's OpenGL device with (undumped) capabilities\n");
    
    return D3D_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_2_1T_EnumTextureFormats(LPDIRECT3DDEVICE2 iface,
					       LPD3DENUMTEXTUREFORMATSCALLBACK lpD3DEnumTextureProc,
					       LPVOID lpArg)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice2, iface);
    TRACE("(%p/%p)->(%p,%p)\n", This, iface, lpD3DEnumTextureProc, lpArg);
    return enum_texture_format_OpenGL(lpD3DEnumTextureProc, NULL, lpArg);
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_EnumTextureFormats(LPDIRECT3DDEVICE7 iface,
					       LPD3DENUMPIXELFORMATSCALLBACK lpD3DEnumPixelProc,
					       LPVOID lpArg)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    TRACE("(%p/%p)->(%p,%p)\n", This, iface, lpD3DEnumPixelProc, lpArg);
    return enum_texture_format_OpenGL(NULL, lpD3DEnumPixelProc, lpArg);
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_2T_SetRenderState(LPDIRECT3DDEVICE7 iface,
					      D3DRENDERSTATETYPE dwRenderStateType,
					      DWORD dwRenderState)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    TRACE("(%p/%p)->(%08x,%08lx)\n", This, iface, dwRenderStateType, dwRenderState);

    /* Call the render state functions */
    store_render_state(This, dwRenderStateType, dwRenderState, &This->state_block);
    set_render_state(This, dwRenderStateType, &This->state_block);

    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_2T_GetRenderState(LPDIRECT3DDEVICE7 iface,
					      D3DRENDERSTATETYPE dwRenderStateType,
					      LPDWORD lpdwRenderState)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    TRACE("(%p/%p)->(%08x,%p)\n", This, iface, dwRenderStateType, lpdwRenderState);

    /* Call the render state functions */
    get_render_state(This, dwRenderStateType, lpdwRenderState, &This->state_block);

    TRACE(" - asked for rendering state : %s, returning value %08lx.\n", _get_renderstate(dwRenderStateType), *lpdwRenderState);

    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_3_2T_SetLightState(LPDIRECT3DDEVICE3 iface,
					  D3DLIGHTSTATETYPE dwLightStateType,
					  DWORD dwLightState)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice3, iface);
    
    TRACE("(%p/%p)->(%08x,%08lx)\n", This, iface, dwLightStateType, dwLightState);

    if (!dwLightStateType && (dwLightStateType > D3DLIGHTSTATE_COLORVERTEX))
	TRACE("Unexpected Light State Type\n");
	return DDERR_INVALIDPARAMS;
	
    if (dwLightStateType == D3DLIGHTSTATE_MATERIAL /* 1 */) {
	IDirect3DMaterialImpl *mat = (IDirect3DMaterialImpl *) dwLightState;

	if (mat != NULL) {
	    mat->activate(mat);
	} else {
	    ERR(" D3DLIGHTSTATE_MATERIAL called with NULL material !!!\n");
	}
    } else if (dwLightStateType == D3DLIGHTSTATE_COLORMODEL /* 3 */) {
	switch (dwLightState) {
	    case D3DCOLOR_MONO:
	       ERR("DDCOLOR_MONO should not happen!\n");
	       break;
	    case D3DCOLOR_RGB:
	       /* We are already in this mode */
	       break;
	    default:
	       ERR("Unknown color model!\n");
	       break;
	}
    } else {
        D3DRENDERSTATETYPE rs;
	switch (dwLightStateType) {

	    case D3DLIGHTSTATE_AMBIENT:       /* 2 */
		rs = D3DRENDERSTATE_AMBIENT;
		break;		
	    case D3DLIGHTSTATE_FOGMODE:       /* 4 */
		rs = D3DRENDERSTATE_FOGVERTEXMODE;
		break;
	    case D3DLIGHTSTATE_FOGSTART:      /* 5 */
		rs = D3DRENDERSTATE_FOGSTART;
		break;
	    case D3DLIGHTSTATE_FOGEND:        /* 6 */
		rs = D3DRENDERSTATE_FOGEND;
		break;
	    case D3DLIGHTSTATE_FOGDENSITY:    /* 7 */
		rs = D3DRENDERSTATE_FOGDENSITY;
		break;
	    case D3DLIGHTSTATE_COLORVERTEX:   /* 8 */
		rs = D3DRENDERSTATE_COLORVERTEX;
		break;
	    default:
		break;
	}

	IDirect3DDevice7_SetRenderState(ICOM_INTERFACE(This, IDirect3DDevice7),
	                   		rs,dwLightState);
    }

    return DD_OK;
}

static void draw_primitive_start_GL(D3DPRIMITIVETYPE d3dpt)
{
    switch (d3dpt) {
        case D3DPT_POINTLIST:
            TRACE("Start POINTS\n");
	    glBegin(GL_POINTS);
	    break;

	case D3DPT_LINELIST:
	    TRACE("Start LINES\n");
	    glBegin(GL_LINES);
	    break;

	case D3DPT_LINESTRIP:
	    TRACE("Start LINE_STRIP\n");
	    glBegin(GL_LINE_STRIP);
	    break;

	case D3DPT_TRIANGLELIST:
	    TRACE("Start TRIANGLES\n");
	    glBegin(GL_TRIANGLES);
	    break;

	case D3DPT_TRIANGLESTRIP:
	    TRACE("Start TRIANGLE_STRIP\n");
	    glBegin(GL_TRIANGLE_STRIP);
	    break;

	case D3DPT_TRIANGLEFAN:
	    TRACE("Start TRIANGLE_FAN\n");
	    glBegin(GL_TRIANGLE_FAN);
	    break;

	default:
	    FIXME("Unhandled primitive %08x\n", d3dpt);
	    break;
    }
}

/* This function calculate the Z coordinate from Zproj */ 
static float ZfromZproj(IDirect3DDeviceImpl *This, D3DVALUE Zproj)
{
    float a,b,c,d;
    /* Assume that X = Y = 0 and W = 1 */
    a = This->proj_mat->_33;
    b = This->proj_mat->_34;
    c = This->proj_mat->_43;
    d = This->proj_mat->_44;
    /* We have in homogenous coordinates Z' = a * Z + c and W' = b * Z + d
     * So in non homogenous coordinates we have Zproj = (a * Z + c) / (b * Z + d)
     * And finally Z = (d * Zproj - c) / (a - b * Zproj)
     */
    return (d*Zproj - c) / (a - b*Zproj);
}

static void build_fog_table(BYTE *fog_table, DWORD fog_color) {
    int i;
    
    TRACE(" rebuilding fog table (%06lx)...\n", fog_color & 0x00FFFFFF);
    
    for (i = 0; i < 3; i++) {
        BYTE fog_color_component = (fog_color >> (8 * i)) & 0xFF;
	DWORD elt;
	for (elt = 0; elt < 0x10000; elt++) {
	    /* We apply the fog transformation and cache the result */
	    DWORD fog_intensity = elt & 0xFF;
	    DWORD vertex_color = (elt >> 8) & 0xFF;
	    fog_table[(i * 0x10000) + elt] = ((fog_intensity * vertex_color) + ((0xFF - fog_intensity) * fog_color_component)) / 0xFF;
	}
    }
}

static void draw_primitive_handle_GL_state(IDirect3DDeviceImpl *This,
					   BOOLEAN vertex_transformed,
					   BOOLEAN vertex_lit) {
    IDirect3DDeviceGLImpl* glThis = (IDirect3DDeviceGLImpl*) This;
  
    /* Puts GL in the correct lighting / transformation mode */
    if ((vertex_transformed == FALSE) && 
	(glThis->transform_state != GL_TRANSFORM_NORMAL)) {
        /* Need to put the correct transformation again if we go from Transformed
	   vertices to non-transformed ones.
	*/
        This->set_matrices(This, VIEWMAT_CHANGED|WORLDMAT_CHANGED|PROJMAT_CHANGED,
			   This->world_mat, This->view_mat, This->proj_mat);
	glThis->transform_state = GL_TRANSFORM_NORMAL;

    } else if ((vertex_transformed == TRUE) &&
	       (glThis->transform_state != GL_TRANSFORM_ORTHO)) {
        /* Set our orthographic projection */
	if (glThis->transform_state != GL_TRANSFORM_ORTHO) {
	    glThis->transform_state = GL_TRANSFORM_ORTHO;
	    d3ddevice_set_ortho(This);
	}
    }

    /* TODO: optimize this to not always reset all the fog stuff on all DrawPrimitive call
             if no fogging state change occurred */
    if (This->state_block.render_state[D3DRENDERSTATE_FOGENABLE - 1] == TRUE) {
        if (vertex_transformed == TRUE) {
	    if (glThis->fogging != 0) {
		glDisable(GL_FOG);
		glThis->fogging = 0;
	    }
	    /* Now check if our fog_table still corresponds to the current vertex color.
	       Element '0x..00' is always the fog color as it corresponds to maximum fog intensity */
	    if ((glThis->fog_table[0 * 0x10000 + 0x0000] != ((This->state_block.render_state[D3DRENDERSTATE_FOGCOLOR - 1] >>  0) & 0xFF)) ||
		(glThis->fog_table[1 * 0x10000 + 0x0000] != ((This->state_block.render_state[D3DRENDERSTATE_FOGCOLOR - 1] >>  8) & 0xFF)) ||
		(glThis->fog_table[2 * 0x10000 + 0x0000] != ((This->state_block.render_state[D3DRENDERSTATE_FOGCOLOR - 1] >> 16) & 0xFF))) {
	        /* We need to rebuild our fog table.... */
		build_fog_table(glThis->fog_table, This->state_block.render_state[D3DRENDERSTATE_FOGCOLOR - 1]);
	    }
	} else {
	    if (This->state_block.render_state[D3DRENDERSTATE_FOGTABLEMODE - 1] != D3DFOG_NONE) {
	        switch (This->state_block.render_state[D3DRENDERSTATE_FOGTABLEMODE - 1]) {
                    case D3DFOG_LINEAR: glFogi(GL_FOG_MODE, GL_LINEAR); break; 
		    case D3DFOG_EXP:    glFogi(GL_FOG_MODE, GL_EXP); break; 
		    case D3DFOG_EXP2:   glFogi(GL_FOG_MODE, GL_EXP2); break;
		}
		if (vertex_lit == FALSE) {
		    glFogf(GL_FOG_START, *(float*)&This->state_block.render_state[D3DRENDERSTATE_FOGSTART - 1]);
		    glFogf(GL_FOG_END, *(float*)&This->state_block.render_state[D3DRENDERSTATE_FOGEND - 1]);
		} else {
		    /* Special case of 'pixel fog' */
		    glFogf(GL_FOG_START, ZfromZproj(This, *(float*)&This->state_block.render_state[D3DRENDERSTATE_FOGSTART - 1]));
		    glFogf(GL_FOG_END, ZfromZproj(This, *(float*)&This->state_block.render_state[D3DRENDERSTATE_FOGEND - 1]));
		}
		if (glThis->fogging == 0) {
		    glEnable(GL_FOG);
		    glThis->fogging = 1;
		}
	    } else {
		if (glThis->fogging != 0) {
		    glDisable(GL_FOG);
		    glThis->fogging = 0;
		}
	    }
        }
    } else {
	if (glThis->fogging != 0) {
	    glDisable(GL_FOG);
	    glThis->fogging = 0;
	}
    }
    
    /* Handle the 'no-normal' case */
    if ((vertex_lit == FALSE) && (This->state_block.render_state[D3DRENDERSTATE_LIGHTING - 1] == TRUE)) {
	if (glThis->lighting == 0) {
	    glEnable(GL_LIGHTING);
	    glThis->lighting = 1;
	}
    } else {
	if (glThis->lighting != 0) {
	    glDisable(GL_LIGHTING);
	    glThis->lighting = 0;
	}
    }

    /* Handle the code for pre-vertex material properties */
    if (vertex_transformed == FALSE) {
        if ((This->state_block.render_state[D3DRENDERSTATE_LIGHTING - 1] == TRUE) &&
	    (This->state_block.render_state[D3DRENDERSTATE_COLORVERTEX - 1] == TRUE)) {
	    if ((This->state_block.render_state[D3DRENDERSTATE_DIFFUSEMATERIALSOURCE - 1] != D3DMCS_MATERIAL) ||
		(This->state_block.render_state[D3DRENDERSTATE_AMBIENTMATERIALSOURCE - 1] != D3DMCS_MATERIAL) ||
		(This->state_block.render_state[D3DRENDERSTATE_EMISSIVEMATERIALSOURCE - 1] != D3DMCS_MATERIAL) ||
		(This->state_block.render_state[D3DRENDERSTATE_SPECULARMATERIALSOURCE - 1] != D3DMCS_MATERIAL)) {
	        glEnable(GL_COLOR_MATERIAL);
	    }
	}
    }
}


inline static void draw_primitive(IDirect3DDeviceImpl *This, DWORD maxvert, WORD *index,
				  D3DVERTEXTYPE d3dvt, D3DPRIMITIVETYPE d3dpt, void *lpvertex)
{
    D3DDRAWPRIMITIVESTRIDEDDATA strided;

    switch (d3dvt) {
        case D3DVT_VERTEX: {
	    strided.position.lpvData = &((D3DVERTEX *) lpvertex)->u1.x;
	    strided.position.dwStride = sizeof(D3DVERTEX);
	    strided.normal.lpvData = &((D3DVERTEX *) lpvertex)->u4.nx;
	    strided.normal.dwStride = sizeof(D3DVERTEX);
	    strided.textureCoords[0].lpvData = &((D3DVERTEX *) lpvertex)->u7.tu;
	    strided.textureCoords[0].dwStride = sizeof(D3DVERTEX);
	    draw_primitive_strided(This, d3dpt, D3DFVF_VERTEX, &strided, 0 /* Unused */, index, maxvert, 0 /* Unused */);
	} break;

        case D3DVT_LVERTEX: {
	    strided.position.lpvData = &((D3DLVERTEX *) lpvertex)->u1.x;
	    strided.position.dwStride = sizeof(D3DLVERTEX);
	    strided.diffuse.lpvData = &((D3DLVERTEX *) lpvertex)->u4.color;
	    strided.diffuse.dwStride = sizeof(D3DLVERTEX);
	    strided.specular.lpvData = &((D3DLVERTEX *) lpvertex)->u5.specular;
	    strided.specular.dwStride = sizeof(D3DLVERTEX);
	    strided.textureCoords[0].lpvData = &((D3DLVERTEX *) lpvertex)->u6.tu;
	    strided.textureCoords[0].dwStride = sizeof(D3DLVERTEX);
	    draw_primitive_strided(This, d3dpt, D3DFVF_LVERTEX, &strided, 0 /* Unused */, index, maxvert, 0 /* Unused */);
	} break;

        case D3DVT_TLVERTEX: {
	    strided.position.lpvData = &((D3DTLVERTEX *) lpvertex)->u1.sx;
	    strided.position.dwStride = sizeof(D3DTLVERTEX);
	    strided.diffuse.lpvData = &((D3DTLVERTEX *) lpvertex)->u5.color;
	    strided.diffuse.dwStride = sizeof(D3DTLVERTEX);
	    strided.specular.lpvData = &((D3DTLVERTEX *) lpvertex)->u6.specular;
	    strided.specular.dwStride = sizeof(D3DTLVERTEX);
	    strided.textureCoords[0].lpvData = &((D3DTLVERTEX *) lpvertex)->u7.tu;
	    strided.textureCoords[0].dwStride = sizeof(D3DTLVERTEX);
	    draw_primitive_strided(This, d3dpt, D3DFVF_TLVERTEX, &strided, 0 /* Unused */, index, maxvert, 0 /* Unused */);
	} break;

        default:
	    FIXME("Unhandled vertex type %08x\n", d3dvt);
	    break;
    }
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_2_DrawPrimitive(LPDIRECT3DDEVICE2 iface,
				       D3DPRIMITIVETYPE d3dptPrimitiveType,
				       D3DVERTEXTYPE d3dvtVertexType,
				       LPVOID lpvVertices,
				       DWORD dwVertexCount,
				       DWORD dwFlags)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice2, iface);

    TRACE("(%p/%p)->(%08x,%08x,%p,%08lx,%08lx)\n", This, iface, d3dptPrimitiveType, d3dvtVertexType, lpvVertices, dwVertexCount, dwFlags);
    if (TRACE_ON(ddraw)) {
        TRACE(" - flags : "); dump_DPFLAGS(dwFlags);
    }

    draw_primitive(This, dwVertexCount, NULL, d3dvtVertexType, d3dptPrimitiveType, lpvVertices);
		   
    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_2_DrawIndexedPrimitive(LPDIRECT3DDEVICE2 iface,
					      D3DPRIMITIVETYPE d3dptPrimitiveType,
					      D3DVERTEXTYPE d3dvtVertexType,
					      LPVOID lpvVertices,
					      DWORD dwVertexCount,
					      LPWORD dwIndices,
					      DWORD dwIndexCount,
					      DWORD dwFlags)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice2, iface);
    TRACE("(%p/%p)->(%08x,%08x,%p,%08lx,%p,%08lx,%08lx)\n", This, iface, d3dptPrimitiveType, d3dvtVertexType, lpvVertices, dwVertexCount, dwIndices, dwIndexCount, dwFlags);
    if (TRACE_ON(ddraw)) {
        TRACE(" - flags : "); dump_DPFLAGS(dwFlags);
    }

    draw_primitive(This, dwIndexCount, dwIndices, d3dvtVertexType, d3dptPrimitiveType, lpvVertices);
    
    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_1_CreateExecuteBuffer(LPDIRECT3DDEVICE iface,
					     LPD3DEXECUTEBUFFERDESC lpDesc,
					     LPDIRECT3DEXECUTEBUFFER* lplpDirect3DExecuteBuffer,
					     IUnknown* pUnkOuter)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice, iface);
    IDirect3DExecuteBufferImpl *ret;
    HRESULT ret_value;
    
    TRACE("(%p/%p)->(%p,%p,%p)\n", This, iface, lpDesc, lplpDirect3DExecuteBuffer, pUnkOuter);

    ret_value = d3dexecutebuffer_create(&ret, This->d3d, This, lpDesc);
    *lplpDirect3DExecuteBuffer = ICOM_INTERFACE(ret, IDirect3DExecuteBuffer);

    TRACE(" returning %p.\n", *lplpDirect3DExecuteBuffer);
    
    return ret_value;
}

/* These are the various handler used in the generic path */
inline static void handle_xyz(D3DVALUE *coords) {
    glVertex3fv(coords);
}
inline static void handle_xyzrhw(D3DVALUE *coords) {
    if (coords[3] < 1e-8)
        glVertex3fv(coords);
    else {
        GLfloat w = 1.0 / coords[3];
	
        glVertex4f(coords[0] * w,
		   coords[1] * w,
		   coords[2] * w,
		   w);
    }
}
inline static void handle_normal(D3DVALUE *coords) {
    glNormal3fv(coords);
}

inline static void handle_diffuse_base(STATEBLOCK *sb, DWORD *color) {
    if ((sb->render_state[D3DRENDERSTATE_ALPHATESTENABLE - 1] == TRUE) ||
	(sb->render_state[D3DRENDERSTATE_ALPHABLENDENABLE - 1] == TRUE)) {
        glColor4ub((*color >> 16) & 0xFF,
		   (*color >>  8) & 0xFF,
		   (*color >>  0) & 0xFF,
		   (*color >> 24) & 0xFF);
    } else {
        glColor3ub((*color >> 16) & 0xFF,
		   (*color >>  8) & 0xFF,
		   (*color >>  0) & 0xFF);    
    }
}

inline static void handle_specular_base(STATEBLOCK *sb, DWORD *color) {
    glColor4ub((*color >> 16) & 0xFF,
	       (*color >>  8) & 0xFF,
	       (*color >>  0) & 0xFF,
	       (*color >> 24) & 0xFF); /* No idea if the alpha field is really used.. */
}

inline static void handle_diffuse(STATEBLOCK *sb, DWORD *color, BOOLEAN lighted) {
    if ((lighted == FALSE) &&
	(sb->render_state[D3DRENDERSTATE_LIGHTING - 1] == TRUE) &&
	(sb->render_state[D3DRENDERSTATE_COLORVERTEX - 1] == TRUE)) {
        if (sb->render_state[D3DRENDERSTATE_DIFFUSEMATERIALSOURCE - 1] == D3DMCS_COLOR1) {
	    glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE);
	    handle_diffuse_base(sb, color);
	}
	if (sb->render_state[D3DRENDERSTATE_AMBIENTMATERIALSOURCE - 1] == D3DMCS_COLOR1) {
	    glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT);
	    handle_diffuse_base(sb, color);
	}
	if ((sb->render_state[D3DRENDERSTATE_SPECULARMATERIALSOURCE - 1] == D3DMCS_COLOR1) &&
	    (sb->render_state[D3DRENDERSTATE_SPECULARENABLE - 1] == TRUE)) {
	    glColorMaterial(GL_FRONT_AND_BACK, GL_SPECULAR);
	    handle_diffuse_base(sb, color);
	}
	if (sb->render_state[D3DRENDERSTATE_EMISSIVEMATERIALSOURCE - 1] == D3DMCS_COLOR1) {
	    glColorMaterial(GL_FRONT_AND_BACK, GL_EMISSION);
	    handle_diffuse_base(sb, color);
	}
    } else {
        handle_diffuse_base(sb, color);
    }    
}

inline static void handle_specular(STATEBLOCK *sb, DWORD *color, BOOLEAN lighted) {
    if ((lighted == FALSE) &&
	(sb->render_state[D3DRENDERSTATE_LIGHTING - 1] == TRUE) &&
	(sb->render_state[D3DRENDERSTATE_COLORVERTEX - 1] == TRUE)) {
        if (sb->render_state[D3DRENDERSTATE_DIFFUSEMATERIALSOURCE - 1] == D3DMCS_COLOR2) {
	    glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE);
	    handle_specular_base(sb, color);
	}
	if (sb->render_state[D3DRENDERSTATE_AMBIENTMATERIALSOURCE - 1] == D3DMCS_COLOR2) {
	    glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT);
	    handle_specular_base(sb, color);
	}
	if ((sb->render_state[D3DRENDERSTATE_SPECULARMATERIALSOURCE - 1] == D3DMCS_COLOR2) &&
	    (sb->render_state[D3DRENDERSTATE_SPECULARENABLE - 1] == TRUE)) {
	    glColorMaterial(GL_FRONT_AND_BACK, GL_SPECULAR);
	    handle_specular_base(sb, color);
	}
	if (sb->render_state[D3DRENDERSTATE_EMISSIVEMATERIALSOURCE - 1] == D3DMCS_COLOR2) {
	    glColorMaterial(GL_FRONT_AND_BACK, GL_EMISSION);
	    handle_specular_base(sb, color);
	}
    }
    /* No else here as we do not know how to handle 'specular' on its own in any case.. */
}

inline static void handle_diffuse_and_specular(STATEBLOCK *sb, BYTE *fog_table, DWORD *color_d, DWORD *color_s, BOOLEAN lighted) {
    if (lighted == TRUE) {
        DWORD color = *color_d;
        if (sb->render_state[D3DRENDERSTATE_FOGENABLE - 1] == TRUE) {
	    /* Special case where the specular value is used to do fogging */
	    BYTE fog_intensity = *color_s >> 24; /* The alpha value of the specular component is the fog 'intensity' for this vertex */
	    color &= 0xFF000000; /* Only keep the alpha component */
	    color |= fog_table[((*color_d >>  0) & 0xFF) << 8 | fog_intensity] <<  0;
	    color |= fog_table[((*color_d >>  8) & 0xFF) << 8 | fog_intensity] <<  8;
	    color |= fog_table[((*color_d >> 16) & 0xFF) << 8 | fog_intensity] << 16;
	}
	if (sb->render_state[D3DRENDERSTATE_SPECULARENABLE - 1] == TRUE) {
	    /* Standard specular value in transformed mode. TODO */
	}
	handle_diffuse_base(sb, &color);
    } else {
        if (sb->render_state[D3DRENDERSTATE_LIGHTING - 1] == TRUE) {
	    handle_diffuse(sb, color_d, FALSE);
	    handle_specular(sb, color_s, FALSE);
	} else {
	    /* In that case, only put the diffuse color... */
	    handle_diffuse_base(sb, color_d);
	}
    }
}

inline static void handle_texture(D3DVALUE *coords) {
    glTexCoord2fv(coords);
}
inline static void handle_textures(D3DVALUE *coords, int tex_stage) {
    /* For the moment, draw only the first texture.. */
    if (tex_stage == 0) glTexCoord2fv(coords);
}

static void draw_primitive_strided(IDirect3DDeviceImpl *This,
				   D3DPRIMITIVETYPE d3dptPrimitiveType,
				   DWORD d3dvtVertexType,
				   LPD3DDRAWPRIMITIVESTRIDEDDATA lpD3DDrawPrimStrideData,
				   DWORD dwVertexCount,
				   LPWORD dwIndices,
				   DWORD dwIndexCount,
				   DWORD dwFlags)
{
    BOOLEAN vertex_lighted = FALSE;
    IDirect3DDeviceGLImpl* glThis = (IDirect3DDeviceGLImpl*) This;
    int num_active_stages = 0;

    /* I put the trace before the various locks... So as to better understand where locks occur :-) */
    if (TRACE_ON(ddraw)) {
        TRACE(" Vertex format : "); dump_flexible_vertex(d3dvtVertexType);
    }

    /* This is to prevent 'thread contention' between a thread locking the device and another
       doing 3D display on it... */
    EnterCriticalSection(&(This->crit));   
    
    ENTER_GL();
    if (glThis->state[WINE_GL_BUFFER_BACK] == SURFACE_MEMORY_DIRTY) {
        This->flush_to_framebuffer(This, &(glThis->lock_rect[WINE_GL_BUFFER_BACK]), glThis->lock_surf[WINE_GL_BUFFER_BACK]);
    }

    glThis->state[WINE_GL_BUFFER_BACK] = SURFACE_GL;
    
    /* Just a hack for now.. Will have to find better algorithm :-/ */
    if ((d3dvtVertexType & D3DFVF_POSITION_MASK) != D3DFVF_XYZ) {
        vertex_lighted = TRUE;
    } else {
        if ((d3dvtVertexType & D3DFVF_NORMAL) == 0) glNormal3f(0.0, 0.0, 0.0);
    }
    
    /* Compute the number of active texture stages and set the various texture parameters */
    num_active_stages = draw_primitive_handle_textures(This);

    draw_primitive_handle_GL_state(This,
				   (d3dvtVertexType & D3DFVF_POSITION_MASK) != D3DFVF_XYZ,
				   vertex_lighted);
    draw_primitive_start_GL(d3dptPrimitiveType);

    /* Some fast paths first before the generic case.... */
    if ((d3dvtVertexType == D3DFVF_VERTEX) && (num_active_stages <= 1)) {
	int index;
	
	for (index = 0; index < dwIndexCount; index++) {
	    int i = (dwIndices == NULL) ? index : dwIndices[index];
	    D3DVALUE *normal = 
	      (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->normal.lpvData) + i * lpD3DDrawPrimStrideData->normal.dwStride);
	    D3DVALUE *tex_coord =
	      (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->textureCoords[0].lpvData) + i * lpD3DDrawPrimStrideData->textureCoords[0].dwStride);
	    D3DVALUE *position =
	      (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->position.lpvData) + i * lpD3DDrawPrimStrideData->position.dwStride);
	    
	    handle_normal(normal);
	    handle_texture(tex_coord);
	    handle_xyz(position);
	    
	    TRACE_(ddraw_geom)(" %f %f %f / %f %f %f (%f %f)\n",
			       position[0], position[1], position[2],
			       normal[0], normal[1], normal[2],
			       tex_coord[0], tex_coord[1]);
	}
    } else if ((d3dvtVertexType == D3DFVF_TLVERTEX) && (num_active_stages <= 1)) {
	int index;
	
	for (index = 0; index < dwIndexCount; index++) {
	    int i = (dwIndices == NULL) ? index : dwIndices[index];
	    DWORD *color_d = 
	      (DWORD *) (((char *) lpD3DDrawPrimStrideData->diffuse.lpvData) + i * lpD3DDrawPrimStrideData->diffuse.dwStride);
	    DWORD *color_s = 
	      (DWORD *) (((char *) lpD3DDrawPrimStrideData->specular.lpvData) + i * lpD3DDrawPrimStrideData->specular.dwStride);
	    D3DVALUE *tex_coord =
	      (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->textureCoords[0].lpvData) + i * lpD3DDrawPrimStrideData->textureCoords[0].dwStride);
	    D3DVALUE *position =
	      (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->position.lpvData) + i * lpD3DDrawPrimStrideData->position.dwStride);

	    handle_diffuse_and_specular(&(This->state_block), glThis->fog_table, color_d, color_s, TRUE);
	    handle_texture(tex_coord);
	    handle_xyzrhw(position);

	    TRACE_(ddraw_geom)(" %f %f %f %f / %02lx %02lx %02lx %02lx - %02lx %02lx %02lx %02lx (%f %f)\n",
			       position[0], position[1], position[2], position[3], 
			       (*color_d >> 16) & 0xFF,
			       (*color_d >>  8) & 0xFF,
			       (*color_d >>  0) & 0xFF,
			       (*color_d >> 24) & 0xFF,
			       (*color_s >> 16) & 0xFF,
			       (*color_s >>  8) & 0xFF,
			       (*color_s >>  0) & 0xFF,
			       (*color_s >> 24) & 0xFF,
			       tex_coord[0], tex_coord[1]);
	} 
    } else if (((d3dvtVertexType & D3DFVF_POSITION_MASK) == D3DFVF_XYZ) ||
	       ((d3dvtVertexType & D3DFVF_POSITION_MASK) == D3DFVF_XYZRHW)) {
        /* This is the 'slow path' but that should support all possible vertex formats out there...
	   Note that people should write a fast path for all vertex formats out there...
	*/  
	int index;
	int num_tex_index = ((d3dvtVertexType & D3DFVF_TEXCOUNT_MASK) >> D3DFVF_TEXCOUNT_SHIFT);
	static const D3DVALUE no_index[] = { 0.0, 0.0, 0.0, 0.0 };
	  
	for (index = 0; index < dwIndexCount; index++) {
	    int i = (dwIndices == NULL) ? index : dwIndices[index];
	    int tex_stage;

	    if (d3dvtVertexType & D3DFVF_NORMAL) { 
	        D3DVALUE *normal = 
		  (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->normal.lpvData) + i * lpD3DDrawPrimStrideData->normal.dwStride);	    
		handle_normal(normal);
	    }
	    if ((d3dvtVertexType & (D3DFVF_DIFFUSE|D3DFVF_SPECULAR)) == (D3DFVF_DIFFUSE|D3DFVF_SPECULAR)) {
	        DWORD *color_d = 
		  (DWORD *) (((char *) lpD3DDrawPrimStrideData->diffuse.lpvData) + i * lpD3DDrawPrimStrideData->diffuse.dwStride);
		DWORD *color_s = 
		  (DWORD *) (((char *) lpD3DDrawPrimStrideData->specular.lpvData) + i * lpD3DDrawPrimStrideData->specular.dwStride);
		handle_diffuse_and_specular(&(This->state_block), glThis->fog_table, color_d, color_s, vertex_lighted);
	    } else {
	        if (d3dvtVertexType & D3DFVF_SPECULAR) { 
		    DWORD *color_s = 
		      (DWORD *) (((char *) lpD3DDrawPrimStrideData->specular.lpvData) + i * lpD3DDrawPrimStrideData->specular.dwStride);
		    handle_specular(&(This->state_block), color_s, vertex_lighted);
		} else if (d3dvtVertexType & D3DFVF_DIFFUSE) {
		    DWORD *color_d = 
		      (DWORD *) (((char *) lpD3DDrawPrimStrideData->diffuse.lpvData) + i * lpD3DDrawPrimStrideData->diffuse.dwStride);
		    handle_diffuse(&(This->state_block), color_d, vertex_lighted);
		}
	    }

	    for (tex_stage = 0; tex_stage < num_active_stages; tex_stage++) {
	        int tex_index = This->state_block.texture_stage_state[tex_stage][D3DTSS_TEXCOORDINDEX - 1] & 0x0000FFFF;
		if (tex_index >= num_tex_index) {
		    handle_textures((D3DVALUE *) no_index, tex_stage);
		 } else {
		     D3DVALUE *tex_coord =
		       (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->textureCoords[tex_index].lpvData) + 
				     i * lpD3DDrawPrimStrideData->textureCoords[tex_index].dwStride);
		     handle_textures(tex_coord, tex_stage);
		}
	    }
	    
	    if ((d3dvtVertexType & D3DFVF_POSITION_MASK) == D3DFVF_XYZ) {
	        D3DVALUE *position =
		  (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->position.lpvData) + i * lpD3DDrawPrimStrideData->position.dwStride);
		handle_xyz(position);
	    } else if ((d3dvtVertexType & D3DFVF_POSITION_MASK) == D3DFVF_XYZRHW) {
	        D3DVALUE *position =
		  (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->position.lpvData) + i * lpD3DDrawPrimStrideData->position.dwStride);
		handle_xyzrhw(position);
	    }

	    if (TRACE_ON(ddraw_geom)) {
	        int tex_index;

		if ((d3dvtVertexType & D3DFVF_POSITION_MASK) == D3DFVF_XYZ) {
		    D3DVALUE *position =
		      (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->position.lpvData) + i * lpD3DDrawPrimStrideData->position.dwStride);
		    TRACE_(ddraw_geom)(" %f %f %f", position[0], position[1], position[2]);
		} else if ((d3dvtVertexType & D3DFVF_POSITION_MASK) == D3DFVF_XYZRHW) {
		    D3DVALUE *position =
		      (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->position.lpvData) + i * lpD3DDrawPrimStrideData->position.dwStride);
		    TRACE_(ddraw_geom)(" %f %f %f %f", position[0], position[1], position[2], position[3]);
		}
	        if (d3dvtVertexType & D3DFVF_NORMAL) { 
		    D3DVALUE *normal = 
		      (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->normal.lpvData) + i * lpD3DDrawPrimStrideData->normal.dwStride);	    
		    TRACE_(ddraw_geom)(" / %f %f %f", normal[0], normal[1], normal[2]);
		}
		if (d3dvtVertexType & D3DFVF_DIFFUSE) {
		    DWORD *color_d = 
		      (DWORD *) (((char *) lpD3DDrawPrimStrideData->diffuse.lpvData) + i * lpD3DDrawPrimStrideData->diffuse.dwStride);
		    TRACE_(ddraw_geom)(" / %02lx %02lx %02lx %02lx",
				       (*color_d >> 16) & 0xFF,
				       (*color_d >>  8) & 0xFF,
				       (*color_d >>  0) & 0xFF,
				       (*color_d >> 24) & 0xFF);
		}
	        if (d3dvtVertexType & D3DFVF_SPECULAR) { 
		    DWORD *color_s = 
		      (DWORD *) (((char *) lpD3DDrawPrimStrideData->specular.lpvData) + i * lpD3DDrawPrimStrideData->specular.dwStride);
		    TRACE_(ddraw_geom)(" / %02lx %02lx %02lx %02lx",
				       (*color_s >> 16) & 0xFF,
				       (*color_s >>  8) & 0xFF,
				       (*color_s >>  0) & 0xFF,
				       (*color_s >> 24) & 0xFF);
		}
		for (tex_index = 0; tex_index < ((d3dvtVertexType & D3DFVF_TEXCOUNT_MASK) >> D3DFVF_TEXCOUNT_SHIFT); tex_index++) {
                    D3DVALUE *tex_coord =
		      (D3DVALUE *) (((char *) lpD3DDrawPrimStrideData->textureCoords[tex_index].lpvData) + 
				    i * lpD3DDrawPrimStrideData->textureCoords[tex_index].dwStride);
		    TRACE_(ddraw_geom)(" / %f %f", tex_coord[0], tex_coord[1]);
		}
		TRACE_(ddraw_geom)("\n");
	    }
	}
    } else {
        ERR(" matrix weighting not handled yet....\n");
    }
    
    glEnd();

    /* Whatever the case, disable the color material stuff */
    glDisable(GL_COLOR_MATERIAL);

    LEAVE_GL();
    TRACE("End\n");    

    LeaveCriticalSection(&(This->crit));
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_DrawPrimitive(LPDIRECT3DDEVICE7 iface,
					  D3DPRIMITIVETYPE d3dptPrimitiveType,
					  DWORD d3dvtVertexType,
					  LPVOID lpvVertices,
					  DWORD dwVertexCount,
					  DWORD dwFlags)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    D3DDRAWPRIMITIVESTRIDEDDATA strided;

    TRACE("(%p/%p)->(%08x,%08lx,%p,%08lx,%08lx)\n", This, iface, d3dptPrimitiveType, d3dvtVertexType, lpvVertices, dwVertexCount, dwFlags);
    if (TRACE_ON(ddraw)) {
        TRACE(" - flags : "); dump_DPFLAGS(dwFlags);
    }

    convert_FVF_to_strided_data(d3dvtVertexType, lpvVertices, &strided, 0);
    draw_primitive_strided(This, d3dptPrimitiveType, d3dvtVertexType, &strided, dwVertexCount, NULL, dwVertexCount, dwFlags);
    
    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_DrawIndexedPrimitive(LPDIRECT3DDEVICE7 iface,
						 D3DPRIMITIVETYPE d3dptPrimitiveType,
						 DWORD d3dvtVertexType,
						 LPVOID lpvVertices,
						 DWORD dwVertexCount,
						 LPWORD dwIndices,
						 DWORD dwIndexCount,
						 DWORD dwFlags)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    D3DDRAWPRIMITIVESTRIDEDDATA strided;

    TRACE("(%p/%p)->(%08x,%08lx,%p,%08lx,%p,%08lx,%08lx)\n", This, iface, d3dptPrimitiveType, d3dvtVertexType, lpvVertices, dwVertexCount, dwIndices, dwIndexCount, dwFlags);
    if (TRACE_ON(ddraw)) {
        TRACE(" - flags : "); dump_DPFLAGS(dwFlags);
    }

    convert_FVF_to_strided_data(d3dvtVertexType, lpvVertices, &strided, 0);
    draw_primitive_strided(This, d3dptPrimitiveType, d3dvtVertexType, &strided, dwVertexCount, dwIndices, dwIndexCount, dwFlags);
    
    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_DrawPrimitiveStrided(LPDIRECT3DDEVICE7 iface,
                                                   D3DPRIMITIVETYPE d3dptPrimitiveType,
                                                   DWORD dwVertexType,
                                                   LPD3DDRAWPRIMITIVESTRIDEDDATA lpD3DDrawPrimStrideData,
                                                   DWORD dwVertexCount,
                                                   DWORD dwFlags)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);

    TRACE("(%p/%p)->(%08x,%08lx,%p,%08lx,%08lx)\n", This, iface, d3dptPrimitiveType, dwVertexType, lpD3DDrawPrimStrideData, dwVertexCount, dwFlags);
    if (TRACE_ON(ddraw)) {
        TRACE(" - flags : "); dump_DPFLAGS(dwFlags);
    }
    draw_primitive_strided(This, d3dptPrimitiveType, dwVertexType, lpD3DDrawPrimStrideData, dwVertexCount, NULL, dwVertexCount, dwFlags);

    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_DrawIndexedPrimitiveStrided(LPDIRECT3DDEVICE7 iface,
                                                          D3DPRIMITIVETYPE d3dptPrimitiveType,
                                                          DWORD dwVertexType,
                                                          LPD3DDRAWPRIMITIVESTRIDEDDATA lpD3DDrawPrimStrideData,
                                                          DWORD dwVertexCount,
                                                          LPWORD lpIndex,
                                                          DWORD dwIndexCount,
                                                          DWORD dwFlags)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);

    TRACE("(%p/%p)->(%08x,%08lx,%p,%08lx,%p,%08lx,%08lx)\n", This, iface, d3dptPrimitiveType, dwVertexType, lpD3DDrawPrimStrideData, dwVertexCount, lpIndex, dwIndexCount, dwFlags);
    if (TRACE_ON(ddraw)) {
        TRACE(" - flags : "); dump_DPFLAGS(dwFlags);
    }

    draw_primitive_strided(This, d3dptPrimitiveType, dwVertexType, lpD3DDrawPrimStrideData, dwVertexCount, lpIndex, dwIndexCount, dwFlags);

    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_DrawPrimitiveVB(LPDIRECT3DDEVICE7 iface,
					    D3DPRIMITIVETYPE d3dptPrimitiveType,
					    LPDIRECT3DVERTEXBUFFER7 lpD3DVertexBuf,
					    DWORD dwStartVertex,
					    DWORD dwNumVertices,
					    DWORD dwFlags)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    IDirect3DVertexBufferImpl *vb_impl = ICOM_OBJECT(IDirect3DVertexBufferImpl, IDirect3DVertexBuffer7, lpD3DVertexBuf);
    D3DDRAWPRIMITIVESTRIDEDDATA strided;

    TRACE("(%p/%p)->(%08x,%p,%08lx,%08lx,%08lx)\n", This, iface, d3dptPrimitiveType, lpD3DVertexBuf, dwStartVertex, dwNumVertices, dwFlags);
    if (TRACE_ON(ddraw)) {
        TRACE(" - flags : "); dump_DPFLAGS(dwFlags);
    }

    if (vb_impl->processed == TRUE) {
        IDirect3DVertexBufferGLImpl *vb_glimp = (IDirect3DVertexBufferGLImpl *) vb_impl;
	IDirect3DDeviceGLImpl *glThis = (IDirect3DDeviceGLImpl *) This;

	glThis->transform_state = GL_TRANSFORM_VERTEXBUFFER;
	This->set_matrices(This, VIEWMAT_CHANGED|WORLDMAT_CHANGED|PROJMAT_CHANGED,
			   &(vb_glimp->world_mat), &(vb_glimp->view_mat), &(vb_glimp->proj_mat));

	convert_FVF_to_strided_data(vb_glimp->dwVertexTypeDesc, vb_glimp->vertices, &strided, dwStartVertex);
	draw_primitive_strided(This, d3dptPrimitiveType, vb_glimp->dwVertexTypeDesc, &strided, dwNumVertices, NULL, dwNumVertices, dwFlags);

    } else {
        convert_FVF_to_strided_data(vb_impl->desc.dwFVF, vb_impl->vertices, &strided, dwStartVertex);
	draw_primitive_strided(This, d3dptPrimitiveType, vb_impl->desc.dwFVF, &strided, dwNumVertices, NULL, dwNumVertices, dwFlags);
    }

    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_DrawIndexedPrimitiveVB(LPDIRECT3DDEVICE7 iface,
						   D3DPRIMITIVETYPE d3dptPrimitiveType,
						   LPDIRECT3DVERTEXBUFFER7 lpD3DVertexBuf,
						   DWORD dwStartVertex,
						   DWORD dwNumVertices,
						   LPWORD lpwIndices,
						   DWORD dwIndexCount,
						   DWORD dwFlags)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    IDirect3DVertexBufferImpl *vb_impl = ICOM_OBJECT(IDirect3DVertexBufferImpl, IDirect3DVertexBuffer7, lpD3DVertexBuf);
    D3DDRAWPRIMITIVESTRIDEDDATA strided;
    
    TRACE("(%p/%p)->(%08x,%p,%08lx,%08lx,%p,%08lx,%08lx)\n", This, iface, d3dptPrimitiveType, lpD3DVertexBuf, dwStartVertex, dwNumVertices, lpwIndices, dwIndexCount, dwFlags);
    if (TRACE_ON(ddraw)) {
        TRACE(" - flags : "); dump_DPFLAGS(dwFlags);
    }

    if (vb_impl->processed == TRUE) {
        IDirect3DVertexBufferGLImpl *vb_glimp = (IDirect3DVertexBufferGLImpl *) vb_impl;
	IDirect3DDeviceGLImpl *glThis = (IDirect3DDeviceGLImpl *) This;

	glThis->transform_state = GL_TRANSFORM_VERTEXBUFFER;
	This->set_matrices(This, VIEWMAT_CHANGED|WORLDMAT_CHANGED|PROJMAT_CHANGED,
			   &(vb_glimp->world_mat), &(vb_glimp->view_mat), &(vb_glimp->proj_mat));

	convert_FVF_to_strided_data(vb_glimp->dwVertexTypeDesc, vb_glimp->vertices, &strided, dwStartVertex);
	draw_primitive_strided(This, d3dptPrimitiveType, vb_glimp->dwVertexTypeDesc, &strided, dwNumVertices, lpwIndices, dwIndexCount, dwFlags);

    } else {
        convert_FVF_to_strided_data(vb_impl->desc.dwFVF, vb_impl->vertices, &strided, dwStartVertex);
	draw_primitive_strided(This, d3dptPrimitiveType, vb_impl->desc.dwFVF, &strided, dwNumVertices, lpwIndices, dwIndexCount, dwFlags);
    }

    return DD_OK;
}

/* We need a static function for that to handle the 'special' case of 'SELECT_ARG2' */
static BOOLEAN
handle_color_alpha_args(IDirect3DDeviceImpl *This, DWORD dwStage, D3DTEXTURESTAGESTATETYPE d3dTexStageStateType, DWORD dwState, D3DTEXTUREOP tex_op)
{
    BOOLEAN is_complement = FALSE;
    BOOLEAN is_alpha_replicate = FALSE;
    BOOLEAN handled = TRUE;
    GLenum src;
    BOOLEAN is_color = ((d3dTexStageStateType == D3DTSS_COLORARG1) || (d3dTexStageStateType == D3DTSS_COLORARG2));
    int num;
    
    if (is_color) {
        if (d3dTexStageStateType == D3DTSS_COLORARG1) num = 0;
	else if (d3dTexStageStateType == D3DTSS_COLORARG2) num = 1;
	else {
	    handled = FALSE;
	    num = 0;
	}
	if (tex_op == D3DTOP_SELECTARG2) {
	    num = 1 - num;
	}
    } else {
        if (d3dTexStageStateType == D3DTSS_ALPHAARG1) num = 0;
	else if (d3dTexStageStateType == D3DTSS_ALPHAARG2) num = 1;
	else {
	    handled = FALSE;
	    num = 0;
	}
	if (tex_op == D3DTOP_SELECTARG2) {
	    num = 1 - num;
	}
    }
    
    if (dwState & D3DTA_COMPLEMENT) {
        is_complement = TRUE;
    }
    if (dwState & D3DTA_ALPHAREPLICATE) {
	is_alpha_replicate = TRUE;
    }
    dwState &= D3DTA_SELECTMASK;
    if ((dwStage == 0) && (dwState == D3DTA_CURRENT)) {
        dwState = D3DTA_DIFFUSE;
    }

    switch (dwState) {
        case D3DTA_CURRENT: src = GL_PREVIOUS_EXT; break;
	case D3DTA_DIFFUSE: src = GL_PRIMARY_COLOR_EXT; break;
	case D3DTA_TEXTURE: src = GL_TEXTURE; break;
	case D3DTA_TFACTOR: {
	    /* Get the constant value from the current rendering state */
	    GLfloat color[4];
	    DWORD col = This->state_block.render_state[D3DRENDERSTATE_TEXTUREFACTOR - 1];
	    
	    color[0] = ((col >> 16) & 0xFF) / 255.0f;
	    color[1] = ((col >>  8) & 0xFF) / 255.0f;
	    color[2] = ((col >>  0) & 0xFF) / 255.0f;
	    color[3] = ((col >> 24) & 0xFF) / 255.0f;
	    glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, color);
	    
	    src = GL_CONSTANT_EXT;
	} break;
	default: src = GL_TEXTURE; handled = FALSE; break;
    }

    if (is_color) {
        glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT + num, src);
	if (is_alpha_replicate) {
	    glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT + num, is_complement ? GL_ONE_MINUS_SRC_ALPHA : GL_SRC_ALPHA);
	} else {
	    glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT + num, is_complement ? GL_ONE_MINUS_SRC_COLOR : GL_SRC_COLOR);
	}
    } else {
        glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT + num, src);
	glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_EXT + num, is_complement ? GL_ONE_MINUS_SRC_ALPHA : GL_SRC_ALPHA);
    }

    return handled;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_SetTextureStageState(LPDIRECT3DDEVICE7 iface,
						 DWORD dwStage,
						 D3DTEXTURESTAGESTATETYPE d3dTexStageStateType,
						 DWORD dwState)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    IDirect3DDeviceGLImpl *glThis = (IDirect3DDeviceGLImpl *) This;
    const char *type;
    DWORD prev_state;
    
    TRACE("(%p/%p)->(%08lx,%08x,%08lx)\n", This, iface, dwStage, d3dTexStageStateType, dwState);

    if (dwStage > 0) return DD_OK; /* We nothing in this case for now */

    switch (d3dTexStageStateType) {
#define GEN_CASE(a) case a: type = #a; break
        GEN_CASE(D3DTSS_COLOROP);
	GEN_CASE(D3DTSS_COLORARG1);
	GEN_CASE(D3DTSS_COLORARG2);
	GEN_CASE(D3DTSS_ALPHAOP);
	GEN_CASE(D3DTSS_ALPHAARG1);
	GEN_CASE(D3DTSS_ALPHAARG2);
	GEN_CASE(D3DTSS_BUMPENVMAT00);
	GEN_CASE(D3DTSS_BUMPENVMAT01);
	GEN_CASE(D3DTSS_BUMPENVMAT10);
	GEN_CASE(D3DTSS_BUMPENVMAT11);
	GEN_CASE(D3DTSS_TEXCOORDINDEX);
	GEN_CASE(D3DTSS_ADDRESS);
	GEN_CASE(D3DTSS_ADDRESSU);
	GEN_CASE(D3DTSS_ADDRESSV);
	GEN_CASE(D3DTSS_BORDERCOLOR);
	GEN_CASE(D3DTSS_MAGFILTER);
	GEN_CASE(D3DTSS_MINFILTER);
	GEN_CASE(D3DTSS_MIPFILTER);
	GEN_CASE(D3DTSS_MIPMAPLODBIAS);
	GEN_CASE(D3DTSS_MAXMIPLEVEL);
	GEN_CASE(D3DTSS_MAXANISOTROPY);
	GEN_CASE(D3DTSS_BUMPENVLSCALE);
	GEN_CASE(D3DTSS_BUMPENVLOFFSET);
	GEN_CASE(D3DTSS_TEXTURETRANSFORMFLAGS);
#undef GEN_CASE
        default: type = "UNKNOWN";
    }

    /* Store the values in the state array */
    prev_state = This->state_block.texture_stage_state[dwStage][d3dTexStageStateType - 1];
    This->state_block.texture_stage_state[dwStage][d3dTexStageStateType - 1] = dwState;
    /* Some special cases when one state modifies more than one... */
    if (d3dTexStageStateType == D3DTSS_ADDRESS) {
        This->state_block.texture_stage_state[dwStage][D3DTSS_ADDRESSU - 1] = dwState;
	This->state_block.texture_stage_state[dwStage][D3DTSS_ADDRESSV - 1] = dwState;
    }

    ENTER_GL();
    
    switch (d3dTexStageStateType) {
        case D3DTSS_MINFILTER:
        case D3DTSS_MIPFILTER:
	    if (TRACE_ON(ddraw)) {
	        if (d3dTexStageStateType == D3DTSS_MINFILTER) {
		    switch ((D3DTEXTUREMINFILTER) dwState) {
	                case D3DTFN_POINT:  TRACE(" Stage type is : D3DTSS_MINFILTER => D3DTFN_POINT\n"); break;
			case D3DTFN_LINEAR: TRACE(" Stage type is : D3DTSS_MINFILTER => D3DTFN_LINEAR\n"); break;
			default: FIXME(" Unhandled stage type : D3DTSS_MINFILTER => %08lx\n", dwState); break;
		    }
		} else {
		    switch ((D3DTEXTUREMIPFILTER) dwState) {
	                case D3DTFP_NONE:   TRACE(" Stage type is : D3DTSS_MIPFILTER => D3DTFP_NONE\n"); break;
			case D3DTFP_POINT:  TRACE(" Stage type is : D3DTSS_MIPFILTER => D3DTFP_POINT\n"); break;
			case D3DTFP_LINEAR: TRACE(" Stage type is : D3DTSS_MIPFILTER => D3DTFP_LINEAR\n"); break;
			default: FIXME(" Unhandled stage type : D3DTSS_MIPFILTER => %08lx\n", dwState); break;
		    }
		}
	    }
	    break;
	    
        case D3DTSS_MAGFILTER:
	    if (TRACE_ON(ddraw)) {
	        switch ((D3DTEXTUREMAGFILTER) dwState) {
	            case D3DTFG_POINT:  TRACE(" Stage type is : D3DTSS_MAGFILTER => D3DTFG_POINT\n"); break;
		    case D3DTFG_LINEAR: TRACE(" Stage type is : D3DTSS_MAGFILTER => D3DTFG_LINEAR\n"); break;
		    default: FIXME(" Unhandled stage type : D3DTSS_MAGFILTER => %08lx\n", dwState); break;
		}
	    }
            break;

        case D3DTSS_ADDRESS:
        case D3DTSS_ADDRESSU:
        case D3DTSS_ADDRESSV: {
	    switch ((D3DTEXTUREADDRESS) dwState) {
	        case D3DTADDRESS_WRAP:   TRACE(" Stage type is : %s => D3DTADDRESS_WRAP\n", type); break;
	        case D3DTADDRESS_CLAMP:  TRACE(" Stage type is : %s => D3DTADDRESS_CLAMP\n", type); break;
	        case D3DTADDRESS_BORDER: TRACE(" Stage type is : %s => D3DTADDRESS_BORDER\n", type); break;
		case D3DTADDRESS_MIRROR:
		    if (GL_extensions.mirrored_repeat == TRUE) {
			TRACE(" Stage type is : %s => D3DTADDRESS_MIRROR\n", type);
		    } else {
			FIXME(" Stage type is : %s => D3DTADDRESS_MIRROR - not supported by GL !\n", type);
		    }
		    break;
	        default: FIXME(" Unhandled stage type : %s => %08lx\n", type, dwState); break;
	    }
        } break;

	case D3DTSS_ALPHAOP:
	case D3DTSS_COLOROP: {
            int scale = 1;
            GLenum parm = (d3dTexStageStateType == D3DTSS_ALPHAOP) ? GL_COMBINE_ALPHA_EXT : GL_COMBINE_RGB_EXT;
	    const char *value;
	    int handled = 1;
	    
	    switch (dwState) {
#define GEN_CASE(a) case a: value = #a; break
	        GEN_CASE(D3DTOP_DISABLE);
		GEN_CASE(D3DTOP_SELECTARG1);
		GEN_CASE(D3DTOP_SELECTARG2);
		GEN_CASE(D3DTOP_MODULATE);
		GEN_CASE(D3DTOP_MODULATE2X);
		GEN_CASE(D3DTOP_MODULATE4X);
		GEN_CASE(D3DTOP_ADD);
		GEN_CASE(D3DTOP_ADDSIGNED);
		GEN_CASE(D3DTOP_ADDSIGNED2X);
		GEN_CASE(D3DTOP_SUBTRACT);
		GEN_CASE(D3DTOP_ADDSMOOTH);
		GEN_CASE(D3DTOP_BLENDDIFFUSEALPHA);
		GEN_CASE(D3DTOP_BLENDTEXTUREALPHA);
		GEN_CASE(D3DTOP_BLENDFACTORALPHA);
		GEN_CASE(D3DTOP_BLENDTEXTUREALPHAPM);
		GEN_CASE(D3DTOP_BLENDCURRENTALPHA);
		GEN_CASE(D3DTOP_PREMODULATE);
		GEN_CASE(D3DTOP_MODULATEALPHA_ADDCOLOR);
		GEN_CASE(D3DTOP_MODULATECOLOR_ADDALPHA);
		GEN_CASE(D3DTOP_MODULATEINVALPHA_ADDCOLOR);
		GEN_CASE(D3DTOP_MODULATEINVCOLOR_ADDALPHA);
		GEN_CASE(D3DTOP_BUMPENVMAP);
		GEN_CASE(D3DTOP_BUMPENVMAPLUMINANCE);
		GEN_CASE(D3DTOP_DOTPRODUCT3);
		GEN_CASE(D3DTOP_FORCE_DWORD);
#undef GEN_CASE
	        default: value = "UNKNOWN";
	    }

            if ((d3dTexStageStateType == D3DTSS_COLOROP) && (dwState == D3DTOP_DISABLE) && (dwStage == 0)) {
                glDisable(GL_TEXTURE_2D);
		TRACE(" disabling 2D texturing.\n");
            } else {
	        /* Re-enable texturing */
	        if ((dwStage == 0) && (This->current_texture[0] != NULL)) {
		    glEnable(GL_TEXTURE_2D);
		    TRACE(" enabling 2D texturing.\n");
		}
		
                /* Re-Enable GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT */
                if (dwState != D3DTOP_DISABLE) {
		    if (glThis->current_tex_env != GL_COMBINE_EXT) {
			glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT);
			glThis->current_tex_env = GL_COMBINE_EXT;
		    }
                }

                /* Now set up the operand correctly */
                switch (dwState) {
                    case D3DTOP_DISABLE:
		        /* Contrary to the docs, alpha can be disabled when colorop is enabled
			   and it works, so ignore this op */
		        TRACE(" Note : disable ALPHAOP but COLOROP enabled!\n");
			break;

		    case D3DTOP_SELECTARG1:
		    case D3DTOP_SELECTARG2:
			glTexEnvi(GL_TEXTURE_ENV, parm, GL_REPLACE);
			break;
			
		    case D3DTOP_MODULATE4X:
			scale = scale * 2;  /* Drop through */
		    case D3DTOP_MODULATE2X:
			scale = scale * 2;  /* Drop through */
		    case D3DTOP_MODULATE:
			glTexEnvi(GL_TEXTURE_ENV, parm, GL_MODULATE);
			break;

		    case D3DTOP_ADD:
			glTexEnvi(GL_TEXTURE_ENV, parm, GL_ADD);
			break;

		    case D3DTOP_ADDSIGNED2X:
			scale = scale * 2;  /* Drop through */
		    case D3DTOP_ADDSIGNED:
			glTexEnvi(GL_TEXTURE_ENV, parm, GL_ADD_SIGNED_EXT);
			break;

			/* For the four blending modes, use the Arg2 parameter */
		    case D3DTOP_BLENDDIFFUSEALPHA:
		    case D3DTOP_BLENDTEXTUREALPHA:
		    case D3DTOP_BLENDFACTORALPHA:
		    case D3DTOP_BLENDCURRENTALPHA: {
		        GLenum src = GL_PRIMARY_COLOR_EXT; /* Just to prevent a compiler warning.. */

			switch (dwState) {
			    case D3DTOP_BLENDDIFFUSEALPHA: src = GL_PRIMARY_COLOR_EXT;
			    case D3DTOP_BLENDTEXTUREALPHA: src = GL_TEXTURE;
			    case D3DTOP_BLENDFACTORALPHA:  src = GL_CONSTANT_EXT;
			    case D3DTOP_BLENDCURRENTALPHA: src = GL_PREVIOUS_EXT;
			}
			
			glTexEnvi(GL_TEXTURE_ENV, parm, GL_INTERPOLATE_EXT);
			glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE2_RGB_EXT, src);
			glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND2_RGB_EXT, GL_SRC_ALPHA);
			glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE2_ALPHA_EXT, src);
			glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND2_ALPHA_EXT, GL_SRC_ALPHA);
		    } break;
			
		    default:
			handled = FALSE;
			break;
                }
            }

	    if (((prev_state == D3DTOP_SELECTARG2) && (dwState != D3DTOP_SELECTARG2)) ||
		((dwState == D3DTOP_SELECTARG2) && (prev_state != D3DTOP_SELECTARG2))) {
	        /* Switch the arguments if needed... */
	        if (d3dTexStageStateType == D3DTSS_COLOROP) {
		    handle_color_alpha_args(This, dwStage, D3DTSS_COLORARG1,
					    This->state_block.texture_stage_state[dwStage][D3DTSS_COLORARG1 - 1],
					    dwState);
		    handle_color_alpha_args(This, dwStage, D3DTSS_COLORARG2,
					    This->state_block.texture_stage_state[dwStage][D3DTSS_COLORARG2 - 1],
					    dwState);
		} else {
		    handle_color_alpha_args(This, dwStage, D3DTSS_ALPHAARG1,
					    This->state_block.texture_stage_state[dwStage][D3DTSS_ALPHAARG1 - 1],
					    dwState);
		    handle_color_alpha_args(This, dwStage, D3DTSS_ALPHAARG2,
					    This->state_block.texture_stage_state[dwStage][D3DTSS_ALPHAARG2 - 1],
					    dwState);
		}
	    }
	    
	    if (handled) {
	        if (d3dTexStageStateType == D3DTSS_ALPHAOP) {
		    glTexEnvi(GL_TEXTURE_ENV, GL_ALPHA_SCALE, scale);
		} else {
		    glTexEnvi(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, scale);
		}			
		TRACE(" Stage type is : %s => %s\n", type, value);
	    } else {
	        FIXME(" Unhandled stage type is : %s => %s\n", type, value);
	    }
        } break;

	case D3DTSS_COLORARG1:
	case D3DTSS_COLORARG2:
	case D3DTSS_ALPHAARG1:
	case D3DTSS_ALPHAARG2: {
	    const char *value, *value_comp = "", *value_alpha = "";
	    BOOLEAN handled;
	    D3DTEXTUREOP tex_op;
	    
	    switch (dwState & D3DTA_SELECTMASK) {
#define GEN_CASE(a) case a: value = #a; break
	        GEN_CASE(D3DTA_DIFFUSE);
		GEN_CASE(D3DTA_CURRENT);
		GEN_CASE(D3DTA_TEXTURE);
		GEN_CASE(D3DTA_TFACTOR);
	        GEN_CASE(D3DTA_SPECULAR);
#undef GEN_CASE
	        default: value = "UNKNOWN";
	    }
	    if (dwState & D3DTA_COMPLEMENT) {
	        value_comp = " | D3DTA_COMPLEMENT";
	    }
	    if (dwState & D3DTA_ALPHAREPLICATE) {
	        value_alpha = " | D3DTA_ALPHAREPLICATE";
	    }

	    if ((d3dTexStageStateType == D3DTSS_COLORARG1) || (d3dTexStageStateType == D3DTSS_COLORARG2)) {
	        tex_op = This->state_block.texture_stage_state[dwStage][D3DTSS_COLOROP - 1];
	    } else {
	        tex_op = This->state_block.texture_stage_state[dwStage][D3DTSS_ALPHAOP - 1];
	    }
	    
	    handled = handle_color_alpha_args(This, dwStage, d3dTexStageStateType, dwState, tex_op);
	    
	    if (handled) {
	        TRACE(" Stage type : %s => %s%s%s\n", type, value, value_comp, value_alpha);
	    } else {
	        FIXME(" Unhandled stage type : %s => %s%s%s\n", type, value, value_comp, value_alpha);
	    }
	} break;

	case D3DTSS_MIPMAPLODBIAS: {
	    D3DVALUE value = *((D3DVALUE *) &dwState);
	    BOOLEAN handled = TRUE;
	    
	    if ((value != 0.0) && (GL_extensions.mipmap_lodbias == FALSE))
	        handled = FALSE;

	    if (handled) {
	        TRACE(" Stage type : D3DTSS_MIPMAPLODBIAS => %f\n", value);
		glTexEnvf(GL_TEXTURE_FILTER_CONTROL_WINE, GL_TEXTURE_LOD_BIAS_WINE, value);
	    } else {
	        FIXME(" Unhandled stage type : D3DTSS_MIPMAPLODBIAS => %f\n", value);
	    }
	} break;

	case D3DTSS_MAXMIPLEVEL: 
	    TRACE(" Stage type : D3DTSS_MAXMIPLEVEL => %ld\n", dwState);
	    break;

	case D3DTSS_BORDERCOLOR:
	    TRACE(" Stage type : D3DTSS_BORDERCOLOR => %02lx %02lx %02lx %02lx (RGBA)\n",
		  ((dwState >> 16) & 0xFF),
		  ((dwState >>  8) & 0xFF),
		  ((dwState >>  0) & 0xFF),
		  ((dwState >> 24) & 0xFF));
	    break;
	    
	case D3DTSS_TEXCOORDINDEX: {
	    BOOLEAN handled = TRUE;
	    const char *value;
	    
	    switch (dwState & 0xFFFF0000) {
#define GEN_CASE(a) case a: value = #a; break
	        GEN_CASE(D3DTSS_TCI_PASSTHRU);
		GEN_CASE(D3DTSS_TCI_CAMERASPACENORMAL);
		GEN_CASE(D3DTSS_TCI_CAMERASPACEPOSITION);
		GEN_CASE(D3DTSS_TCI_CAMERASPACEREFLECTIONVECTOR);
#undef GEN_CASE
		default: value = "UNKNOWN";
	    }
	    if ((dwState & 0xFFFF0000) != D3DTSS_TCI_PASSTHRU)
	        handled = FALSE;

	    if (handled) {
	        TRACE(" Stage type : D3DTSS_TEXCOORDINDEX => %ld | %s\n", dwState & 0x0000FFFF, value);
	    } else {
	        FIXME(" Unhandled stage type : D3DTSS_TEXCOORDINDEX => %ld | %s\n", dwState & 0x0000FFFF, value);
	    }
	} break;
	    
	case D3DTSS_TEXTURETRANSFORMFLAGS: {
	    const char *projected = "", *value;
	    BOOLEAN handled = TRUE;
	    switch (dwState & 0xFF) {
#define GEN_CASE(a) case a: value = #a; break
	        GEN_CASE(D3DTTFF_DISABLE);
		GEN_CASE(D3DTTFF_COUNT1);
		GEN_CASE(D3DTTFF_COUNT2);
		GEN_CASE(D3DTTFF_COUNT3);
		GEN_CASE(D3DTTFF_COUNT4);
#undef GEN_CASE
		default: value = "UNKNOWN";
	    }
	    if (dwState & D3DTTFF_PROJECTED) {
	        projected = " | D3DTTFF_PROJECTED";
		handled = FALSE;
	    }

	    if ((dwState & 0xFF) != D3DTTFF_DISABLE) {
	        This->matrices_updated(This, TEXMAT0_CHANGED << dwStage);
	    }

	    if (handled == TRUE) {
	        TRACE(" Stage type : D3DTSS_TEXTURETRANSFORMFLAGS => %s%s\n", value, projected);
	    } else {
	        FIXME(" Unhandled stage type : D3DTSS_TEXTURETRANSFORMFLAGS => %s%s\n", value, projected);
	    }
	} break;
	    
	default:
	    FIXME(" Unhandled stage type : %s => %08lx\n", type, dwState);
	    break;
    }

    LEAVE_GL();
    
    return DD_OK;
}

static DWORD
draw_primitive_handle_textures(IDirect3DDeviceImpl *This)
{
    IDirect3DDeviceGLImpl *glThis = (IDirect3DDeviceGLImpl *) This;
    DWORD stage;
    
    for (stage = 0; stage < MAX_TEXTURES; stage++) {
	IDirectDrawSurfaceImpl *surf_ptr = This->current_texture[stage];

	/* First check if we need to bind any other texture for this stage */
	if (This->current_texture[stage] != glThis->current_bound_texture[stage]) {
	    if (This->current_texture[stage] == NULL) {
		TRACE(" disabling 2D texturing for stage %ld.\n", stage);
		glBindTexture(GL_TEXTURE_2D, 0);
		glDisable(GL_TEXTURE_2D);
	    } else {
		GLenum tex_name = ((IDirect3DTextureGLImpl *) surf_ptr->tex_private)->tex_name;
		
		if (glThis->current_bound_texture[stage] == NULL) {
		    if (This->state_block.texture_stage_state[stage][D3DTSS_COLOROP - 1] != D3DTOP_DISABLE) {
			TRACE(" enabling 2D texturing and");
			glEnable(GL_TEXTURE_2D);
		    }
		}
		TRACE(" activating OpenGL texture id %d for stage %ld.\n", tex_name, stage);
		glBindTexture(GL_TEXTURE_2D, tex_name);
	    }

	    glThis->current_bound_texture[stage] = This->current_texture[stage];
	} else {
	    if (glThis->current_bound_texture[stage] == NULL) {
		TRACE(" displaying without texturing activated for stage %ld.\n", stage);
	    } else {
		TRACE(" using already bound texture id %d for stage %ld.\n",
		      ((IDirect3DTextureGLImpl *) (glThis->current_bound_texture[stage])->tex_private)->tex_name, stage);
	    }
	}

	/* If no texure valid for this stage, go out of the loop */
	if (This->current_texture[stage] == NULL) break;

	/* Then check if we need to flush this texture to GL or not (ie did it change) ?.
	   This will also update the various texture parameters if needed.
	*/
	gltex_upload_texture(surf_ptr, This, stage);
    }

    return stage;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_3T_SetTexture(LPDIRECT3DDEVICE7 iface,
				       DWORD dwStage,
				       LPDIRECTDRAWSURFACE7 lpTexture2)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    
    TRACE("(%p/%p)->(%08lx,%p)\n", This, iface, dwStage, lpTexture2);
    
    if (dwStage > 0) return DD_OK;

    if (This->current_texture[dwStage] != NULL) {
	IDirectDrawSurface7_Release(ICOM_INTERFACE(This->current_texture[dwStage], IDirectDrawSurface7));
    }
    
    if (lpTexture2 == NULL) {
	This->current_texture[dwStage] = NULL;
    } else {
        IDirectDrawSurfaceImpl *tex_impl = ICOM_OBJECT(IDirectDrawSurfaceImpl, IDirectDrawSurface7, lpTexture2);
	IDirectDrawSurface7_AddRef(ICOM_INTERFACE(tex_impl, IDirectDrawSurface7));
	This->current_texture[dwStage] = tex_impl;
    }
    
    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_GetCaps(LPDIRECT3DDEVICE7 iface,
				 LPD3DDEVICEDESC7 lpD3DHELDevDesc)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    TRACE("(%p/%p)->(%p)\n", This, iface, lpD3DHELDevDesc);

    fill_opengl_caps_7(lpD3DHELDevDesc);

    TRACE(" returning caps : no dump function yet.\n");

    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_SetMaterial(LPDIRECT3DDEVICE7 iface,
				     LPD3DMATERIAL7 lpMat)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    TRACE("(%p/%p)->(%p)\n", This, iface, lpMat);
    
    if (TRACE_ON(ddraw)) {
        TRACE(" material is : \n");
	dump_D3DMATERIAL7(lpMat);
    }
    
    This->current_material = *lpMat;

    ENTER_GL();
    glMaterialfv(GL_FRONT_AND_BACK,
		 GL_DIFFUSE,
		 (float *) &(This->current_material.u.diffuse));
    glMaterialfv(GL_FRONT_AND_BACK,
		 GL_AMBIENT,
		 (float *) &(This->current_material.u1.ambient));
    glMaterialfv(GL_FRONT_AND_BACK,
		 GL_SPECULAR,
		 (float *) &(This->current_material.u2.specular));
    glMaterialfv(GL_FRONT_AND_BACK,
		 GL_EMISSION,
		 (float *) &(This->current_material.u3.emissive));
    glMaterialf(GL_FRONT_AND_BACK,
		GL_SHININESS,
		This->current_material.u4.power); /* Not sure about this... */
    LEAVE_GL();

    return DD_OK;
}


HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_SetLight(LPDIRECT3DDEVICE7 iface,
				  DWORD dwLightIndex,
				  LPD3DLIGHT7 lpLight)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    IDirect3DDeviceGLImpl *glThis = (IDirect3DDeviceGLImpl *) This;
    TRACE("(%p/%p)->(%08lx,%p)\n", This, iface, dwLightIndex, lpLight);
    
    if (TRACE_ON(ddraw)) {
        TRACE(" setting light : \n");
	dump_D3DLIGHT7(lpLight);
    }
    
    if (dwLightIndex >= MAX_LIGHTS) return DDERR_INVALIDPARAMS;
    This->set_lights |= 0x00000001 << dwLightIndex;
    This->light_parameters[dwLightIndex] = *lpLight;

    /* Some checks to print out nice warnings :-) */
    switch (lpLight->dltType) {
        case D3DLIGHT_DIRECTIONAL:
        case D3DLIGHT_POINT:
            /* These are handled properly... */
            break;
	    
        case D3DLIGHT_SPOT:
            if ((lpLight->dvTheta != 0.0) ||
		(lpLight->dvTheta != lpLight->dvPhi)) {
	        ERR("dvTheta not fully supported yet !\n");
	    }
	    break;

	default:
	    ERR("Light type not handled yet : %08x !\n", lpLight->dltType);
    }
    
    /* This will force the Light setting on next drawing of primitives */
    glThis->transform_state = GL_TRANSFORM_NONE;
    
    return DD_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_LightEnable(LPDIRECT3DDEVICE7 iface,
				     DWORD dwLightIndex,
				     BOOL bEnable)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    TRACE("(%p/%p)->(%08lx,%d)\n", This, iface, dwLightIndex, bEnable);
    
    if (dwLightIndex >= MAX_LIGHTS) return DDERR_INVALIDPARAMS;

    ENTER_GL();
    if (bEnable) {
        if (((0x00000001 << dwLightIndex) & This->set_lights) == 0) {
	    /* Set the default parameters.. */
	    TRACE(" setting default light parameters...\n");
	    GL_IDirect3DDeviceImpl_7_SetLight(iface, dwLightIndex, &(This->light_parameters[dwLightIndex]));
	}
	glEnable(GL_LIGHT0 + dwLightIndex);
	if ((This->active_lights & (0x00000001 << dwLightIndex)) == 0) {
	    /* This light gets active... Need to update its parameters to GL before the next drawing */
	    IDirect3DDeviceGLImpl *glThis = (IDirect3DDeviceGLImpl *) This;
	    
	    This->active_lights |= 0x00000001 << dwLightIndex;
	    glThis->transform_state = GL_TRANSFORM_NONE;
	}
    } else {
        glDisable(GL_LIGHT0 + dwLightIndex);
	This->active_lights &= ~(0x00000001 << dwLightIndex);
    }
    LEAVE_GL();

    return DD_OK;
}

HRESULT  WINAPI  
GL_IDirect3DDeviceImpl_7_SetClipPlane(LPDIRECT3DDEVICE7 iface, DWORD dwIndex, CONST D3DVALUE* pPlaneEquation) 
{
    ICOM_THIS(IDirect3DDeviceImpl,iface);
    IDirect3DDeviceGLImpl* glThis = (IDirect3DDeviceGLImpl*) This;

    TRACE("(%p)->(%ld,%p)\n", This, dwIndex, pPlaneEquation);

    if (dwIndex >= This->max_clipping_planes) {
	return DDERR_INVALIDPARAMS;
    }

    TRACE(" clip plane %ld : %f %f %f %f\n", dwIndex, pPlaneEquation[0], pPlaneEquation[1], pPlaneEquation[2], pPlaneEquation[3] );

    memcpy(This->clipping_planes[dwIndex].plane, pPlaneEquation, sizeof(D3DVALUE[4]));
    
    /* This is to force the reset of the transformation matrices on the next drawing.
     * This is needed to use the correct matrices for the various clipping planes.
     */
    glThis->transform_state = GL_TRANSFORM_NONE;
    
    return D3D_OK;
}

HRESULT WINAPI
GL_IDirect3DDeviceImpl_7_SetViewport(LPDIRECT3DDEVICE7 iface,
				     LPD3DVIEWPORT7 lpData)
{
    ICOM_THIS_FROM(IDirect3DDeviceImpl, IDirect3DDevice7, iface);
    TRACE("(%p/%p)->(%p)\n", This, iface, lpData);

    if (TRACE_ON(ddraw)) {
        TRACE(" viewport is : \n");
	TRACE("    - dwX = %ld   dwY = %ld\n",
	      lpData->dwX, lpData->dwY);
	TRACE("    - dwWidth = %ld   dwHeight = %ld\n",
	      lpData->dwWidth, lpData->dwHeight);
	TRACE("    - dvMinZ = %f   dvMaxZ = %f\n",
	      lpData->dvMinZ, lpData->dvMaxZ);
    }
    ENTER_GL();
    
    /* Set the viewport */
    if ((lpData->dvMinZ != This->active_viewport.dvMinZ) ||
	(lpData->dvMaxZ != This->active_viewport.dvMaxZ)) {
	glDepthRange(lpData->dvMinZ, lpData->dvMaxZ);
    }
    if ((lpData->dwX != This->active_viewport.dwX) ||
	(lpData->dwY != This->active_viewport.dwY) ||
	(lpData->dwWidth != This->active_viewport.dwWidth) ||
	(lpData->dwHeight != This->active_viewport.dwHeight)) {
	glViewport(lpData->dwX,
		   This->surface->surface_desc.dwHeight - (lpData->dwHeight + lpData->dwY),
		   lpData->dwWidth, lpData->dwHeight);
    }

    LEAVE_GL();

    This->active_viewport = *lpData;
    
    return DD_OK;
}

#if !defined(__STRICT_ANSI__) && defined(__GNUC__)
# define XCAST(fun)     (typeof(VTABLE_IDirect3DDevice7.fun))
#else
# define XCAST(fun)     (void*)
#endif

ICOM_VTABLE(IDirect3DDevice7) VTABLE_IDirect3DDevice7 =
{
    ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
    XCAST(QueryInterface) Main_IDirect3DDeviceImpl_7_3T_2T_1T_QueryInterface,
    XCAST(AddRef) Main_IDirect3DDeviceImpl_7_3T_2T_1T_AddRef,
    XCAST(Release) GL_IDirect3DDeviceImpl_7_3T_2T_1T_Release,
    XCAST(GetCaps) GL_IDirect3DDeviceImpl_7_GetCaps,
    XCAST(EnumTextureFormats) GL_IDirect3DDeviceImpl_7_3T_EnumTextureFormats,
    XCAST(BeginScene) Main_IDirect3DDeviceImpl_7_3T_2T_1T_BeginScene,
    XCAST(EndScene) Main_IDirect3DDeviceImpl_7_3T_2T_1T_EndScene,
    XCAST(GetDirect3D) Main_IDirect3DDeviceImpl_7_3T_2T_1T_GetDirect3D,
    XCAST(SetRenderTarget) Main_IDirect3DDeviceImpl_7_3T_2T_SetRenderTarget,
    XCAST(GetRenderTarget) Main_IDirect3DDeviceImpl_7_3T_2T_GetRenderTarget,
    XCAST(Clear) Main_IDirect3DDeviceImpl_7_Clear,
    XCAST(SetTransform) Main_IDirect3DDeviceImpl_7_3T_2T_SetTransform,
    XCAST(GetTransform) Main_IDirect3DDeviceImpl_7_3T_2T_GetTransform,
    XCAST(SetViewport) GL_IDirect3DDeviceImpl_7_SetViewport,
    XCAST(MultiplyTransform) Main_IDirect3DDeviceImpl_7_3T_2T_MultiplyTransform,
    XCAST(GetViewport) Main_IDirect3DDeviceImpl_7_GetViewport,
    XCAST(SetMaterial) GL_IDirect3DDeviceImpl_7_SetMaterial,
    XCAST(GetMaterial) Main_IDirect3DDeviceImpl_7_GetMaterial,
    XCAST(SetLight) GL_IDirect3DDeviceImpl_7_SetLight,
    XCAST(GetLight) Main_IDirect3DDeviceImpl_7_GetLight,
    XCAST(SetRenderState) GL_IDirect3DDeviceImpl_7_3T_2T_SetRenderState,
    XCAST(GetRenderState) GL_IDirect3DDeviceImpl_7_3T_2T_GetRenderState,
    XCAST(BeginStateBlock) Main_IDirect3DDeviceImpl_7_BeginStateBlock,
    XCAST(EndStateBlock) Main_IDirect3DDeviceImpl_7_EndStateBlock,
    XCAST(PreLoad) Main_IDirect3DDeviceImpl_7_PreLoad,
    XCAST(DrawPrimitive) GL_IDirect3DDeviceImpl_7_3T_DrawPrimitive,
    XCAST(DrawIndexedPrimitive) GL_IDirect3DDeviceImpl_7_3T_DrawIndexedPrimitive,
    XCAST(SetClipStatus) Main_IDirect3DDeviceImpl_7_3T_2T_SetClipStatus,
    XCAST(GetClipStatus) Main_IDirect3DDeviceImpl_7_3T_2T_GetClipStatus,
    XCAST(DrawPrimitiveStrided) GL_IDirect3DDeviceImpl_7_3T_DrawPrimitiveStrided,
    XCAST(DrawIndexedPrimitiveStrided) GL_IDirect3DDeviceImpl_7_3T_DrawIndexedPrimitiveStrided,
    XCAST(DrawPrimitiveVB) GL_IDirect3DDeviceImpl_7_3T_DrawPrimitiveVB,
    XCAST(DrawIndexedPrimitiveVB) GL_IDirect3DDeviceImpl_7_3T_DrawIndexedPrimitiveVB,
    XCAST(ComputeSphereVisibility) Main_IDirect3DDeviceImpl_7_3T_ComputeSphereVisibility,
    XCAST(GetTexture) Main_IDirect3DDeviceImpl_7_3T_GetTexture,
    XCAST(SetTexture) GL_IDirect3DDeviceImpl_7_3T_SetTexture,
    XCAST(GetTextureStageState) Main_IDirect3DDeviceImpl_7_3T_GetTextureStageState,
    XCAST(SetTextureStageState) GL_IDirect3DDeviceImpl_7_3T_SetTextureStageState,
    XCAST(ValidateDevice) Main_IDirect3DDeviceImpl_7_3T_ValidateDevice,
    XCAST(ApplyStateBlock) Main_IDirect3DDeviceImpl_7_ApplyStateBlock,
    XCAST(CaptureStateBlock) Main_IDirect3DDeviceImpl_7_CaptureStateBlock,
    XCAST(DeleteStateBlock) Main_IDirect3DDeviceImpl_7_DeleteStateBlock,
    XCAST(CreateStateBlock) Main_IDirect3DDeviceImpl_7_CreateStateBlock,
    XCAST(Load) Main_IDirect3DDeviceImpl_7_Load,
    XCAST(LightEnable) GL_IDirect3DDeviceImpl_7_LightEnable,
    XCAST(GetLightEnable) Main_IDirect3DDeviceImpl_7_GetLightEnable,
    XCAST(SetClipPlane) GL_IDirect3DDeviceImpl_7_SetClipPlane,
    XCAST(GetClipPlane) Main_IDirect3DDeviceImpl_7_GetClipPlane,
    XCAST(GetInfo) Main_IDirect3DDeviceImpl_7_GetInfo,
};

#if !defined(__STRICT_ANSI__) && defined(__GNUC__)
#undef XCAST
#endif


#if !defined(__STRICT_ANSI__) && defined(__GNUC__)
# define XCAST(fun)     (typeof(VTABLE_IDirect3DDevice3.fun))
#else
# define XCAST(fun)     (void*)
#endif

ICOM_VTABLE(IDirect3DDevice3) VTABLE_IDirect3DDevice3 =
{
    ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
    XCAST(QueryInterface) Thunk_IDirect3DDeviceImpl_3_QueryInterface,
    XCAST(AddRef) Thunk_IDirect3DDeviceImpl_3_AddRef,
    XCAST(Release) Thunk_IDirect3DDeviceImpl_3_Release,
    XCAST(GetCaps) GL_IDirect3DDeviceImpl_3_2T_1T_GetCaps,
    XCAST(GetStats) Main_IDirect3DDeviceImpl_3_2T_1T_GetStats,
    XCAST(AddViewport) Main_IDirect3DDeviceImpl_3_2T_1T_AddViewport,
    XCAST(DeleteViewport) Main_IDirect3DDeviceImpl_3_2T_1T_DeleteViewport,
    XCAST(NextViewport) Main_IDirect3DDeviceImpl_3_2T_1T_NextViewport,
    XCAST(EnumTextureFormats) Thunk_IDirect3DDeviceImpl_3_EnumTextureFormats,
    XCAST(BeginScene) Thunk_IDirect3DDeviceImpl_3_BeginScene,
    XCAST(EndScene) Thunk_IDirect3DDeviceImpl_3_EndScene,
    XCAST(GetDirect3D) Thunk_IDirect3DDeviceImpl_3_GetDirect3D,
    XCAST(SetCurrentViewport) Main_IDirect3DDeviceImpl_3_2T_SetCurrentViewport,
    XCAST(GetCurrentViewport) Main_IDirect3DDeviceImpl_3_2T_GetCurrentViewport,
    XCAST(SetRenderTarget) Thunk_IDirect3DDeviceImpl_3_SetRenderTarget,
    XCAST(GetRenderTarget) Thunk_IDirect3DDeviceImpl_3_GetRenderTarget,
    XCAST(Begin) Main_IDirect3DDeviceImpl_3_Begin,
    XCAST(BeginIndexed) Main_IDirect3DDeviceImpl_3_BeginIndexed,
    XCAST(Vertex) Main_IDirect3DDeviceImpl_3_2T_Vertex,
    XCAST(Index) Main_IDirect3DDeviceImpl_3_2T_Index,
    XCAST(End) Main_IDirect3DDeviceImpl_3_2T_End,
    XCAST(GetRenderState) Thunk_IDirect3DDeviceImpl_3_GetRenderState,
    XCAST(SetRenderState) Thunk_IDirect3DDeviceImpl_3_SetRenderState,
    XCAST(GetLightState) Main_IDirect3DDeviceImpl_3_2T_GetLightState,
    XCAST(SetLightState) GL_IDirect3DDeviceImpl_3_2T_SetLightState,
    XCAST(SetTransform) Thunk_IDirect3DDeviceImpl_3_SetTransform,
    XCAST(GetTransform) Thunk_IDirect3DDeviceImpl_3_GetTransform,
    XCAST(MultiplyTransform) Thunk_IDirect3DDeviceImpl_3_MultiplyTransform,
    XCAST(DrawPrimitive) Thunk_IDirect3DDeviceImpl_3_DrawPrimitive,
    XCAST(DrawIndexedPrimitive) Thunk_IDirect3DDeviceImpl_3_DrawIndexedPrimitive,
    XCAST(SetClipStatus) Thunk_IDirect3DDeviceImpl_3_SetClipStatus,
    XCAST(GetClipStatus) Thunk_IDirect3DDeviceImpl_3_GetClipStatus,
    XCAST(DrawPrimitiveStrided) Thunk_IDirect3DDeviceImpl_3_DrawPrimitiveStrided,
    XCAST(DrawIndexedPrimitiveStrided) Thunk_IDirect3DDeviceImpl_3_DrawIndexedPrimitiveStrided,
    XCAST(DrawPrimitiveVB) Thunk_IDirect3DDeviceImpl_3_DrawPrimitiveVB,
    XCAST(DrawIndexedPrimitiveVB) Thunk_IDirect3DDeviceImpl_3_DrawIndexedPrimitiveVB,
    XCAST(ComputeSphereVisibility) Thunk_IDirect3DDeviceImpl_3_ComputeSphereVisibility,
    XCAST(GetTexture) Thunk_IDirect3DDeviceImpl_3_GetTexture,
    XCAST(SetTexture) Thunk_IDirect3DDeviceImpl_3_SetTexture,
    XCAST(GetTextureStageState) Thunk_IDirect3DDeviceImpl_3_GetTextureStageState,
    XCAST(SetTextureStageState) Thunk_IDirect3DDeviceImpl_3_SetTextureStageState,
    XCAST(ValidateDevice) Thunk_IDirect3DDeviceImpl_3_ValidateDevice,
};

#if !defined(__STRICT_ANSI__) && defined(__GNUC__)
#undef XCAST
#endif


#if !defined(__STRICT_ANSI__) && defined(__GNUC__)
# define XCAST(fun)     (typeof(VTABLE_IDirect3DDevice2.fun))
#else
# define XCAST(fun)     (void*)
#endif

ICOM_VTABLE(IDirect3DDevice2) VTABLE_IDirect3DDevice2 =
{
    ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
    XCAST(QueryInterface) Thunk_IDirect3DDeviceImpl_2_QueryInterface,
    XCAST(AddRef) Thunk_IDirect3DDeviceImpl_2_AddRef,
    XCAST(Release) Thunk_IDirect3DDeviceImpl_2_Release,
    XCAST(GetCaps) Thunk_IDirect3DDeviceImpl_2_GetCaps,
    XCAST(SwapTextureHandles) Main_IDirect3DDeviceImpl_2_1T_SwapTextureHandles,
    XCAST(GetStats) Thunk_IDirect3DDeviceImpl_2_GetStats,
    XCAST(AddViewport) Thunk_IDirect3DDeviceImpl_2_AddViewport,
    XCAST(DeleteViewport) Thunk_IDirect3DDeviceImpl_2_DeleteViewport,
    XCAST(NextViewport) Thunk_IDirect3DDeviceImpl_2_NextViewport,
    XCAST(EnumTextureFormats) GL_IDirect3DDeviceImpl_2_1T_EnumTextureFormats,
    XCAST(BeginScene) Thunk_IDirect3DDeviceImpl_2_BeginScene,
    XCAST(EndScene) Thunk_IDirect3DDeviceImpl_2_EndScene,
    XCAST(GetDirect3D) Thunk_IDirect3DDeviceImpl_2_GetDirect3D,
    XCAST(SetCurrentViewport) Thunk_IDirect3DDeviceImpl_2_SetCurrentViewport,
    XCAST(GetCurrentViewport) Thunk_IDirect3DDeviceImpl_2_GetCurrentViewport,
    XCAST(SetRenderTarget) Thunk_IDirect3DDeviceImpl_2_SetRenderTarget,
    XCAST(GetRenderTarget) Thunk_IDirect3DDeviceImpl_2_GetRenderTarget,
    XCAST(Begin) Main_IDirect3DDeviceImpl_2_Begin,
    XCAST(BeginIndexed) Main_IDirect3DDeviceImpl_2_BeginIndexed,
    XCAST(Vertex) Thunk_IDirect3DDeviceImpl_2_Vertex,
    XCAST(Index) Thunk_IDirect3DDeviceImpl_2_Index,
    XCAST(End) Thunk_IDirect3DDeviceImpl_2_End,
    XCAST(GetRenderState) Thunk_IDirect3DDeviceImpl_2_GetRenderState,
    XCAST(SetRenderState) Thunk_IDirect3DDeviceImpl_2_SetRenderState,
    XCAST(GetLightState) Thunk_IDirect3DDeviceImpl_2_GetLightState,
    XCAST(SetLightState) Thunk_IDirect3DDeviceImpl_2_SetLightState,
    XCAST(SetTransform) Thunk_IDirect3DDeviceImpl_2_SetTransform,
    XCAST(GetTransform) Thunk_IDirect3DDeviceImpl_2_GetTransform,
    XCAST(MultiplyTransform) Thunk_IDirect3DDeviceImpl_2_MultiplyTransform,
    XCAST(DrawPrimitive) GL_IDirect3DDeviceImpl_2_DrawPrimitive,
    XCAST(DrawIndexedPrimitive) GL_IDirect3DDeviceImpl_2_DrawIndexedPrimitive,
    XCAST(SetClipStatus) Thunk_IDirect3DDeviceImpl_2_SetClipStatus,
    XCAST(GetClipStatus) Thunk_IDirect3DDeviceImpl_2_GetClipStatus,
};

#if !defined(__STRICT_ANSI__) && defined(__GNUC__)
#undef XCAST
#endif


#if !defined(__STRICT_ANSI__) && defined(__GNUC__)
# define XCAST(fun)     (typeof(VTABLE_IDirect3DDevice.fun))
#else
# define XCAST(fun)     (void*)
#endif

ICOM_VTABLE(IDirect3DDevice) VTABLE_IDirect3DDevice =
{
    ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
    XCAST(QueryInterface) Thunk_IDirect3DDeviceImpl_1_QueryInterface,
    XCAST(AddRef) Thunk_IDirect3DDeviceImpl_1_AddRef,
    XCAST(Release) Thunk_IDirect3DDeviceImpl_1_Release,
    XCAST(Initialize) Main_IDirect3DDeviceImpl_1_Initialize,
    XCAST(GetCaps) Thunk_IDirect3DDeviceImpl_1_GetCaps,
    XCAST(SwapTextureHandles) Thunk_IDirect3DDeviceImpl_1_SwapTextureHandles,
    XCAST(CreateExecuteBuffer) GL_IDirect3DDeviceImpl_1_CreateExecuteBuffer,
    XCAST(GetStats) Thunk_IDirect3DDeviceImpl_1_GetStats,
    XCAST(Execute) Main_IDirect3DDeviceImpl_1_Execute,
    XCAST(AddViewport) Thunk_IDirect3DDeviceImpl_1_AddViewport,
    XCAST(DeleteViewport) Thunk_IDirect3DDeviceImpl_1_DeleteViewport,
    XCAST(NextViewport) Thunk_IDirect3DDeviceImpl_1_NextViewport,
    XCAST(Pick) Main_IDirect3DDeviceImpl_1_Pick,
    XCAST(GetPickRecords) Main_IDirect3DDeviceImpl_1_GetPickRecords,
    XCAST(EnumTextureFormats) Thunk_IDirect3DDeviceImpl_1_EnumTextureFormats,
    XCAST(CreateMatrix) Main_IDirect3DDeviceImpl_1_CreateMatrix,
    XCAST(SetMatrix) Main_IDirect3DDeviceImpl_1_SetMatrix,
    XCAST(GetMatrix) Main_IDirect3DDeviceImpl_1_GetMatrix,
    XCAST(DeleteMatrix) Main_IDirect3DDeviceImpl_1_DeleteMatrix,
    XCAST(BeginScene) Thunk_IDirect3DDeviceImpl_1_BeginScene,
    XCAST(EndScene) Thunk_IDirect3DDeviceImpl_1_EndScene,
    XCAST(GetDirect3D) Thunk_IDirect3DDeviceImpl_1_GetDirect3D,
};

#if !defined(__STRICT_ANSI__) && defined(__GNUC__)
#undef XCAST
#endif

static HRESULT d3ddevice_clear(IDirect3DDeviceImpl *This,
			       WINE_GL_BUFFER_TYPE buffer_type,
			       DWORD dwCount,
			       LPD3DRECT lpRects,
			       DWORD dwFlags,
			       DWORD dwColor,
			       D3DVALUE dvZ,
			       DWORD dwStencil)
{
    IDirect3DDeviceGLImpl *glThis = (IDirect3DDeviceGLImpl *) This;
    GLbitfield bitfield = 0;
    D3DRECT rect;
    int i;
    
    TRACE("(%p)->(%08lx,%p,%08lx,%08lx,%f,%08lx)\n", This, dwCount, lpRects, dwFlags, dwColor, dvZ, dwStencil);
    if (TRACE_ON(ddraw)) {
	if (dwCount > 0) {
	    int i;
	    TRACE(" rectangles : \n");
	    for (i = 0; i < dwCount; i++) {
	        TRACE("  - %ld x %ld     %ld x %ld\n", lpRects[i].u1.x1, lpRects[i].u2.y1, lpRects[i].u3.x2, lpRects[i].u4.y2);
	    }
	}
    }

    if (dwCount == 0) {
        dwCount = 1;
	rect.u1.x1 = 0;
	rect.u2.y1 = 0;
	rect.u3.x2 = This->surface->surface_desc.dwWidth;
	rect.u4.y2 = This->surface->surface_desc.dwHeight;
	lpRects = &rect;
    }
    
    /* Clears the screen */
    ENTER_GL();

    if (dwFlags & D3DCLEAR_TARGET) {
	if (glThis->state[buffer_type] == SURFACE_MEMORY_DIRTY) {
	    /* TODO: optimize here the case where Clear changes all the screen... */
	    This->flush_to_framebuffer(This, &(glThis->lock_rect[buffer_type]), glThis->lock_surf[buffer_type]);
	}
	glThis->state[buffer_type] = SURFACE_GL;
    }

    if (dwFlags & D3DCLEAR_ZBUFFER) {
	bitfield |= GL_DEPTH_BUFFER_BIT;
	if (glThis->depth_mask == FALSE) {
	    glDepthMask(GL_TRUE); /* Enables Z writing to be sure to delete also the Z buffer */
	}
	if (dvZ != glThis->prev_clear_Z) {
	    glClearDepth(dvZ);
	    glThis->prev_clear_Z = dvZ;
	}
	TRACE(" depth value : %f\n", dvZ);
    }
    if (dwFlags & D3DCLEAR_STENCIL) {
        bitfield |= GL_STENCIL_BUFFER_BIT;
	if (dwStencil != glThis->prev_clear_stencil) {
	    glClearStencil(dwStencil);
	    glThis->prev_clear_stencil = dwStencil;
	}
	TRACE(" stencil value : %ld\n", dwStencil);
    }    
    if (dwFlags & D3DCLEAR_TARGET) {
        bitfield |= GL_COLOR_BUFFER_BIT;
	if (dwColor != glThis->prev_clear_color) {
	    glClearColor(((dwColor >> 16) & 0xFF) / 255.0,
			 ((dwColor >>  8) & 0xFF) / 255.0,
			 ((dwColor >>  0) & 0xFF) / 255.0,
			 ((dwColor >> 24) & 0xFF) / 255.0);
	    glThis->prev_clear_color = dwColor;
	}
	TRACE(" color value (ARGB) : %08lx\n", dwColor);
    }

    glEnable(GL_SCISSOR_TEST); 
    for (i = 0; i < dwCount; i++) {
        glScissor(lpRects[i].u1.x1, This->surface->surface_desc.dwHeight - lpRects[i].u4.y2,
		  lpRects[i].u3.x2 - lpRects[i].u1.x1, lpRects[i].u4.y2 - lpRects[i].u2.y1);
        glClear(bitfield);
    }
    glDisable(GL_SCISSOR_TEST); 
    
    if (dwFlags & D3DCLEAR_ZBUFFER) {
	if (glThis->depth_mask == FALSE) glDepthMask(GL_FALSE);
    }
    
    LEAVE_GL();
    
    return DD_OK;
}

static HRESULT d3ddevice_clear_back(IDirect3DDeviceImpl *This,
				    DWORD dwCount,
				    LPD3DRECT lpRects,
				    DWORD dwFlags,
				    DWORD dwColor,
				    D3DVALUE dvZ,
				    DWORD dwStencil)
{
    return d3ddevice_clear(This, WINE_GL_BUFFER_BACK, dwCount, lpRects, dwFlags, dwColor, dvZ, dwStencil);
}

static HRESULT
setup_rect_and_surface_for_blt(IDirectDrawSurfaceImpl *This,
			       WINE_GL_BUFFER_TYPE *buffer_type_p, D3DRECT *rect)
{
    IDirect3DDeviceGLImpl *gl_d3d_dev = (IDirect3DDeviceGLImpl *) This->d3ddevice;
    WINE_GL_BUFFER_TYPE buffer_type;
    
    /* First check if we BLT to the backbuffer... */
    if ((This->surface_desc.ddsCaps.dwCaps & (DDSCAPS_BACKBUFFER)) != 0) {
	buffer_type = WINE_GL_BUFFER_BACK;
    } else if ((This->surface_desc.ddsCaps.dwCaps & (DDSCAPS_FRONTBUFFER|DDSCAPS_PRIMARYSURFACE)) != 0) {
	buffer_type = WINE_GL_BUFFER_FRONT;
    } else {
	ERR("Only BLT override to front or back-buffer is supported for now !\n");
	return DDERR_INVALIDPARAMS;
    }
            
    if ((gl_d3d_dev->state[buffer_type] == SURFACE_MEMORY_DIRTY) &&
	(rect->u1.x1 >= gl_d3d_dev->lock_rect[buffer_type].left) &&
	(rect->u2.y1 >= gl_d3d_dev->lock_rect[buffer_type].top) &&
	(rect->u3.x2 <= gl_d3d_dev->lock_rect[buffer_type].right) &&
	(rect->u4.y2 <= gl_d3d_dev->lock_rect[buffer_type].bottom)) {
	/* If the memory zone is already dirty, use the standard 'in memory' blit operations and not
	 * GL to do it.
	 */
	return DDERR_INVALIDPARAMS;
    }
    *buffer_type_p = buffer_type;
    
    return DD_OK;
}

HRESULT
d3ddevice_blt(IDirectDrawSurfaceImpl *This, LPRECT rdst,
	      LPDIRECTDRAWSURFACE7 src, LPRECT rsrc,
	      DWORD dwFlags, LPDDBLTFX lpbltfx)
{
    WINE_GL_BUFFER_TYPE buffer_type;
    D3DRECT rect;

    if (rdst) {
	rect.u1.x1 = rdst->left;
	rect.u2.y1 = rdst->top;
	rect.u3.x2 = rdst->right;
	rect.u4.y2 = rdst->bottom;
    } else {
	rect.u1.x1 = 0;
	rect.u2.y1 = 0;
	rect.u3.x2 = This->surface_desc.dwWidth;
	rect.u4.y2 = This->surface_desc.dwHeight;
    }
    
    if (setup_rect_and_surface_for_blt(This, &buffer_type, &rect) != DD_OK) return DDERR_INVALIDPARAMS;

    if (dwFlags & DDBLT_COLORFILL) {
        /* This is easy to handle for the D3D Device... */
        DWORD color;
        GLenum prev_draw;
        
        /* The color as given in the Blt function is in the format of the frame-buffer...
         * 'clear' expect it in ARGB format => we need to do some conversion :-)
         */
        if (This->surface_desc.u4.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) {
            if (This->palette) {
                color = ((0xFF000000) |
                         (This->palette->palents[lpbltfx->u5.dwFillColor].peRed << 16) |
                         (This->palette->palents[lpbltfx->u5.dwFillColor].peGreen << 8) |
                         (This->palette->palents[lpbltfx->u5.dwFillColor].peBlue));
            } else {
                color = 0xFF000000;
            }
        } else if ((This->surface_desc.u4.ddpfPixelFormat.dwFlags & DDPF_RGB) &&
                   (((This->surface_desc.u4.ddpfPixelFormat.dwFlags & DDPF_ALPHAPIXELS) == 0) ||
                    (This->surface_desc.u4.ddpfPixelFormat.u5.dwRGBAlphaBitMask == 0x00000000))) {
            if ((This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount == 16) &&
                (This->surface_desc.u4.ddpfPixelFormat.u2.dwRBitMask == 0xF800) &&
                (This->surface_desc.u4.ddpfPixelFormat.u3.dwGBitMask == 0x07E0) &&
                (This->surface_desc.u4.ddpfPixelFormat.u4.dwBBitMask == 0x001F)) {
                if (lpbltfx->u5.dwFillColor == 0xFFFF) {
                    color = 0xFFFFFFFF;
                } else {
                    color = ((0xFF000000) |
                             ((lpbltfx->u5.dwFillColor & 0xF800) << 8) |
                             ((lpbltfx->u5.dwFillColor & 0x07E0) << 5) |
                             ((lpbltfx->u5.dwFillColor & 0x001F) << 3));
                }
            } else if (((This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount == 32) ||
                        (This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount == 24)) &&
                       (This->surface_desc.u4.ddpfPixelFormat.u2.dwRBitMask == 0x00FF0000) &&
                       (This->surface_desc.u4.ddpfPixelFormat.u3.dwGBitMask == 0x0000FF00) &&
                       (This->surface_desc.u4.ddpfPixelFormat.u4.dwBBitMask == 0x000000FF)) {
                color = 0xFF000000 | lpbltfx->u5.dwFillColor;
            } else {
                ERR("Wrong surface type for BLT override (unknown RGB format) !\n");
                return DDERR_INVALIDPARAMS;
            }
        } else {
            ERR("Wrong surface type for BLT override !\n");
            return DDERR_INVALIDPARAMS;
        }
        
        TRACE(" executing D3D Device override.\n");
	
        ENTER_GL();

        glGetIntegerv(GL_DRAW_BUFFER, &prev_draw);
        if (buffer_type == WINE_GL_BUFFER_FRONT)
            glDrawBuffer(GL_FRONT);
        else
            glDrawBuffer(GL_BACK);
        
        d3ddevice_clear(This->d3ddevice, buffer_type, 1, &rect, D3DCLEAR_TARGET, color, 0.0, 0x00000000);
	
        if (((buffer_type == WINE_GL_BUFFER_FRONT) && (prev_draw == GL_BACK)) ||
            ((buffer_type == WINE_GL_BUFFER_BACK)  && (prev_draw == GL_FRONT)))
            glDrawBuffer(prev_draw);
	
        LEAVE_GL();
        
        return DD_OK;
    } else if ((dwFlags & (~(DDBLT_KEYSRC|DDBLT_WAIT|DDBLT_ASYNC))) == 0) {
	/* Normal blit without any special case... */
	if (src != NULL) {
	    /* And which has a SRC surface */
	    IDirectDrawSurfaceImpl *src_impl = ICOM_OBJECT(IDirectDrawSurfaceImpl, IDirectDrawSurface7, src);
	    
	    if ((src_impl->surface_desc.ddsCaps.dwCaps & DDSCAPS_3DDEVICE) &&
		(src_impl->d3ddevice == This->d3ddevice) &&
		((dwFlags & DDBLT_KEYSRC) == 0)) {
		/* Both are 3D devices and using the same GL device and the Blt is without color-keying */
		D3DRECT src_rect;
		int width, height;
		GLenum prev_draw;
		WINE_GL_BUFFER_TYPE src_buffer_type;
		IDirect3DDeviceGLImpl *gl_d3d_dev = (IDirect3DDeviceGLImpl *) This->d3ddevice;
		BOOLEAN initial;
		DWORD opt_bitmap;
		int x, y;
	
		if (rsrc) {
		    src_rect.u1.x1 = rsrc->left;
		    src_rect.u2.y1 = rsrc->top;
		    src_rect.u3.x2 = rsrc->right;
		    src_rect.u4.y2 = rsrc->bottom;
		} else {
		    src_rect.u1.x1 = 0;
		    src_rect.u2.y1 = 0;
		    src_rect.u3.x2 = src_impl->surface_desc.dwWidth;
		    src_rect.u4.y2 = src_impl->surface_desc.dwHeight;
		}

		width = src_rect.u3.x2 - src_rect.u1.x1;
		height = src_rect.u4.y2 - src_rect.u2.y1;

		if ((width != (rect.u3.x2 - rect.u1.x1)) ||
		    (height != (rect.u4.y2 - rect.u2.y1))) {
		    FIXME(" buffer to buffer copy not supported with stretching yet !\n");
		    return DDERR_INVALIDPARAMS;
		}

		/* First check if we BLT from the backbuffer... */
		if ((src_impl->surface_desc.ddsCaps.dwCaps & (DDSCAPS_BACKBUFFER)) != 0) {
		    src_buffer_type = WINE_GL_BUFFER_BACK;
		} else if ((src_impl->surface_desc.ddsCaps.dwCaps & (DDSCAPS_FRONTBUFFER|DDSCAPS_PRIMARYSURFACE)) != 0) {
		    src_buffer_type = WINE_GL_BUFFER_FRONT;
		} else {
		    ERR("Unexpected case in direct buffer to buffer copy !\n");
		    return DDERR_INVALIDPARAMS;
		}
		
		TRACE(" using direct buffer to buffer copy.\n");

		ENTER_GL();

		opt_bitmap = d3ddevice_set_state_for_flush(This->d3ddevice, (LPCRECT) &rect, FALSE, &initial);
		
		if (upload_surface_to_tex_memory_init(This, 0, &gl_d3d_dev->current_internal_format,
						      initial, FALSE, UNLOCK_TEX_SIZE, UNLOCK_TEX_SIZE) != DD_OK) {
		    ERR(" unsupported pixel format at direct buffer to buffer copy.\n");
		    LEAVE_GL();
		    return DDERR_INVALIDPARAMS;
		}
		
		glGetIntegerv(GL_DRAW_BUFFER, &prev_draw);
		if (buffer_type == WINE_GL_BUFFER_FRONT)
		    glDrawBuffer(GL_FRONT);
		else
		    glDrawBuffer(GL_BACK);

		if (src_buffer_type == WINE_GL_BUFFER_FRONT)
		    glReadBuffer(GL_FRONT);
		else
		    glReadBuffer(GL_BACK);

		/* Now the serious stuff happens. Basically, we copy from the source buffer to the texture memory.
		   And directly re-draws this on the destination buffer. */
		for (y = 0; y < height; y += UNLOCK_TEX_SIZE) {
		    int get_height;
		    
		    if ((src_rect.u2.y1 + y + UNLOCK_TEX_SIZE) > src_impl->surface_desc.dwHeight)
			get_height = src_impl->surface_desc.dwHeight - (src_rect.u2.y1 + y);
		    else
			get_height = UNLOCK_TEX_SIZE;
		    
		    for (x = 0; x < width; x += UNLOCK_TEX_SIZE) {
			int get_width;
			
			if ((src_rect.u1.x1 + x + UNLOCK_TEX_SIZE) > src_impl->surface_desc.dwWidth)
			    get_width = src_impl->surface_desc.dwWidth - (src_rect.u1.x1 + x);
			else
			    get_width = UNLOCK_TEX_SIZE;
			
			glCopyTexSubImage2D(GL_TEXTURE_2D, 0,
					    0, UNLOCK_TEX_SIZE - get_height,
					    src_rect.u1.x1 + x, src_impl->surface_desc.dwHeight - (src_rect.u2.y1 + y + get_height),
					    get_width, get_height);
			
			glBegin(GL_QUADS);
			glTexCoord2f(0.0, 0.0);
			glVertex3d(rect.u1.x1 + x,
				   rect.u2.y1 + y + UNLOCK_TEX_SIZE,
				   0.5);
			glTexCoord2f(1.0, 0.0);
			glVertex3d(rect.u1.x1 + x + UNLOCK_TEX_SIZE,
				   rect.u2.y1 + y + UNLOCK_TEX_SIZE,
				   0.5);
			glTexCoord2f(1.0, 1.0);
			glVertex3d(rect.u1.x1 + x + UNLOCK_TEX_SIZE,
				   rect.u2.y1 + y,
				   0.5);
			glTexCoord2f(0.0, 1.0);
			glVertex3d(rect.u1.x1 + x,
				   rect.u2.y1 + y,
				   0.5);
			glEnd();
		    }
		}
		
		upload_surface_to_tex_memory_release();
		d3ddevice_restore_state_after_flush(This->d3ddevice, opt_bitmap, FALSE);
		
		if (((buffer_type == WINE_GL_BUFFER_FRONT) && (prev_draw == GL_BACK)) ||
		    ((buffer_type == WINE_GL_BUFFER_BACK)  && (prev_draw == GL_FRONT)))
		    glDrawBuffer(prev_draw);
		
		LEAVE_GL();

		return DD_OK;
	    } else {
		/* This is the normal 'with source' Blit. Use the texture engine to do the Blt for us
		   (this prevents calling glReadPixels) */
		D3DRECT src_rect;
		int width, height;
		GLenum prev_draw;
		IDirect3DDeviceGLImpl *gl_d3d_dev = (IDirect3DDeviceGLImpl *) This->d3ddevice;
		BOOLEAN initial;
		DWORD opt_bitmap;
		int x, y;
		double x_stretch, y_stretch;
		
		if (rsrc) {
		    src_rect.u1.x1 = rsrc->left;
		    src_rect.u2.y1 = rsrc->top;
		    src_rect.u3.x2 = rsrc->right;
		    src_rect.u4.y2 = rsrc->bottom;
		} else {
		    src_rect.u1.x1 = 0;
		    src_rect.u2.y1 = 0;
		    src_rect.u3.x2 = src_impl->surface_desc.dwWidth;
		    src_rect.u4.y2 = src_impl->surface_desc.dwHeight;
		}

		width = src_rect.u3.x2 - src_rect.u1.x1;
		height = src_rect.u4.y2 - src_rect.u2.y1;

		x_stretch = (double) (rect.u3.x2 - rect.u1.x1) / (double) width;
		y_stretch = (double) (rect.u4.y2 - rect.u2.y1) / (double) height;

		TRACE(" using memory to buffer Blt overide.\n");

		ENTER_GL();

		opt_bitmap = d3ddevice_set_state_for_flush(This->d3ddevice, (LPCRECT) &rect, ((dwFlags & DDBLT_KEYSRC) != 0), &initial);
		
		if (upload_surface_to_tex_memory_init(src_impl, 0, &gl_d3d_dev->current_internal_format,
						      initial, ((dwFlags & DDBLT_KEYSRC) != 0), UNLOCK_TEX_SIZE, UNLOCK_TEX_SIZE) != DD_OK) {
		    ERR(" unsupported pixel format at memory to buffer Blt overide.\n");
		    LEAVE_GL();
		    return DDERR_INVALIDPARAMS;
		}
		
		glGetIntegerv(GL_DRAW_BUFFER, &prev_draw);
		if (buffer_type == WINE_GL_BUFFER_FRONT)
		    glDrawBuffer(GL_FRONT);
		else
		    glDrawBuffer(GL_BACK);

		/* Now the serious stuff happens. This is basically the same code that for the memory
		   flush to frame buffer ... with stretching and different rectangles added :-) */
		for (y = 0; y < height; y += UNLOCK_TEX_SIZE) {
		    RECT flush_rect;

		    flush_rect.top    = src_rect.u2.y1 + y;
		    flush_rect.bottom = ((src_rect.u2.y1 + y + UNLOCK_TEX_SIZE > src_rect.u4.y2) ?
					 src_rect.u4.y2 :
					 (src_rect.u2.y1 + y + UNLOCK_TEX_SIZE));
		    
		    for (x = 0; x < width; x += UNLOCK_TEX_SIZE) {
			flush_rect.left  = src_rect.u1.x1 + x;
			flush_rect.right = ((src_rect.u1.x1 + x + UNLOCK_TEX_SIZE > src_rect.u3.x2) ?
					    src_rect.u3.x2 :
					    (src_rect.u1.x1 + x + UNLOCK_TEX_SIZE));
			
			upload_surface_to_tex_memory(&flush_rect, 0, 0, &(gl_d3d_dev->surface_ptr));
			
			glBegin(GL_QUADS);
			glTexCoord2f(0.0, 0.0);
			glVertex3d(rect.u1.x1 + (x * x_stretch),
				   rect.u2.y1 + (y * y_stretch),
				   0.5);
			glTexCoord2f(1.0, 0.0);
			glVertex3d(rect.u1.x1 + ((x + UNLOCK_TEX_SIZE) * x_stretch),
				   rect.u2.y1 + (y * y_stretch),
				   0.5);
			glTexCoord2f(1.0, 1.0);
			glVertex3d(rect.u1.x1 + ((x + UNLOCK_TEX_SIZE) * x_stretch),
				   rect.u2.y1 + ((y + UNLOCK_TEX_SIZE) * y_stretch),
				   0.5);
			glTexCoord2f(0.0, 1.0);
			glVertex3d(rect.u1.x1 + (x * x_stretch),
				   rect.u2.y1 + ((y + UNLOCK_TEX_SIZE) * y_stretch),
				   0.5);
			glEnd();
		    }
		}
		
		upload_surface_to_tex_memory_release();
		d3ddevice_restore_state_after_flush(This->d3ddevice, opt_bitmap, ((dwFlags & DDBLT_KEYSRC) != 0));
		
		if (((buffer_type == WINE_GL_BUFFER_FRONT) && (prev_draw == GL_BACK)) ||
		    ((buffer_type == WINE_GL_BUFFER_BACK)  && (prev_draw == GL_FRONT)))
		    glDrawBuffer(prev_draw);
		
		LEAVE_GL();

		return DD_OK;		
	    }
	}
    }
    return DDERR_INVALIDPARAMS;
}

HRESULT
d3ddevice_bltfast(IDirectDrawSurfaceImpl *This, DWORD dstx,
		  DWORD dsty, LPDIRECTDRAWSURFACE7 src,
		  LPRECT rsrc, DWORD trans)
{
    RECT rsrc2;
    RECT rdst;
    IDirectDrawSurfaceImpl *src_impl = ICOM_OBJECT(IDirectDrawSurfaceImpl, IDirectDrawSurface7, src);
    IDirect3DDeviceGLImpl *gl_d3d_dev = (IDirect3DDeviceGLImpl *) This->d3ddevice;
    WINE_GL_BUFFER_TYPE buffer_type;
    GLenum prev_draw;
    DWORD opt_bitmap;
    BOOLEAN initial;
    int width, height, x, y;
    
    /* Cannot support DSTCOLORKEY blitting... */
    if ((trans & DDBLTFAST_DESTCOLORKEY) != 0) return DDERR_INVALIDPARAMS;

    if (rsrc == NULL) {
	WARN("rsrc is NULL - getting the whole surface !!\n");
	rsrc = &rsrc2;
	rsrc->left = rsrc->top = 0;
	rsrc->right = src_impl->surface_desc.dwWidth;
	rsrc->bottom = src_impl->surface_desc.dwHeight;
    } else {
	rsrc2 = *rsrc;
	rsrc = &rsrc2;
    }

    rdst.left = dstx;
    rdst.top = dsty;
    rdst.right = dstx + (rsrc->right - rsrc->left);
    if (rdst.right > This->surface_desc.dwWidth) {
	rsrc->right -= (This->surface_desc.dwWidth - rdst.right);
	rdst.right = This->surface_desc.dwWidth;
    }
    rdst.bottom = dsty + (rsrc->bottom - rsrc->top);
    if (rdst.bottom > This->surface_desc.dwHeight) {
	rsrc->bottom -= (This->surface_desc.dwHeight - rdst.bottom);
	rdst.bottom = This->surface_desc.dwHeight;
    }

    width = rsrc->right - rsrc->left;
    height = rsrc->bottom - rsrc->top;
    
    if (setup_rect_and_surface_for_blt(This, &buffer_type, (D3DRECT *) &rdst) != DD_OK) return DDERR_INVALIDPARAMS;

    TRACE(" using BltFast memory to frame buffer overide.\n");
    
    ENTER_GL();
    
    opt_bitmap = d3ddevice_set_state_for_flush(This->d3ddevice, &rdst, (trans & DDBLTFAST_SRCCOLORKEY) != 0, &initial);
    
    if (upload_surface_to_tex_memory_init(src_impl, 0, &gl_d3d_dev->current_internal_format,
					  initial, (trans & DDBLTFAST_SRCCOLORKEY) != 0,
					  UNLOCK_TEX_SIZE, UNLOCK_TEX_SIZE) != DD_OK) {
	ERR(" unsupported pixel format at memory to buffer Blt overide.\n");
	LEAVE_GL();
	return DDERR_INVALIDPARAMS;
    }
    
    glGetIntegerv(GL_DRAW_BUFFER, &prev_draw);
    if (buffer_type == WINE_GL_BUFFER_FRONT)
	glDrawBuffer(GL_FRONT);
    else
	glDrawBuffer(GL_BACK);
    
    /* Now the serious stuff happens. This is basically the same code that for the memory
       flush to frame buffer but with different rectangles for source and destination :-) */
    for (y = 0; y < height; y += UNLOCK_TEX_SIZE) {
	RECT flush_rect;
	
	flush_rect.top    = rsrc->top + y;
	flush_rect.bottom = ((rsrc->top + y + UNLOCK_TEX_SIZE > rsrc->bottom) ?
			     rsrc->bottom :
			     (rsrc->top + y + UNLOCK_TEX_SIZE));
	
	for (x = 0; x < width; x += UNLOCK_TEX_SIZE) {
	    flush_rect.left  = rsrc->left + x;
	    flush_rect.right = ((rsrc->left + x + UNLOCK_TEX_SIZE > rsrc->right) ?
				rsrc->right :
				(rsrc->left + x + UNLOCK_TEX_SIZE));
	    
	    upload_surface_to_tex_memory(&flush_rect, 0, 0, &(gl_d3d_dev->surface_ptr));
	    
	    glBegin(GL_QUADS);
	    glTexCoord2f(0.0, 0.0);
	    glVertex3d(rdst.left + x,
		       rdst.top + y,
		       0.5);
	    glTexCoord2f(1.0, 0.0);
	    glVertex3d(rdst.left + (x + UNLOCK_TEX_SIZE),
		       rdst.top + y,
		       0.5);
	    glTexCoord2f(1.0, 1.0);
	    glVertex3d(rdst.left + (x + UNLOCK_TEX_SIZE),
		       rdst.top + (y + UNLOCK_TEX_SIZE),
		       0.5);
	    glTexCoord2f(0.0, 1.0);
	    glVertex3d(rdst.left + x,
		       rdst.top + (y + UNLOCK_TEX_SIZE),
		       0.5);
	    glEnd();
	}
    }
    
    upload_surface_to_tex_memory_release();
    d3ddevice_restore_state_after_flush(This->d3ddevice, opt_bitmap, (trans & DDBLTFAST_SRCCOLORKEY) != 0);
    
    if (((buffer_type == WINE_GL_BUFFER_FRONT) && (prev_draw == GL_BACK)) ||
	((buffer_type == WINE_GL_BUFFER_BACK)  && (prev_draw == GL_FRONT)))
	glDrawBuffer(prev_draw);
    
    LEAVE_GL();
    
    return DD_OK;
}

void
d3ddevice_set_ortho(IDirect3DDeviceImpl *This)
{
    GLfloat height, width;
    GLfloat trans_mat[16];

    TRACE("(%p)\n", This);
    
    width = This->surface->surface_desc.dwWidth;
    height = This->surface->surface_desc.dwHeight;
    
    /* The X axis is straighforward.. For the Y axis, we need to convert 'D3D' screen coordinates
       to OpenGL screen coordinates (ie the upper left corner is not the same).
       For Z, the mystery is what should it be mapped to ? Ie should the resulting range be between
       -1.0 and 1.0 (as the X and Y coordinates) or between 0.0 and 1.0 ? */
    trans_mat[ 0] = 2.0 / width;  trans_mat[ 4] = 0.0;  trans_mat[ 8] = 0.0; trans_mat[12] = -1.0;
    trans_mat[ 1] = 0.0; trans_mat[ 5] = -2.0 / height; trans_mat[ 9] = 0.0; trans_mat[13] =  1.0;
    trans_mat[ 2] = 0.0; trans_mat[ 6] = 0.0; trans_mat[10] = 1.0;           trans_mat[14] = -1.0;
    trans_mat[ 3] = 0.0; trans_mat[ 7] = 0.0; trans_mat[11] = 0.0;           trans_mat[15] =  1.0;

    ENTER_GL();
    glMatrixMode(GL_MODELVIEW);
    glLoadIdentity();
    /* See the OpenGL Red Book for an explanation of the following translation (in the OpenGL
       Correctness Tips section).
       
       Basically, from what I understood, if the game does not filter the font texture,
       as the 'real' pixel will lie at the middle of the two texels, OpenGL may choose the wrong
       one and we will have strange artifacts (as the rounding and stuff may give different results
       for different pixels, ie sometimes take the left pixel, sometimes the right).
    */
    glTranslatef(0.375, 0.375, 0);
    glMatrixMode(GL_PROJECTION);
    glLoadMatrixf(trans_mat);
    LEAVE_GL();
}

void
d3ddevice_set_matrices(IDirect3DDeviceImpl *This, DWORD matrices,
		       D3DMATRIX *world_mat, D3DMATRIX *view_mat, D3DMATRIX *proj_mat)
{
    TRACE("(%p,%08lx,%p,%p,%p)\n", This, matrices, world_mat, view_mat, proj_mat);
    
    ENTER_GL();
    if ((matrices & (VIEWMAT_CHANGED|WORLDMAT_CHANGED)) != 0) {
        glMatrixMode(GL_MODELVIEW);
	glLoadMatrixf((float *) view_mat);

	/* Now also re-loads all the Lights and Clipping Planes using the new matrices */
	if (This->state_block.render_state[D3DRENDERSTATE_CLIPPING - 1] != FALSE) {
	    GLint i;
	    DWORD runner;
	    for (i = 0, runner = 0x00000001; i < This->max_clipping_planes; i++, runner <<= 1) {
	        if (runner & This->state_block.render_state[D3DRENDERSTATE_CLIPPLANEENABLE - 1]) {
		    GLdouble plane[4];

		    plane[0] = This->clipping_planes[i].plane[0];
		    plane[1] = This->clipping_planes[i].plane[1];
		    plane[2] = This->clipping_planes[i].plane[2];
		    plane[3] = This->clipping_planes[i].plane[3];
		    
		    glClipPlane( GL_CLIP_PLANE0 + i, (const GLdouble*) (&plane) );
		}
	    }
	}
	if (This->state_block.render_state[D3DRENDERSTATE_LIGHTING - 1] != FALSE) {
	    GLint i;
	    DWORD runner;

	    for (i = 0, runner = 0x00000001; i < MAX_LIGHTS; i++, runner <<= 1) {
	        if (runner & This->active_lights) {
		    switch (This->light_parameters[i].dltType) {
		        case D3DLIGHT_DIRECTIONAL: {
			    float direction[4];
			    float cut_off = 180.0;
			    
			    glLightfv(GL_LIGHT0 + i, GL_AMBIENT,  (float *) &(This->light_parameters[i].dcvAmbient));
			    glLightfv(GL_LIGHT0 + i, GL_DIFFUSE,  (float *) &(This->light_parameters[i].dcvDiffuse));
			    glLightfv(GL_LIGHT0 + i, GL_SPECULAR, (float *) &(This->light_parameters[i].dcvSpecular));
			    glLightfv(GL_LIGHT0 + i, GL_SPOT_CUTOFF, &cut_off);
			    
			    direction[0] = This->light_parameters[i].dvDirection.u1.x;
			    direction[1] = This->light_parameters[i].dvDirection.u2.y;
			    direction[2] = This->light_parameters[i].dvDirection.u3.z;
			    direction[3] = 0.0;
			    glLightfv(GL_LIGHT0 + i, GL_POSITION, (float *) direction);
			} break;

			case D3DLIGHT_POINT: {
			    float position[4];
			    float cut_off = 180.0;
			    
			    glLightfv(GL_LIGHT0 + i, GL_AMBIENT,  (float *) &(This->light_parameters[i].dcvAmbient));
			    glLightfv(GL_LIGHT0 + i, GL_DIFFUSE,  (float *) &(This->light_parameters[i].dcvDiffuse));
			    glLightfv(GL_LIGHT0 + i, GL_SPECULAR, (float *) &(This->light_parameters[i].dcvSpecular));
			    position[0] = This->light_parameters[i].dvPosition.u1.x;
			    position[1] = This->light_parameters[i].dvPosition.u2.y;
			    position[2] = This->light_parameters[i].dvPosition.u3.z;
			    position[3] = 1.0;
			    glLightfv(GL_LIGHT0 + i, GL_POSITION, (float *) position);
			    glLightfv(GL_LIGHT0 + i, GL_CONSTANT_ATTENUATION, &(This->light_parameters[i].dvAttenuation0));
			    glLightfv(GL_LIGHT0 + i, GL_LINEAR_ATTENUATION, &(This->light_parameters[i].dvAttenuation1));
			    glLightfv(GL_LIGHT0 + i, GL_QUADRATIC_ATTENUATION, &(This->light_parameters[i].dvAttenuation2));
			    glLightfv(GL_LIGHT0 + i, GL_SPOT_CUTOFF, &cut_off);
			} break;

			case D3DLIGHT_SPOT: {
			    float direction[4];
			    float position[4];
			    float cut_off = 90.0 * (This->light_parameters[i].dvPhi / M_PI);
			    
			    glLightfv(GL_LIGHT0 + i, GL_AMBIENT,  (float *) &(This->light_parameters[i].dcvAmbient));
			    glLightfv(GL_LIGHT0 + i, GL_DIFFUSE,  (float *) &(This->light_parameters[i].dcvDiffuse));
			    glLightfv(GL_LIGHT0 + i, GL_SPECULAR, (float *) &(This->light_parameters[i].dcvSpecular));
			    
			    direction[0] = This->light_parameters[i].dvDirection.u1.x;
			    direction[1] = This->light_parameters[i].dvDirection.u2.y;
			    direction[2] = This->light_parameters[i].dvDirection.u3.z;
			    direction[3] = 0.0;
			    glLightfv(GL_LIGHT0 + i, GL_SPOT_DIRECTION, (float *) direction);
			    position[0] = This->light_parameters[i].dvPosition.u1.x;
			    position[1] = This->light_parameters[i].dvPosition.u2.y;
			    position[2] = This->light_parameters[i].dvPosition.u3.z;
			    position[3] = 1.0;
			    glLightfv(GL_LIGHT0 + i, GL_POSITION, (float *) position);
			    glLightfv(GL_LIGHT0 + i, GL_CONSTANT_ATTENUATION, &(This->light_parameters[i].dvAttenuation0));
			    glLightfv(GL_LIGHT0 + i, GL_LINEAR_ATTENUATION, &(This->light_parameters[i].dvAttenuation1));
			    glLightfv(GL_LIGHT0 + i, GL_QUADRATIC_ATTENUATION, &(This->light_parameters[i].dvAttenuation2));
			    glLightfv(GL_LIGHT0 + i, GL_SPOT_CUTOFF, &cut_off);
			    glLightfv(GL_LIGHT0 + i, GL_SPOT_EXPONENT, &(This->light_parameters[i].dvFalloff));
			} break;

			default:
			    /* No warning here as it's already done at light setting */
			    break;
		    }
		}
	    }
	}
	
	glMultMatrixf((float *) world_mat);
    }
    if ((matrices & PROJMAT_CHANGED) != 0) {
	glMatrixMode(GL_PROJECTION);
	glLoadMatrixf((float *) proj_mat);
    }
    LEAVE_GL();
}

void
d3ddevice_matrices_updated(IDirect3DDeviceImpl *This, DWORD matrices)
{
    IDirect3DDeviceGLImpl *glThis = (IDirect3DDeviceGLImpl *) This;
    DWORD tex_mat, tex_stage;

    TRACE("(%p,%08lx)\n", This, matrices);
    
    if (matrices & (VIEWMAT_CHANGED|WORLDMAT_CHANGED|PROJMAT_CHANGED)) {
        if (glThis->transform_state == GL_TRANSFORM_NORMAL) {
	    /* This will force an update of the transform state at the next drawing. */
	    glThis->transform_state = GL_TRANSFORM_NONE;
	}
    }
    if (matrices & (TEXMAT0_CHANGED|TEXMAT1_CHANGED|TEXMAT2_CHANGED|TEXMAT3_CHANGED|
		    TEXMAT4_CHANGED|TEXMAT5_CHANGED|TEXMAT6_CHANGED|TEXMAT7_CHANGED))
    {
        ENTER_GL();
	for (tex_mat = TEXMAT0_CHANGED, tex_stage = 0; tex_mat <= TEXMAT7_CHANGED; tex_mat <<= 1, tex_stage++) {
	    if (matrices & tex_mat) {
	        if (This->state_block.texture_stage_state[tex_stage][D3DTSS_TEXTURETRANSFORMFLAGS - 1] != D3DTTFF_DISABLE) {
		    if (tex_stage == 0) {
		        /* No multi-texturing support for now ... */
		        glMatrixMode(GL_TEXTURE);
			glLoadMatrixf((float *) This->tex_mat[tex_stage]);
			if (memcmp(This->tex_mat[tex_stage], id_mat, 16 * sizeof(D3DVALUE))) {
			    This->tex_mat_is_identity[tex_stage] = FALSE;
			} else {
			    This->tex_mat_is_identity[tex_stage] = TRUE;
			}
		    }
		} else {
		    if (tex_stage == 0) {
			if (This->tex_mat_is_identity[tex_stage] == FALSE) {
			    glMatrixMode(GL_TEXTURE);
			    glLoadIdentity();
			    This->tex_mat_is_identity[tex_stage] = TRUE;
			}
		    }
		}
	    }
	}
	LEAVE_GL();
    }
}

/* TODO for both these functions :
    - change / restore OpenGL parameters for pictures transfers in case they are ever modified
      by other OpenGL code in D3D
    - handle the case where no 'Begin / EndScene' was done between two locks
    - handle the rectangles in the unlock too
    - handle pitch correctly...
*/
static void d3ddevice_lock_update(IDirectDrawSurfaceImpl* This, LPCRECT pRect, DWORD dwFlags)
{
    IDirect3DDeviceImpl *d3d_dev = This->d3ddevice;
    IDirect3DDeviceGLImpl* gl_d3d_dev = (IDirect3DDeviceGLImpl*) d3d_dev;
    WINE_GL_BUFFER_TYPE buffer_type;
    RECT loc_rect;
    
    if ((This->surface_desc.ddsCaps.dwCaps & (DDSCAPS_FRONTBUFFER|DDSCAPS_PRIMARYSURFACE)) != 0) {
        buffer_type = WINE_GL_BUFFER_FRONT;
	if ((gl_d3d_dev->state[WINE_GL_BUFFER_FRONT] != SURFACE_GL) &&
	    (gl_d3d_dev->lock_surf[WINE_GL_BUFFER_FRONT] != This)) {
	    ERR("Change of front buffer.. Expect graphic corruptions !\n");
	}
	gl_d3d_dev->lock_surf[WINE_GL_BUFFER_FRONT] = This;
    } else if ((This->surface_desc.ddsCaps.dwCaps & (DDSCAPS_BACKBUFFER)) == (DDSCAPS_BACKBUFFER)) {
        buffer_type = WINE_GL_BUFFER_BACK;
	if ((gl_d3d_dev->state[WINE_GL_BUFFER_BACK] != SURFACE_GL) &&
	    (gl_d3d_dev->lock_surf[WINE_GL_BUFFER_BACK] != This)) {
	    ERR("Change of back buffer.. Expect graphic corruptions !\n");
	}
	gl_d3d_dev->lock_surf[WINE_GL_BUFFER_BACK] = This;
    } else {
        ERR("Wrong surface type for locking !\n");
	return;
    }

    if (pRect == NULL) {
	loc_rect.top = 0;
	loc_rect.left = 0;
	loc_rect.bottom = This->surface_desc.dwHeight;
	loc_rect.right = This->surface_desc.dwWidth;
	pRect = &loc_rect;
    }
    
    /* Try to acquire the device critical section */
    EnterCriticalSection(&(d3d_dev->crit));
    
    if (gl_d3d_dev->lock_rect_valid[buffer_type] == TRUE) {
	ERR("Two consecutive locks on %s buffer... Expect problems !\n",
	    (buffer_type == WINE_GL_BUFFER_BACK ? "back" : "front"));
    }
    gl_d3d_dev->lock_rect_valid[buffer_type] = TRUE;
    
    if (gl_d3d_dev->state[buffer_type] != SURFACE_GL) {
	/* Check if the new rectangle is in the previous one or not.
	   If it is not, flush first the previous locks on screen.
	*/
	if ((pRect->top    < gl_d3d_dev->lock_rect[buffer_type].top) ||
	    (pRect->left   < gl_d3d_dev->lock_rect[buffer_type].left) ||
	    (pRect->right  > gl_d3d_dev->lock_rect[buffer_type].right) ||
	    (pRect->bottom > gl_d3d_dev->lock_rect[buffer_type].bottom)) {
	    if (gl_d3d_dev->state[buffer_type] == SURFACE_MEMORY_DIRTY) {
		TRACE(" flushing back to %s buffer as new rect : (%ldx%ld) - (%ldx%ld) not included in old rect : (%ldx%ld) - (%ldx%ld)\n",
		      (buffer_type == WINE_GL_BUFFER_BACK ? "back" : "front"),
		      pRect->left, pRect->top, pRect->right, pRect->bottom,
		      gl_d3d_dev->lock_rect[buffer_type].left, gl_d3d_dev->lock_rect[buffer_type].top,
		      gl_d3d_dev->lock_rect[buffer_type].right, gl_d3d_dev->lock_rect[buffer_type].bottom);
		d3d_dev->flush_to_framebuffer(d3d_dev, &(gl_d3d_dev->lock_rect[buffer_type]), gl_d3d_dev->lock_surf[buffer_type]);
	    }
	    gl_d3d_dev->state[buffer_type] = SURFACE_GL;
	    gl_d3d_dev->lock_rect[buffer_type] = *pRect;
	}
	/* In the other case, do not upgrade the locking rectangle as it's no need... */
    } else {
	gl_d3d_dev->lock_rect[buffer_type] = *pRect;
    }
    
    if (gl_d3d_dev->state[buffer_type] == SURFACE_GL) {
        /* If the surface is already in memory, no need to do anything here... */
        GLenum buffer_format;
	GLenum buffer_color;
	int y;
	char *dst;

	TRACE(" copying %s buffer to main memory with rectangle (%ldx%ld) - (%ldx%ld).\n", (buffer_type == WINE_GL_BUFFER_BACK ? "back" : "front"),
	      pRect->left, pRect->top, pRect->right, pRect->bottom);
	
	/* Note that here we cannot do 'optmizations' about the WriteOnly flag... Indeed, a game
	   may only write to the device... But when we will blit it back to the screen, we need
	   also to blit correctly the parts the application did not overwrite... */

	if (((This->surface_desc.u4.ddpfPixelFormat.dwFlags & DDPF_RGB) != 0) &&
	    (((This->surface_desc.u4.ddpfPixelFormat.dwFlags & DDPF_ALPHAPIXELS) == 0) ||
	     (This->surface_desc.u4.ddpfPixelFormat.u5.dwRGBAlphaBitMask == 0x00000000))) {
	    if ((This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount == 16) &&
		(This->surface_desc.u4.ddpfPixelFormat.u2.dwRBitMask == 0xF800) &&
		(This->surface_desc.u4.ddpfPixelFormat.u3.dwGBitMask == 0x07E0) &&
		(This->surface_desc.u4.ddpfPixelFormat.u4.dwBBitMask == 0x001F)) {
		buffer_format = GL_UNSIGNED_SHORT_5_6_5;
		buffer_color = GL_RGB;
	    } else if ((This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount == 24) &&
		       (This->surface_desc.u4.ddpfPixelFormat.u2.dwRBitMask == 0xFF0000) &&
		       (This->surface_desc.u4.ddpfPixelFormat.u3.dwGBitMask == 0x00FF00) &&
		       (This->surface_desc.u4.ddpfPixelFormat.u4.dwBBitMask == 0x0000FF)) {
		buffer_format = GL_UNSIGNED_BYTE;
		buffer_color = GL_RGB;
	    } else if ((This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount == 32) &&
		       (This->surface_desc.u4.ddpfPixelFormat.u2.dwRBitMask == 0x00FF0000) &&
		       (This->surface_desc.u4.ddpfPixelFormat.u3.dwGBitMask == 0x0000FF00) &&
		       (This->surface_desc.u4.ddpfPixelFormat.u4.dwBBitMask == 0x000000FF)) {
		buffer_format = GL_UNSIGNED_INT_8_8_8_8_REV;
		buffer_color = GL_BGRA;
	    } else {
		ERR(" unsupported pixel format at device locking.\n");
		return;
	    }
	} else {
	    ERR(" unsupported pixel format at device locking - alpha on frame buffer.\n");
	    return;
	}

	ENTER_GL();
	
	if (buffer_type == WINE_GL_BUFFER_FRONT)
	    /* Application wants to lock the front buffer */
	    glReadBuffer(GL_FRONT);
	else 
	    /* Application wants to lock the back buffer */
	    glReadBuffer(GL_BACK);

	dst = ((char *)This->surface_desc.lpSurface) +
	  (pRect->top * This->surface_desc.u1.lPitch) + (pRect->left * GET_BPP(This->surface_desc));
	for (y = (This->surface_desc.dwHeight - pRect->top - 1);
	     y >= ((int) This->surface_desc.dwHeight - (int) pRect->bottom);
	     y--) {
	    glReadPixels(pRect->left, y,
			 pRect->right - pRect->left, 1,
			 buffer_color, buffer_format, dst);
	    dst += This->surface_desc.u1.lPitch;
	}

	gl_d3d_dev->state[buffer_type] = SURFACE_MEMORY;
	
#if 0
	/* I keep this code here as it's very useful to debug :-) */
	{
	    static int flush_count = 0;
	    char buf[128];
	    FILE *f;
	    
	    if ((++flush_count % 50) == 0) {
	        sprintf(buf, "lock_%06d.pnm", flush_count);
		f = fopen(buf, "wb");
		DDRAW_dump_surface_to_disk(This, f);
	    }
	}
#endif
	
	LEAVE_GL();
    }
}

static void d3ddevice_flush_to_frame_buffer(IDirect3DDeviceImpl *d3d_dev, LPCRECT pRect, IDirectDrawSurfaceImpl *surf) {
    RECT loc_rect;
    IDirect3DDeviceGLImpl* gl_d3d_dev = (IDirect3DDeviceGLImpl*) d3d_dev;
    int x, y;
    BOOLEAN initial;
    DWORD opt_bitmap;
    
    /* Note : no need here to lock the 'device critical section' as we are already protected by
       the GL critical section. */

    if (pRect == NULL) {
	loc_rect.top = 0;
	loc_rect.left = 0;
	loc_rect.bottom = d3d_dev->surface->surface_desc.dwHeight;
	loc_rect.right = d3d_dev->surface->surface_desc.dwWidth;
	pRect = &loc_rect;
    }
    
    TRACE(" flushing memory back to screen memory (%ld,%ld) x (%ld,%ld).\n", pRect->top, pRect->left, pRect->right, pRect->bottom);

    opt_bitmap = d3ddevice_set_state_for_flush(d3d_dev, pRect, FALSE, &initial);
    
    if (upload_surface_to_tex_memory_init(surf, 0, &gl_d3d_dev->current_internal_format,
					  initial, FALSE, UNLOCK_TEX_SIZE, UNLOCK_TEX_SIZE) != DD_OK) {
        ERR(" unsupported pixel format at frame buffer flush.\n");
	return;
    }
	
    for (y = pRect->top; y < pRect->bottom; y += UNLOCK_TEX_SIZE) {
	RECT flush_rect;
	
	flush_rect.top = y;
	flush_rect.bottom = (y + UNLOCK_TEX_SIZE > pRect->bottom) ? pRect->bottom : (y + UNLOCK_TEX_SIZE);

	for (x = pRect->left; x < pRect->right; x += UNLOCK_TEX_SIZE) {
	    /* First, upload the texture... */
	    flush_rect.left = x;
	    flush_rect.right = (x + UNLOCK_TEX_SIZE > pRect->right)  ? pRect->right  : (x + UNLOCK_TEX_SIZE);

	    upload_surface_to_tex_memory(&flush_rect, 0, 0, &(gl_d3d_dev->surface_ptr));

	    glBegin(GL_QUADS);
	    glTexCoord2f(0.0, 0.0);
	    glVertex3d(x, y, 0.5);
	    glTexCoord2f(1.0, 0.0);
	    glVertex3d(x + UNLOCK_TEX_SIZE, y, 0.5);
	    glTexCoord2f(1.0, 1.0);
	    glVertex3d(x + UNLOCK_TEX_SIZE, y + UNLOCK_TEX_SIZE, 0.5);
	    glTexCoord2f(0.0, 1.0);
	    glVertex3d(x, y + UNLOCK_TEX_SIZE, 0.5);
	    glEnd();
	}
    }
    
    upload_surface_to_tex_memory_release();
    d3ddevice_restore_state_after_flush(d3d_dev, opt_bitmap, FALSE);
    
#if 0
    /* I keep this code here as it's very useful to debug :-) */
    {
        static int flush_count = 0;
	char buf[128];
	FILE *f;

	if ((++flush_count % 50) == 0) {
	    sprintf(buf, "flush_%06d.pnm", flush_count);
	    f = fopen(buf, "wb");
	    DDRAW_dump_surface_to_disk(surf, f);
	}
    }
#endif
}

static void d3ddevice_unlock_update(IDirectDrawSurfaceImpl* This, LPCRECT pRect)
{
    WINE_GL_BUFFER_TYPE buffer_type;
    IDirect3DDeviceImpl *d3d_dev = This->d3ddevice;
    IDirect3DDeviceGLImpl* gl_d3d_dev = (IDirect3DDeviceGLImpl*) d3d_dev;
  
    if ((This->surface_desc.ddsCaps.dwCaps & (DDSCAPS_FRONTBUFFER|DDSCAPS_PRIMARYSURFACE)) != 0) {
        buffer_type = WINE_GL_BUFFER_FRONT;
    } else if ((This->surface_desc.ddsCaps.dwCaps & (DDSCAPS_BACKBUFFER)) == (DDSCAPS_BACKBUFFER)) {
	buffer_type = WINE_GL_BUFFER_BACK;
    } else {
        ERR("Wrong surface type for locking !\n");
	return;
    }

    if (gl_d3d_dev->lock_rect_valid[buffer_type] == FALSE) {
	ERR("Unlock without prior lock on %s buffer... Expect problems !\n",
	    (buffer_type == WINE_GL_BUFFER_BACK ? "back" : "front"));
    }
    gl_d3d_dev->lock_rect_valid[buffer_type] = FALSE;
    
    /* First, check if we need to do anything. For the backbuffer, flushing is done at the next 3D activity. */
    if ((This->lastlocktype & DDLOCK_READONLY) == 0) {
        if (buffer_type == WINE_GL_BUFFER_FRONT) {
	    GLenum prev_draw;

	    TRACE(" flushing front buffer immediatly on screen.\n");
	    
	    ENTER_GL();
	    glGetIntegerv(GL_DRAW_BUFFER, &prev_draw);
	    glDrawBuffer(GL_FRONT);
	    /* Note: we do not use the application provided lock rectangle but our own stored at
	             lock time. This is because in old D3D versions, the 'lock' parameter did not
		     exist.
	    */
	    d3d_dev->flush_to_framebuffer(d3d_dev, &(gl_d3d_dev->lock_rect[WINE_GL_BUFFER_FRONT]), gl_d3d_dev->lock_surf[WINE_GL_BUFFER_FRONT]);
	    glDrawBuffer(prev_draw);
	    LEAVE_GL();
	} else {
	    gl_d3d_dev->state[WINE_GL_BUFFER_BACK] = SURFACE_MEMORY_DIRTY;
	}
    }

    /* And 'frees' the device critical section */
    LeaveCriticalSection(&(d3d_dev->crit));
}

static void
apply_texture_state(IDirect3DDeviceImpl *This)
{
    int stage, state;
    
    /* Initialize texture stages states */
    for (stage = 0; stage < MAX_TEXTURES; stage++) {
       for (state = 0; state < HIGHEST_TEXTURE_STAGE_STATE; state += 1) {
	   if (This->state_block.set_flags.texture_stage_state[stage][state] == TRUE) {
	       IDirect3DDevice7_SetTextureStageState(ICOM_INTERFACE(This, IDirect3DDevice7),
						     stage, state + 1, This->state_block.texture_stage_state[stage][state]);
	   }
       }
    }
}     

HRESULT
d3ddevice_create(IDirect3DDeviceImpl **obj, IDirectDrawImpl *d3d, IDirectDrawSurfaceImpl *surface)
{
    IDirect3DDeviceImpl *object;
    IDirect3DDeviceGLImpl *gl_object;
    IDirectDrawSurfaceImpl *surf;
    HDC device_context;
    XVisualInfo *vis;
    int num;
    int tex_num;
    XVisualInfo template;
    GLenum buffer = GL_FRONT;
    int light;
    
    object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IDirect3DDeviceGLImpl));
    if (object == NULL) return DDERR_OUTOFMEMORY;

    gl_object = (IDirect3DDeviceGLImpl *) object;
    
    object->ref = 1;
    object->d3d = d3d;
    object->surface = surface;
    object->set_context = set_context;
    object->clear = d3ddevice_clear_back;
    object->set_matrices = d3ddevice_set_matrices;
    object->matrices_updated = d3ddevice_matrices_updated;
    object->flush_to_framebuffer = d3ddevice_flush_to_frame_buffer;
    
    TRACE(" creating OpenGL device for surface = %p, d3d = %p\n", surface, d3d);

    InitializeCriticalSection(&(object->crit));

    TRACE(" device critical section : %p\n", &(object->crit));
    
    device_context = GetDC(surface->ddraw_owner->window);
    gl_object->display = get_display(device_context);
    gl_object->drawable = get_drawable(device_context);
    ReleaseDC(surface->ddraw_owner->window,device_context);

    ENTER_GL();
    template.visualid = (VisualID)GetPropA( GetDesktopWindow(), "__wine_x11_visual_id" );
    vis = XGetVisualInfo(gl_object->display, VisualIDMask, &template, &num);
    if (vis == NULL) {
        HeapFree(GetProcessHeap(), 0, object);
        ERR("No visual found !\n");
	LEAVE_GL();
	return DDERR_INVALIDPARAMS;
    } else {
        TRACE(" visual found\n");
    }

    gl_object->gl_context = glXCreateContext(gl_object->display, vis,
					     NULL, GL_TRUE);

    if (gl_object->gl_context == NULL) {
        HeapFree(GetProcessHeap(), 0, object);
        ERR("Error in context creation !\n");
	LEAVE_GL();
	return DDERR_INVALIDPARAMS;
    } else {
        TRACE(" context created (%p)\n", gl_object->gl_context);
    }
    
    /* Look for the front buffer and override its surface's Flip method (if in double buffering) */
    for (surf = surface; surf != NULL; surf = surf->surface_owner) {
        if ((surf->surface_desc.ddsCaps.dwCaps&(DDSCAPS_FLIP|DDSCAPS_FRONTBUFFER)) == (DDSCAPS_FLIP|DDSCAPS_FRONTBUFFER)) {
            surf->aux_ctx  = (LPVOID) object;
            surf->aux_data = (LPVOID) gl_object->drawable;
            surf->aux_flip = opengl_flip;
	    buffer =  GL_BACK;
            break;
        }
    }
    /* We are not doing any double buffering.. Then force OpenGL to draw on the front buffer */
    if (surf == NULL) {
        TRACE(" no double buffering : drawing on the front buffer\n");
        buffer = GL_FRONT;
    }
    
    for (surf = surface; surf != NULL; surf = surf->surface_owner) {
        IDirectDrawSurfaceImpl *surf2;
	for (surf2 = surf; surf2->prev_attached != NULL; surf2 = surf2->prev_attached) ;
	for (; surf2 != NULL; surf2 = surf2->next_attached) {
	    TRACE(" checking surface %p :", surf2);
	    if (((surf2->surface_desc.ddsCaps.dwCaps & (DDSCAPS_3DDEVICE)) == (DDSCAPS_3DDEVICE)) &&
		((surf2->surface_desc.ddsCaps.dwCaps & (DDSCAPS_ZBUFFER)) != (DDSCAPS_ZBUFFER))) {
	        /* Override the Lock / Unlock function for all these surfaces */
	        surf2->lock_update_prev = surf2->lock_update;
	        surf2->lock_update = d3ddevice_lock_update;
		surf2->unlock_update_prev = surf2->unlock_update;
		surf2->unlock_update = d3ddevice_unlock_update;
		/* And install also the blt / bltfast overrides */
		surf2->aux_blt = d3ddevice_blt;
		surf2->aux_bltfast = d3ddevice_bltfast;
		
		TRACE(" overiding direct surface access.\n");
	    } else {
	        TRACE(" no overide.\n");
	    }
	    surf2->d3ddevice = object;
	}
    }

    /* Set the various light parameters */
    for (light = 0; light < MAX_LIGHTS; light++) {
        /* Only set the fields that are not zero-created */
        object->light_parameters[light].dltType = D3DLIGHT_DIRECTIONAL;
	object->light_parameters[light].dcvDiffuse.u1.r = 1.0;
	object->light_parameters[light].dcvDiffuse.u2.g = 1.0;
	object->light_parameters[light].dcvDiffuse.u3.b = 1.0;
	object->light_parameters[light].dvDirection.u3.z = 1.0;
    }
    
    /* Allocate memory for the matrices */
    object->world_mat = (D3DMATRIX *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, 16 * sizeof(float));
    object->view_mat  = (D3DMATRIX *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, 16 * sizeof(float));
    object->proj_mat  = (D3DMATRIX *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, 16 * sizeof(float));
    memcpy(object->world_mat, id_mat, 16 * sizeof(float));
    memcpy(object->view_mat , id_mat, 16 * sizeof(float));
    memcpy(object->proj_mat , id_mat, 16 * sizeof(float));
    for (tex_num = 0; tex_num < MAX_TEXTURES; tex_num++) {
        object->tex_mat[tex_num] = (D3DMATRIX *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, 16 * sizeof(float));
	memcpy(object->tex_mat[tex_num], id_mat, 16 * sizeof(float));
	object->tex_mat_is_identity[tex_num] = TRUE;
    }
    
    /* Initialisation */
    TRACE(" setting current context\n");
    object->set_context(object);
    TRACE(" current context set\n");

    /* allocate the clipping planes */
    object->max_clipping_planes = opengl_device_caps.wMaxUserClipPlanes;
    object->clipping_planes = (d3d7clippingplane*)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, object->max_clipping_planes * sizeof(d3d7clippingplane));

    glHint(GL_FOG_HINT,GL_NICEST);

    /* Initialize the various GL contexts to be in sync with what we store locally */
    glClearDepth(0.0);
    glClearStencil(0);
    glClearColor(0.0, 0.0, 0.0, 0.0);
    glDepthMask(GL_TRUE);
    gl_object->depth_mask = TRUE;
    glEnable(GL_DEPTH_TEST);
    gl_object->depth_test = TRUE;
    glDisable(GL_ALPHA_TEST);
    glDisable(GL_STENCIL_TEST);
    glDisable(GL_CULL_FACE);
    glDisable(GL_LIGHTING);
    glDisable(GL_BLEND);
    glDisable(GL_FOG);
    glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
    gl_object->current_tex_env = GL_REPLACE;
    
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
    glDrawBuffer(buffer);
    glReadBuffer(buffer);
    /* glDisable(GL_DEPTH_TEST); Need here to check for the presence of a ZBuffer and to reenable it when the ZBuffer is attached */
    LEAVE_GL();

    gl_object->state[WINE_GL_BUFFER_BACK] = SURFACE_GL;
    gl_object->state[WINE_GL_BUFFER_FRONT] = SURFACE_GL;
    
    /* fill_device_capabilities(d3d->ddraw); */    
    
    ICOM_INIT_INTERFACE(object, IDirect3DDevice,  VTABLE_IDirect3DDevice);
    ICOM_INIT_INTERFACE(object, IDirect3DDevice2, VTABLE_IDirect3DDevice2);
    ICOM_INIT_INTERFACE(object, IDirect3DDevice3, VTABLE_IDirect3DDevice3);
    ICOM_INIT_INTERFACE(object, IDirect3DDevice7, VTABLE_IDirect3DDevice7);

    *obj = object;

    TRACE(" creating implementation at %p.\n", *obj);

    /* And finally warn D3D that this device is now present */
    object->d3d->d3d_added_device(object->d3d, object);

    /* FIXME: Should handle other versions than just 7 */
    InitDefaultStateBlock(&object->state_block, 7);
    /* Apply default render state and texture stage state values */
    apply_render_state(object, &object->state_block);
    apply_texture_state(object);

    /* And fill the fog table with the default fog value */
    build_fog_table(gl_object->fog_table, object->state_block.render_state[D3DRENDERSTATE_FOGCOLOR - 1]);
    
    return DD_OK;
}

static void fill_opengl_primcaps(D3DPRIMCAPS *pc)
{
    pc->dwSize = sizeof(*pc);
    pc->dwMiscCaps = D3DPMISCCAPS_CONFORMANT | D3DPMISCCAPS_CULLCCW | D3DPMISCCAPS_CULLCW |
      D3DPMISCCAPS_LINEPATTERNREP | D3DPMISCCAPS_MASKPLANES | D3DPMISCCAPS_MASKZ;
    pc->dwRasterCaps = D3DPRASTERCAPS_DITHER | D3DPRASTERCAPS_FOGRANGE | D3DPRASTERCAPS_FOGTABLE |
      D3DPRASTERCAPS_FOGVERTEX | D3DPRASTERCAPS_STIPPLE | D3DPRASTERCAPS_ZBIAS | D3DPRASTERCAPS_ZTEST | D3DPRASTERCAPS_SUBPIXEL |
	  D3DPRASTERCAPS_ZFOG;
    if (GL_extensions.mipmap_lodbias == TRUE) {
	pc->dwRasterCaps |= D3DPRASTERCAPS_MIPMAPLODBIAS;
    }
    pc->dwZCmpCaps = D3DPCMPCAPS_ALWAYS | D3DPCMPCAPS_EQUAL | D3DPCMPCAPS_GREATER | D3DPCMPCAPS_GREATEREQUAL |
      D3DPCMPCAPS_LESS | D3DPCMPCAPS_LESSEQUAL | D3DPCMPCAPS_NEVER | D3DPCMPCAPS_NOTEQUAL;
    pc->dwSrcBlendCaps  = D3DPBLENDCAPS_ZERO | D3DPBLENDCAPS_ONE | D3DPBLENDCAPS_DESTCOLOR | D3DPBLENDCAPS_INVDESTCOLOR |
      D3DPBLENDCAPS_SRCALPHA | D3DPBLENDCAPS_INVSRCALPHA | D3DPBLENDCAPS_DESTALPHA | D3DPBLENDCAPS_INVDESTALPHA | D3DPBLENDCAPS_SRCALPHASAT |
	D3DPBLENDCAPS_BOTHSRCALPHA | D3DPBLENDCAPS_BOTHINVSRCALPHA;
    pc->dwDestBlendCaps = D3DPBLENDCAPS_ZERO | D3DPBLENDCAPS_ONE | D3DPBLENDCAPS_SRCCOLOR | D3DPBLENDCAPS_INVSRCCOLOR |
      D3DPBLENDCAPS_SRCALPHA | D3DPBLENDCAPS_INVSRCALPHA | D3DPBLENDCAPS_DESTALPHA | D3DPBLENDCAPS_INVDESTALPHA | D3DPBLENDCAPS_SRCALPHASAT |
	D3DPBLENDCAPS_BOTHSRCALPHA | D3DPBLENDCAPS_BOTHINVSRCALPHA;
    pc->dwAlphaCmpCaps  = D3DPCMPCAPS_ALWAYS | D3DPCMPCAPS_EQUAL | D3DPCMPCAPS_GREATER | D3DPCMPCAPS_GREATEREQUAL |
      D3DPCMPCAPS_LESS | D3DPCMPCAPS_LESSEQUAL | D3DPCMPCAPS_NEVER | D3DPCMPCAPS_NOTEQUAL;
    pc->dwShadeCaps = D3DPSHADECAPS_ALPHAFLATBLEND | D3DPSHADECAPS_ALPHAGOURAUDBLEND | D3DPSHADECAPS_COLORFLATRGB | D3DPSHADECAPS_COLORGOURAUDRGB |
      D3DPSHADECAPS_FOGFLAT | D3DPSHADECAPS_FOGGOURAUD | D3DPSHADECAPS_SPECULARFLATRGB | D3DPSHADECAPS_SPECULARGOURAUDRGB;
    pc->dwTextureCaps = D3DPTEXTURECAPS_ALPHA | D3DPTEXTURECAPS_ALPHAPALETTE | D3DPTEXTURECAPS_BORDER | D3DPTEXTURECAPS_PERSPECTIVE |
      D3DPTEXTURECAPS_POW2 | D3DPTEXTURECAPS_TRANSPARENCY;
    pc->dwTextureFilterCaps = D3DPTFILTERCAPS_LINEAR | D3DPTFILTERCAPS_LINEARMIPLINEAR | D3DPTFILTERCAPS_LINEARMIPNEAREST |
      D3DPTFILTERCAPS_MIPLINEAR | D3DPTFILTERCAPS_MIPNEAREST | D3DPTFILTERCAPS_NEAREST | D3DPTFILTERCAPS_MAGFLINEAR |
	  D3DPTFILTERCAPS_MAGFPOINT | D3DPTFILTERCAPS_MINFLINEAR | D3DPTFILTERCAPS_MINFPOINT | D3DPTFILTERCAPS_MIPFLINEAR |
	      D3DPTFILTERCAPS_MIPFPOINT;
    pc->dwTextureBlendCaps = D3DPTBLENDCAPS_ADD | D3DPTBLENDCAPS_COPY | D3DPTBLENDCAPS_DECAL | D3DPTBLENDCAPS_DECALALPHA | D3DPTBLENDCAPS_DECALMASK |
      D3DPTBLENDCAPS_MODULATE | D3DPTBLENDCAPS_MODULATEALPHA | D3DPTBLENDCAPS_MODULATEMASK;
    pc->dwTextureAddressCaps = D3DPTADDRESSCAPS_BORDER | D3DPTADDRESSCAPS_CLAMP | D3DPTADDRESSCAPS_WRAP | D3DPTADDRESSCAPS_INDEPENDENTUV;
    if (GL_extensions.mirrored_repeat == TRUE) {
	pc->dwTextureAddressCaps |= D3DPTADDRESSCAPS_MIRROR;
    }
    pc->dwStippleWidth = 32;
    pc->dwStippleHeight = 32;
}

static void fill_caps(void)
{
    GLint max_clip_planes;
    
    /* Fill first all the fields with default values which will be overriden later on with
       corrent one from the GL code
    */
    opengl_device_caps.dwDevCaps = D3DDEVCAPS_CANRENDERAFTERFLIP | D3DDEVCAPS_DRAWPRIMTLVERTEX | D3DDEVCAPS_EXECUTESYSTEMMEMORY |
      D3DDEVCAPS_EXECUTEVIDEOMEMORY | D3DDEVCAPS_FLOATTLVERTEX | D3DDEVCAPS_TEXTURENONLOCALVIDMEM | D3DDEVCAPS_TEXTURESYSTEMMEMORY |
      D3DDEVCAPS_TEXTUREVIDEOMEMORY | D3DDEVCAPS_TLVERTEXSYSTEMMEMORY | D3DDEVCAPS_TLVERTEXVIDEOMEMORY |
      /* D3D 7 capabilities */
      D3DDEVCAPS_DRAWPRIMITIVES2 | D3DDEVCAPS_HWTRANSFORMANDLIGHT | D3DDEVCAPS_HWRASTERIZATION;
    fill_opengl_primcaps(&(opengl_device_caps.dpcLineCaps));
    fill_opengl_primcaps(&(opengl_device_caps.dpcTriCaps));
    opengl_device_caps.dwDeviceRenderBitDepth  = DDBD_16|DDBD_24|DDBD_32;
    opengl_device_caps.dwDeviceZBufferBitDepth = DDBD_16|DDBD_24|DDBD_32;
    opengl_device_caps.dwMinTextureWidth  = 1;
    opengl_device_caps.dwMinTextureHeight = 1;
    opengl_device_caps.dwMaxTextureWidth  = 1024;
    opengl_device_caps.dwMaxTextureHeight = 1024;
    opengl_device_caps.dwMaxTextureRepeat = 16;
    opengl_device_caps.dwMaxTextureAspectRatio = 1024;
    opengl_device_caps.dwMaxAnisotropy = 0;
    opengl_device_caps.dvGuardBandLeft = 0.0;
    opengl_device_caps.dvGuardBandRight = 0.0;
    opengl_device_caps.dvGuardBandTop = 0.0;
    opengl_device_caps.dvGuardBandBottom = 0.0;
    opengl_device_caps.dvExtentsAdjust = 0.0;
    opengl_device_caps.dwStencilCaps = D3DSTENCILCAPS_DECRSAT | D3DSTENCILCAPS_INCRSAT | D3DSTENCILCAPS_INVERT | D3DSTENCILCAPS_KEEP |
      D3DSTENCILCAPS_REPLACE | D3DSTENCILCAPS_ZERO;
    opengl_device_caps.dwFVFCaps = D3DFVFCAPS_DONOTSTRIPELEMENTS | 1;
    opengl_device_caps.dwTextureOpCaps = 0;
    opengl_device_caps.wMaxTextureBlendStages = 1;
    opengl_device_caps.wMaxSimultaneousTextures = 1;
    opengl_device_caps.dwMaxActiveLights = 16;
    opengl_device_caps.dvMaxVertexW = 100000000.0; /* No idea exactly what to put here... */
    opengl_device_caps.deviceGUID = IID_IDirect3DTnLHalDevice;
    opengl_device_caps.wMaxUserClipPlanes = 1;
    opengl_device_caps.wMaxVertexBlendMatrices = 0;
    opengl_device_caps.dwVertexProcessingCaps = D3DVTXPCAPS_TEXGEN | D3DVTXPCAPS_MATERIALSOURCE7 | D3DVTXPCAPS_VERTEXFOG |
	D3DVTXPCAPS_DIRECTIONALLIGHTS | D3DVTXPCAPS_POSITIONALLIGHTS | D3DVTXPCAPS_LOCALVIEWER;
    opengl_device_caps.dwReserved1 = 0;
    opengl_device_caps.dwReserved2 = 0;
    opengl_device_caps.dwReserved3 = 0;
    opengl_device_caps.dwReserved4 = 0;

    /* And now some GL overides :-) */
    glGetIntegerv(GL_MAX_TEXTURE_SIZE, (GLint *) &opengl_device_caps.dwMaxTextureWidth);
    opengl_device_caps.dwMaxTextureHeight = opengl_device_caps.dwMaxTextureWidth;
    opengl_device_caps.dwMaxTextureAspectRatio = opengl_device_caps.dwMaxTextureWidth;
    TRACE(": max texture size = %ld\n", opengl_device_caps.dwMaxTextureWidth);
    
    glGetIntegerv(GL_MAX_LIGHTS, (GLint *) &opengl_device_caps.dwMaxActiveLights);
    TRACE(": max active lights = %ld\n", opengl_device_caps.dwMaxActiveLights);

    glGetIntegerv(GL_MAX_CLIP_PLANES, &max_clip_planes);
    opengl_device_caps.wMaxUserClipPlanes = max_clip_planes;
    TRACE(": max clipping planes = %d\n", opengl_device_caps.wMaxUserClipPlanes);
}

BOOL
d3ddevice_init_at_startup(void *gl_handle)
{
    XVisualInfo template;
    XVisualInfo *vis;
    HDC device_context;
    Display *display;
    Visual *visual;
    Drawable drawable = (Drawable) GetPropA(GetDesktopWindow(), "__wine_x11_whole_window");
    XWindowAttributes win_attr;
    GLXContext gl_context;
    int num;
    const char *glExtensions;
    const char *glVersion;
    const char *glXExtensions = NULL;
    const void *(*pglXGetProcAddressARB)(const GLubyte *) = NULL;
    int major, minor, patch;
    
    TRACE("Initializing GL...\n");
    
    /* Get a default rendering context to have the 'caps' function query some info from GL */    
    device_context = GetDC(0);
    display = get_display(device_context);
    ReleaseDC(0, device_context);

    ENTER_GL();
    if (XGetWindowAttributes(display, drawable, &win_attr)) {
	visual = win_attr.visual;
    } else {
	visual = DefaultVisual(display, DefaultScreen(display));
    }
    template.visualid = XVisualIDFromVisual(visual);
    vis = XGetVisualInfo(display, VisualIDMask, &template, &num);
    if (vis == NULL) {
	LEAVE_GL();
	WARN("Error creating visual info for capabilities initialization - D3D support disabled !\n");
	return FALSE;
    }
    gl_context = glXCreateContext(display, vis, NULL, GL_TRUE);

    if (gl_context == NULL) {
	LEAVE_GL();
	WARN("Error creating default context for capabilities initialization - D3D support disabled !\n");
	return FALSE;
    }
    if (glXMakeCurrent(display, drawable, gl_context) == False) {
	glXDestroyContext(display, gl_context);
	LEAVE_GL();
	WARN("Error setting default context as current for capabilities initialization - D3D support disabled !\n");
	return FALSE;	
    }
    
    /* Then, query all extensions */
    glXExtensions = glXQueryExtensionsString(display, DefaultScreen(display));
    glExtensions = (const char *) glGetString(GL_EXTENSIONS);
    glVersion = (const char *) glGetString(GL_VERSION);
    if ((glXExtensions != NULL) && (gl_handle != NULL) && (strstr(glXExtensions, "GLX_ARB_get_proc_address"))) {
	pglXGetProcAddressARB = wine_dlsym(gl_handle, "glXGetProcAddressARB", NULL, 0);
    }
    
    /* Parse the GL version string */
    sscanf(glVersion, "%d.%d.%d", &major, &minor, &patch);
    TRACE("GL version %d.%d.%d\n", major, minor, patch);

    /* And starts to fill the extension context properly */
    memset(&GL_extensions, 0, sizeof(GL_extensions));
    TRACE("GL supports following extensions used by Wine :\n");
    
    /* Mirrored Repeat extension :
        - GL_ARB_texture_mirrored_repeat
	- GL_IBM_texture_mirrored_repeat
	- GL >= 1.4
    */
    if ((strstr(glExtensions, "GL_ARB_texture_mirrored_repeat")) ||
	(strstr(glExtensions, "GL_IBM_texture_mirrored_repeat")) ||
	((major >= 1) && (minor >= 4))) {
	TRACE(" - mirrored repeat\n");
	GL_extensions.mirrored_repeat = TRUE;
    }

    /* Texture LOD Bias :
         - GL_EXT_texture_lod_bias
    */
    if (strstr(glExtensions, "GL_EXT_texture_lod_bias")) {
	TRACE(" - texture lod bias\n");
	GL_extensions.mipmap_lodbias = TRUE;
    }
    
    /* Fill the D3D capabilities according to what GL tells us... */
    fill_caps();

    /* And frees this now-useless context */
    glXMakeCurrent(display, None, NULL);
    glXDestroyContext(display, gl_context);
    LEAVE_GL();
    
    return TRUE;
}
