From: Rémi Bernon rbernon@codeweavers.com
--- dlls/opengl32/unix_wgl.c | 124 +++++++++++++++++------------------ dlls/win32u/opengl.c | 116 +++++++++++++------------------- include/wine/opengl_driver.h | 14 +++- 3 files changed, 116 insertions(+), 138 deletions(-)
diff --git a/dlls/opengl32/unix_wgl.c b/dlls/opengl32/unix_wgl.c index 0dc9efef704..5994202f935 100644 --- a/dlls/opengl32/unix_wgl.c +++ b/dlls/opengl32/unix_wgl.c @@ -110,8 +110,10 @@ struct hint_state GLenum perspective_correction; };
-struct opengl_context +struct context { + struct wgl_context base; + HDC hdc; /* context creation DC */ HGLRC share; /* context to be shared with */ int *attribs; /* creation attributes */ @@ -120,7 +122,6 @@ struct opengl_context UINT64 debug_user; /* client pointer */ GLubyte *extensions; /* extension string */ GLuint *disabled_exts; /* indices of disabled extensions */ - struct wgl_context *drv_ctx; /* driver context */ GLubyte *wow64_version; /* wow64 GL version override */
/* semi-stub state tracker for wglCopyContext */ @@ -139,7 +140,7 @@ struct wgl_handle const struct opengl_funcs *funcs; union { - struct opengl_context *context; /* for HANDLE_CONTEXT */ + struct wgl_context *context; /* for HANDLE_CONTEXT */ struct wgl_pbuffer *pbuffer; /* for HANDLE_PBUFFER */ GLsync sync; /* for HANDLE_GLSYNC */ struct wgl_handle *next; /* for free handles */ @@ -151,11 +152,16 @@ static struct wgl_handle wgl_handles[MAX_WGL_HANDLES]; static struct wgl_handle *next_free; static unsigned int handle_count;
+static struct context *context_from_wgl_context( struct wgl_context *context ) +{ + return CONTAINING_RECORD( context, struct context, base ); +} + /* the current context is assumed valid and doesn't need locking */ -static struct opengl_context *get_current_context( TEB *teb ) +static struct context *get_current_context( TEB *teb ) { if (!teb->glCurrentRC) return NULL; - return wgl_handles[LOWORD(teb->glCurrentRC) & ~HANDLE_TYPE_MASK].u.context; + return context_from_wgl_context( wgl_handles[LOWORD(teb->glCurrentRC) & ~HANDLE_TYPE_MASK].u.context ); }
static inline HANDLE next_handle( struct wgl_handle *ptr, enum wgl_handle_type type ) @@ -186,7 +192,7 @@ struct context_attribute_desc
static struct context_attribute_desc context_attributes[] = { -#define CONTEXT_ATTRIBUTE_DESC(bit, name, field) [name] = { bit, offsetof(struct opengl_context, field), sizeof(((struct opengl_context *)0)->field) } +#define CONTEXT_ATTRIBUTE_DESC(bit, name, field) [name] = { bit, offsetof(struct context, field), sizeof(((struct context *)0)->field) } CONTEXT_ATTRIBUTE_DESC( GL_COLOR_BUFFER_BIT, GL_COLOR_CLEAR_VALUE, color_buffer.clear_color ), CONTEXT_ATTRIBUTE_DESC( GL_DEPTH_BUFFER_BIT, GL_DEPTH_FUNC, depth_buffer.depth_func ), CONTEXT_ATTRIBUTE_DESC( GL_ENABLE_BIT, GL_CULL_FACE, enable.cull_face ), @@ -208,7 +214,7 @@ C_ASSERT( sizeof(context_attributes) <= 64 * 1024 );
void set_context_attribute( TEB *teb, GLenum name, const void *value, size_t size ) { - struct opengl_context *ctx = get_current_context( teb ); + struct context *ctx = get_current_context( teb ); GLbitfield bit;
if (!(ctx = get_current_context( teb ))) return; @@ -221,11 +227,11 @@ void set_context_attribute( TEB *teb, GLenum name, const void *value, size_t siz ctx->used |= bit; }
-static BOOL copy_context_attributes( TEB *teb, const struct opengl_funcs *funcs, HGLRC dst_handle, struct opengl_context *dst, - HGLRC src_handle, struct opengl_context *src, GLbitfield mask ) +static BOOL copy_context_attributes( TEB *teb, const struct opengl_funcs *funcs, HGLRC dst_handle, struct context *dst, + HGLRC src_handle, struct context *src, GLbitfield mask ) { HDC draw_hdc = teb->glReserved1[0], read_hdc = teb->glReserved1[1]; - struct opengl_context *old_ctx = get_current_context( teb ); + struct context *old_ctx = get_current_context( teb ); const struct opengl_funcs *old_funcs = teb->glTable;
if (dst == old_ctx) @@ -238,7 +244,7 @@ static BOOL copy_context_attributes( TEB *teb, const struct opengl_funcs *funcs, if (src->used == -1) FIXME( "Unsupported attributes on context %p/%p\n", src_handle, src ); if (src != dst && dst->used == -1) FIXME( "Unsupported attributes on context %p/%p\n", dst_handle, dst );
- funcs->p_wglMakeCurrent( dst->hdc, dst->drv_ctx ); + funcs->p_wglMakeCurrent( dst->hdc, &dst->base );
if (mask & GL_COLOR_BUFFER_BIT) { @@ -287,46 +293,40 @@ static BOOL copy_context_attributes( TEB *teb, const struct opengl_funcs *funcs, dst->used |= (src->used & mask);
if (!old_ctx) funcs->p_wglMakeCurrent( NULL, NULL ); - else if (!old_funcs->p_wglMakeContextCurrentARB) old_funcs->p_wglMakeCurrent( draw_hdc, old_ctx->drv_ctx ); - else old_funcs->p_wglMakeContextCurrentARB( draw_hdc, read_hdc, old_ctx->drv_ctx ); + else if (!old_funcs->p_wglMakeContextCurrentARB) old_funcs->p_wglMakeCurrent( draw_hdc, &old_ctx->base ); + else old_funcs->p_wglMakeContextCurrentARB( draw_hdc, read_hdc, &old_ctx->base );
return dst->used != -1 && src->used != -1; }
-static struct opengl_context *opengl_context_from_handle( TEB *teb, HGLRC handle, const struct opengl_funcs **funcs ); +static struct context *opengl_context_from_handle( TEB *teb, HGLRC handle, const struct opengl_funcs **funcs );
/* update handle context if it has been re-shared with another one */ static void update_handle_context( TEB *teb, HGLRC handle, struct wgl_handle *ptr ) { - struct opengl_context *ctx = ptr->u.context, *shared; + struct context *ctx = context_from_wgl_context( ptr->u.context ), *shared; const struct opengl_funcs *funcs = ptr->funcs, *share_funcs; - struct wgl_context *(*func)( HDC hDC, struct wgl_context * hShareContext, const int *attribList ); - struct wgl_context *prev = ctx->drv_ctx, *drv_ctx;
if (ctx->tid) return; /* currently in use */ if (ctx->share == (HGLRC)-1) return; /* not re-shared */ - if (!(func = funcs->p_wglCreateContextAttribsARB)) func = (void *)funcs->p_wglGetProcAddress( "wglCreateContextAttribsARB" ); - if (!func) return; /* not supported */
shared = ctx->share ? opengl_context_from_handle( teb, ctx->share, &share_funcs ) : NULL; - if (!(drv_ctx = func( ctx->hdc, shared ? shared->drv_ctx : NULL, ctx->attribs ))) + if (!funcs->p_wgl_context_reset( &ctx->base, ctx->hdc, shared ? &shared->base : NULL, ctx->attribs )) { WARN( "Failed to re-create context for wglShareLists\n" ); return; } ctx->share = (HGLRC)-1; /* initial shared context */ - ctx->drv_ctx = drv_ctx; copy_context_attributes( teb, funcs, handle, ctx, handle, ctx, ctx->used ); - funcs->p_wglDeleteContext( prev ); }
-static struct opengl_context *opengl_context_from_handle( TEB *teb, HGLRC handle, const struct opengl_funcs **funcs ) +static struct context *opengl_context_from_handle( TEB *teb, HGLRC handle, const struct opengl_funcs **funcs ) { struct wgl_handle *entry; if (!(entry = get_handle_ptr( handle ))) return NULL; update_handle_context( teb, handle, entry ); *funcs = entry->funcs; - return entry->u.context; + return context_from_wgl_context( entry->u.context ); }
static struct wgl_pbuffer *wgl_pbuffer_from_handle( HPBUFFERARB handle, const struct opengl_funcs **funcs ) @@ -715,7 +715,7 @@ static BOOL filter_extensions( TEB * teb, const char *extensions, GLubyte **exts
static const GLuint *disabled_extensions_index( TEB *teb ) { - struct opengl_context *ctx = get_current_context( teb ); + struct context *ctx = get_current_context( teb ); GLuint **disabled = &ctx->disabled_exts; if (*disabled || filter_extensions( teb, NULL, NULL, disabled )) return *disabled; return NULL; @@ -815,14 +815,14 @@ const GLubyte *wrap_glGetString( TEB *teb, GLenum name ) { if (name == GL_EXTENSIONS) { - struct opengl_context *ctx = get_current_context( teb ); + struct context *ctx = get_current_context( teb ); GLubyte **extensions = &ctx->extensions; GLuint **disabled = &ctx->disabled_exts; if (*extensions || filter_extensions( teb, (const char *)ret, extensions, disabled )) return *extensions; } else if (name == GL_VERSION && is_win64 && is_wow64()) { - struct opengl_context *ctx = get_current_context( teb ); + struct context *ctx = get_current_context( teb ); GLubyte **str = &ctx->wow64_version; int major, minor;
@@ -891,7 +891,7 @@ static char *build_extension_list( TEB *teb )
static UINT get_context_major_version( TEB *teb ) { - struct opengl_context *ctx; + struct context *ctx;
if (!(ctx = get_current_context( teb ))) return TRUE; for (const int *attr = ctx->attribs; attr && attr[0]; attr += 2) @@ -988,7 +988,7 @@ PROC wrap_wglGetProcAddress( TEB *teb, LPCSTR name ) BOOL wrap_wglCopyContext( TEB *teb, HGLRC hglrcSrc, HGLRC hglrcDst, UINT mask ) { const struct opengl_funcs *src_funcs, *dst_funcs; - struct opengl_context *src, *dst; + struct context *src, *dst; BOOL ret = FALSE;
if (!(src = opengl_context_from_handle( teb, hglrcSrc, &src_funcs ))) return FALSE; @@ -1001,27 +1001,26 @@ BOOL wrap_wglCopyContext( TEB *teb, HGLRC hglrcSrc, HGLRC hglrcDst, UINT mask ) HGLRC wrap_wglCreateContext( TEB *teb, HDC hdc ) { HGLRC ret = 0; - struct wgl_context *drv_ctx; - struct opengl_context *context; + struct context *context; const struct opengl_funcs *funcs = get_dc_funcs( hdc );
if (!funcs) return 0; - if (!(drv_ctx = funcs->p_wglCreateContext( hdc ))) return 0; - if ((context = calloc( 1, sizeof(*context) ))) + if (!(context = calloc( 1, sizeof(*context) ))) return 0; + context->hdc = hdc; + context->share = (HGLRC)-1; /* initial shared context */ + if (!funcs->p_wgl_context_reset( &context->base, hdc, NULL, NULL )) free( context ); + else if (!(ret = alloc_handle( HANDLE_CONTEXT, funcs, context ))) { - context->hdc = hdc; - context->share = (HGLRC)-1; /* initial shared context */ - context->drv_ctx = drv_ctx; - if (!(ret = alloc_handle( HANDLE_CONTEXT, funcs, context ))) free( context ); + funcs->p_wgl_context_reset( &context->base, NULL, NULL, NULL ); + free( context ); } - if (!ret) funcs->p_wglDeleteContext( drv_ctx ); return ret; }
BOOL wrap_wglMakeCurrent( TEB *teb, HDC hdc, HGLRC hglrc ) { DWORD tid = HandleToULong(teb->ClientId.UniqueThread); - struct opengl_context *ctx, *prev = get_current_context( teb ); + struct context *ctx, *prev = get_current_context( teb ); const struct opengl_funcs *funcs = teb->glTable;
if (hglrc) @@ -1033,7 +1032,7 @@ BOOL wrap_wglMakeCurrent( TEB *teb, HDC hdc, HGLRC hglrc ) return FALSE; }
- if (!funcs->p_wglMakeCurrent( hdc, ctx->drv_ctx )) return FALSE; + if (!funcs->p_wglMakeCurrent( hdc, &ctx->base )) return FALSE; if (prev) prev->tid = 0; ctx->tid = tid; teb->glReserved1[0] = hdc; @@ -1060,18 +1059,18 @@ BOOL wrap_wglMakeCurrent( TEB *teb, HDC hdc, HGLRC hglrc ) BOOL wrap_wglDeleteContext( TEB *teb, HGLRC hglrc ) { struct wgl_handle *ptr; - struct opengl_context *ctx; + struct context *ctx; DWORD tid = HandleToULong(teb->ClientId.UniqueThread);
if (!(ptr = get_handle_ptr( hglrc ))) return FALSE; - ctx = ptr->u.context; + ctx = context_from_wgl_context( ptr->u.context ); if (ctx->tid && ctx->tid != tid) { RtlSetLastWin32Error( ERROR_BUSY ); return FALSE; } if (hglrc == teb->glCurrentRC) wrap_wglMakeCurrent( teb, 0, 0 ); - ptr->funcs->p_wglDeleteContext( ctx->drv_ctx ); + ptr->funcs->p_wgl_context_reset( &ctx->base, NULL, NULL, NULL ); free( ctx->wow64_version ); free( ctx->disabled_exts ); free( ctx->extensions ); @@ -1083,10 +1082,10 @@ BOOL wrap_wglDeleteContext( TEB *teb, HGLRC hglrc )
static void flush_context( TEB *teb, void (*flush)(void) ) { - struct opengl_context *ctx = get_current_context( teb ); + struct context *ctx = get_current_context( teb ); const struct opengl_funcs *funcs = teb->glTable;
- if (!ctx || !funcs->p_wgl_context_flush( ctx->drv_ctx, flush )) + if (!ctx || !funcs->p_wgl_context_flush( &ctx->base, flush )) { /* default implementation: call the functions directly */ if (flush) flush(); @@ -1150,7 +1149,7 @@ BOOL wrap_wglSwapBuffers( TEB *teb, HDC hdc ) BOOL wrap_wglShareLists( TEB *teb, HGLRC hglrcSrc, HGLRC hglrcDst ) { const struct opengl_funcs *src_funcs, *dst_funcs; - struct opengl_context *src, *dst; + struct context *src, *dst; BOOL ret = FALSE;
if (!(src = opengl_context_from_handle( teb, hglrcSrc, &src_funcs ))) return FALSE; @@ -1173,8 +1172,7 @@ BOOL wrap_wglBindTexImageARB( TEB *teb, HPBUFFERARB handle, int buffer ) HGLRC wrap_wglCreateContextAttribsARB( TEB *teb, HDC hdc, HGLRC share, const int *attribs ) { HGLRC ret = 0; - struct wgl_context *drv_ctx; - struct opengl_context *context, *share_ctx = NULL; + struct context *context, *share_ctx = NULL; const struct opengl_funcs *funcs = get_dc_funcs( hdc ), *share_funcs;
if (!funcs) @@ -1182,25 +1180,23 @@ HGLRC wrap_wglCreateContextAttribsARB( TEB *teb, HDC hdc, HGLRC share, const int RtlSetLastWin32Error( ERROR_DC_NOT_FOUND ); return 0; } - if (!funcs->p_wglCreateContextAttribsARB) return 0; if (share && !(share_ctx = opengl_context_from_handle( teb, share, &share_funcs ))) { RtlSetLastWin32Error( ERROR_INVALID_OPERATION ); return 0; } - if ((drv_ctx = funcs->p_wglCreateContextAttribsARB( hdc, share_ctx ? share_ctx->drv_ctx : NULL, attribs ))) + if ((context = calloc( 1, sizeof(*context) ))) { - if ((context = calloc( 1, sizeof(*context) ))) + context->hdc = hdc; + context->share = (HGLRC)-1; /* initial shared context */ + context->attribs = memdup_attribs( attribs ); + if (!(funcs->p_wgl_context_reset( &context->base, hdc, share_ctx ? &share_ctx->base : NULL, attribs ))) free( context ); + else if (!(ret = alloc_handle( HANDLE_CONTEXT, funcs, context ))) { - context->hdc = hdc; - context->share = (HGLRC)-1; /* initial shared context */ - context->attribs = memdup_attribs( attribs ); - context->drv_ctx = drv_ctx; - if (!(ret = alloc_handle( HANDLE_CONTEXT, funcs, context ))) free( context ); + funcs->p_wgl_context_reset( &context->base, NULL, NULL, NULL ); + free( context ); } - if (!ret) funcs->p_wglDeleteContext( drv_ctx ); } - return ret; }
@@ -1240,7 +1236,7 @@ HDC wrap_wglGetPbufferDCARB( TEB *teb, HPBUFFERARB handle ) BOOL wrap_wglMakeContextCurrentARB( TEB *teb, HDC draw_hdc, HDC read_hdc, HGLRC hglrc ) { DWORD tid = HandleToULong(teb->ClientId.UniqueThread); - struct opengl_context *ctx, *prev = get_current_context( teb ); + struct context *ctx, *prev = get_current_context( teb ); const struct opengl_funcs *funcs = teb->glTable;
if (hglrc) @@ -1253,7 +1249,7 @@ BOOL wrap_wglMakeContextCurrentARB( TEB *teb, HDC draw_hdc, HDC read_hdc, HGLRC }
if (!funcs->p_wglMakeContextCurrentARB) return FALSE; - if (!funcs->p_wglMakeContextCurrentARB( draw_hdc, read_hdc, ctx->drv_ctx )) return FALSE; + if (!funcs->p_wglMakeContextCurrentARB( draw_hdc, read_hdc, &ctx->base )) return FALSE; if (prev) prev->tid = 0; ctx->tid = tid; teb->glReserved1[0] = draw_hdc; @@ -1310,7 +1306,7 @@ static void gl_debug_message_callback( GLenum source, GLenum type, GLuint id, GL struct gl_debug_message_callback_params *params; void *ret_ptr; ULONG ret_len; - struct opengl_context *ctx = (struct opengl_context *)user; + struct context *ctx = (struct context *)user; UINT len = strlen( message ) + 1, size;
if (!ctx->debug_callback) return; @@ -1339,7 +1335,7 @@ static void gl_debug_message_callback( GLenum source, GLenum type, GLuint id, GL
void wrap_glDebugMessageCallback( TEB *teb, GLDEBUGPROC callback, const void *user ) { - struct opengl_context *ctx = get_current_context( teb ); + struct context *ctx = get_current_context( teb ); const struct opengl_funcs *funcs = teb->glTable;
if (!funcs->p_glDebugMessageCallback) return; @@ -1352,7 +1348,7 @@ void wrap_glDebugMessageCallback( TEB *teb, GLDEBUGPROC callback, const void *us
void wrap_glDebugMessageCallbackAMD( TEB *teb, GLDEBUGPROCAMD callback, void *user ) { - struct opengl_context *ctx = get_current_context( teb ); + struct context *ctx = get_current_context( teb ); const struct opengl_funcs *funcs = teb->glTable;
if (!funcs->p_glDebugMessageCallbackAMD) return; @@ -1365,7 +1361,7 @@ void wrap_glDebugMessageCallbackAMD( TEB *teb, GLDEBUGPROCAMD callback, void *us
void wrap_glDebugMessageCallbackARB( TEB *teb, GLDEBUGPROCARB callback, const void *user ) { - struct opengl_context *ctx = get_current_context( teb ); + struct context *ctx = get_current_context( teb ); const struct opengl_funcs *funcs = teb->glTable;
if (!funcs->p_glDebugMessageCallbackARB) return; diff --git a/dlls/win32u/opengl.c b/dlls/win32u/opengl.c index 9bb4a24339b..338fc4cfe73 100644 --- a/dlls/win32u/opengl.c +++ b/dlls/win32u/opengl.c @@ -39,15 +39,6 @@
WINE_DEFAULT_DEBUG_CHANNEL(wgl);
-struct wgl_context -{ - void *driver_private; - void *internal_context; - int pixel_format; - struct opengl_drawable *draw; - struct opengl_drawable *read; -}; - struct wgl_pbuffer { struct opengl_drawable *drawable; @@ -1175,7 +1166,7 @@ static BOOL create_memory_pbuffer( HDC hdc, int format ) } release_dc_ptr( dc );
- if (ret) + if (ret && format) { int width = dib.rect.right - dib.rect.left, height = dib.rect.bottom - dib.rect.top; struct wgl_pbuffer *pbuffer; @@ -1293,49 +1284,6 @@ static void win32u_get_pixel_formats( struct wgl_pixel_format *formats, UINT max *num_onscreen_formats = onscreen_count; }
-static struct wgl_context *context_create( HDC hdc, struct wgl_context *shared, const int *attribs ) -{ - void *shared_private = shared ? shared->driver_private : NULL; - struct wgl_context *context; - int format; - - TRACE( "hdc %p, shared %p, attribs %p\n", hdc, shared, attribs ); - - if ((format = get_dc_pixel_format( hdc, TRUE )) <= 0) - { - if (!format) RtlSetLastWin32Error( ERROR_INVALID_PIXEL_FORMAT ); - return NULL; - } - - if (!(context = calloc( 1, sizeof(*context) ))) return NULL; - context->pixel_format = format; - - if (!driver_funcs->p_context_create( format, shared_private, attribs, &context->driver_private )) - { - free( context ); - return NULL; - } - - TRACE( "created context %p, format %u for driver context %p\n", context, format, context->driver_private ); - return context; -} - -static struct wgl_context *win32u_wglCreateContextAttribsARB( HDC hdc, struct wgl_context *shared, const int *attribs ) -{ - static const int empty_attribs = {0}; - - TRACE( "hdc %p, shared %p, attribs %p\n", hdc, shared, attribs ); - - if (!attribs) attribs = &empty_attribs; - return context_create( hdc, shared, attribs ); -} - -static struct wgl_context *win32u_wglCreateContext( HDC hdc ) -{ - TRACE( "hdc %p\n", hdc ); - return context_create( hdc, NULL, NULL ); -} - static void context_set_drawables( struct wgl_context *context, struct opengl_drawable *new_draw, struct opengl_drawable *new_read ) { struct opengl_drawable *old_draw = context->draw, *old_read = context->read; @@ -1370,7 +1318,7 @@ static BOOL context_sync_drawables( struct wgl_context *context, HDC draw_hdc, H BOOL ret = FALSE, flush; HWND hwnd;
- flush = create_memory_pbuffer( draw_hdc, context->pixel_format ); + flush = create_memory_pbuffer( draw_hdc, context->format ); new_draw = get_dc_opengl_drawable( draw_hdc );
/* get the last used window drawable when reading */ @@ -1423,19 +1371,6 @@ static BOOL context_sync_drawables( struct wgl_context *context, HDC draw_hdc, H return ret; }
-static BOOL win32u_wglDeleteContext( struct wgl_context *context ) -{ - BOOL ret; - - TRACE( "context %p\n", context ); - - if (context->internal_context) driver_funcs->p_context_destroy( context->internal_context ); - ret = driver_funcs->p_context_destroy( context->driver_private ); - free( context ); - - return ret; -} - static void push_internal_context( struct wgl_context *context, HDC hdc, int format ) { TRACE( "context %p, hdc %p\n", context, hdc ); @@ -1477,9 +1412,9 @@ static BOOL win32u_wglMakeContextCurrentARB( HDC draw_hdc, HDC read_hdc, struct if (!format) RtlSetLastWin32Error( ERROR_INVALID_PIXEL_FORMAT ); return FALSE; } - if (context->pixel_format != format) + if (context->format != format) { - WARN( "Mismatched draw_hdc %p format %u, context %p format %u\n", draw_hdc, format, context, context->pixel_format ); + WARN( "Mismatched draw_hdc %p format %u, context %p format %u\n", draw_hdc, format, context, context->format ); RtlSetLastWin32Error( ERROR_INVALID_PIXEL_FORMAT ); return FALSE; } @@ -1908,6 +1843,42 @@ static int get_window_swap_interval( HWND hwnd ) return interval; }
+static BOOL win32u_wgl_context_reset( struct wgl_context *context, HDC hdc, struct wgl_context *share, const int *attribs ) +{ + void *share_private = share ? share->driver_private : NULL; + int format; + + TRACE( "context %p, hdc %p, share %p, attribs %p\n", context, hdc, share, attribs ); + + if (context->internal_context) + { + driver_funcs->p_context_destroy( context->internal_context ); + context->internal_context = NULL; + } + if (context->driver_private && !driver_funcs->p_context_destroy( context->driver_private )) + { + WARN( "Failed to destroy driver context %p\n", context->driver_private ); + return FALSE; + } + context->driver_private = NULL; + if (!hdc) return TRUE; + + if ((format = get_dc_pixel_format( hdc, TRUE )) <= 0) + { + if (!format) RtlSetLastWin32Error( ERROR_INVALID_PIXEL_FORMAT ); + return FALSE; + } + if (!driver_funcs->p_context_create( format, share_private, attribs, &context->driver_private )) + { + WARN( "Failed to create driver context for context %p\n", context ); + return FALSE; + } + context->format = format; + + TRACE( "reset context %p, format %u for driver context %p\n", context, format, context->driver_private ); + return TRUE; +} + static BOOL win32u_wgl_context_flush( struct wgl_context *context, void (*flush)(void) ) { HDC draw_hdc = NtCurrentTeb()->glReserved1[0], read_hdc = NtCurrentTeb()->glReserved1[1]; @@ -2046,13 +2017,14 @@ static void display_funcs_init(void) display_funcs.p_wglGetPixelFormat = win32u_wglGetPixelFormat; display_funcs.p_wglSetPixelFormat = win32u_wglSetPixelFormat;
- display_funcs.p_wglCreateContext = win32u_wglCreateContext; - display_funcs.p_wglDeleteContext = win32u_wglDeleteContext; + display_funcs.p_wglCreateContext = (void *)1; /* never called */ + display_funcs.p_wglDeleteContext = (void *)1; /* never called */ display_funcs.p_wglCopyContext = (void *)1; /* never called */ display_funcs.p_wglShareLists = (void *)1; /* never called */ display_funcs.p_wglMakeCurrent = win32u_wglMakeCurrent;
display_funcs.p_wglSwapBuffers = win32u_wglSwapBuffers; + display_funcs.p_wgl_context_reset = win32u_wgl_context_reset; display_funcs.p_wgl_context_flush = win32u_wgl_context_flush;
if (display_egl.has_EGL_EXT_pixel_format_float) @@ -2081,7 +2053,7 @@ static void display_funcs_init(void) register_extension( wgl_extensions, ARRAY_SIZE(wgl_extensions), "WGL_ARB_create_context" ); register_extension( wgl_extensions, ARRAY_SIZE(wgl_extensions), "WGL_ARB_create_context_no_error" ); register_extension( wgl_extensions, ARRAY_SIZE(wgl_extensions), "WGL_ARB_create_context_profile" ); - display_funcs.p_wglCreateContextAttribsARB = win32u_wglCreateContextAttribsARB; + display_funcs.p_wglCreateContextAttribsARB = (void *)1; /* never called */
register_extension( wgl_extensions, ARRAY_SIZE(wgl_extensions), "WGL_ARB_make_current_read" ); display_funcs.p_wglGetCurrentReadDCARB = (void *)1; /* never called */ diff --git a/include/wine/opengl_driver.h b/include/wine/opengl_driver.h index 386f8969b1b..2a0cdb6859b 100644 --- a/include/wine/opengl_driver.h +++ b/include/wine/opengl_driver.h @@ -66,12 +66,23 @@ struct wgl_pixel_format /* Wine internal opengl driver version, needs to be bumped upon opengl_funcs changes. */ #define WINE_OPENGL_DRIVER_VERSION 36
+struct opengl_drawable; struct wgl_context; struct wgl_pbuffer;
+struct wgl_context +{ + void *driver_private; /* driver context / private data */ + void *internal_context; /* driver context for win32u internal use */ + int format; /* pixel format of the context */ + struct opengl_drawable *draw; /* currently bound draw surface */ + struct opengl_drawable *read; /* currently bound read surface */ +}; + /* interface between opengl32 and win32u */ struct opengl_funcs { + BOOL (*p_wgl_context_reset)( struct wgl_context *context, HDC hdc, struct wgl_context *share, const int *attribs ); BOOL (*p_wgl_context_flush)( struct wgl_context *context, void (*flush)(void) ); BOOL (*p_wglCopyContext)( struct wgl_context * hglrcSrc, struct wgl_context * hglrcDst, UINT mask ); struct wgl_context * (*p_wglCreateContext)( HDC hDc ); @@ -131,8 +142,6 @@ struct egl_platform BOOL has_EGL_EXT_pixel_format_float; };
-/* a driver opengl drawable, either a client surface of a pbuffer */ -struct opengl_drawable; struct opengl_drawable_funcs { void (*destroy)( struct opengl_drawable *iface ); @@ -149,6 +158,7 @@ struct opengl_drawable_funcs #define GL_FLUSH_WAS_CURRENT 0x08 #define GL_FLUSH_SET_CURRENT 0x10
+/* a driver opengl drawable, either a client surface of a pbuffer */ struct opengl_drawable { const struct opengl_drawable_funcs *funcs;