mirror of
https://git.code.sf.net/p/quake/quakeforge
synced 2024-11-25 22:01:33 +00:00
[vid] Allow render systems to unload late
This cleans up the tangled mess of attempting to unload the gl driver in X11: for whatever reason, the display gets tied in to the library.
This commit is contained in:
parent
5821ef8d1f
commit
f12b3ea134
19 changed files with 85 additions and 64 deletions
|
@ -57,13 +57,14 @@ void Win_UpdateWindowStatus (int x, int y);
|
|||
void Win_SetCaption (const char *text);
|
||||
qboolean Win_SetGamma (double gamma);
|
||||
|
||||
struct gl_ctx_s *Win_GL_Context (void);
|
||||
struct vid_internal_s;
|
||||
struct gl_ctx_s *Win_GL_Context (struct vid_internal_s *);
|
||||
void Win_GL_Init_Cvars (void);
|
||||
|
||||
struct sw_ctx_s *Win_SW_Context (void);
|
||||
struct sw_ctx_s *Win_SW_Context (struct vid_internal_s *);
|
||||
void Win_SW_Init_Cvars (void);
|
||||
|
||||
struct vulkan_ctx_s *Win_Vulkan_Context (void);
|
||||
struct vulkan_ctx_s *Win_Vulkan_Context (struct vid_internal_s *);
|
||||
void Win_Vulkan_Init_Cvars (void);
|
||||
|
||||
void IN_UpdateClipCursor (void);
|
||||
|
|
|
@ -80,13 +80,14 @@ void X11_SaveMouseAcceleration (void);
|
|||
void X11_RemoveMouseAcceleration (void);
|
||||
void X11_RestoreMouseAcceleration (void);
|
||||
|
||||
struct gl_ctx_s *X11_GL_Context (void);
|
||||
struct vid_internal_s;
|
||||
struct gl_ctx_s *X11_GL_Context (struct vid_internal_s *);
|
||||
void X11_GL_Init_Cvars (void);
|
||||
|
||||
struct sw_ctx_s *X11_SW_Context (void);
|
||||
struct sw_ctx_s *X11_SW_Context (struct vid_internal_s *);
|
||||
void X11_SW_Init_Cvars (void);
|
||||
|
||||
struct vulkan_ctx_s *X11_Vulkan_Context (void);
|
||||
struct vulkan_ctx_s *X11_Vulkan_Context (struct vid_internal_s *);
|
||||
void X11_Vulkan_Init_Cvars (void);
|
||||
|
||||
#endif // __context_x11_h_
|
||||
|
|
|
@ -8,8 +8,7 @@ typedef struct GL_context *GL_context;
|
|||
|
||||
typedef struct gl_ctx_s {
|
||||
GL_context context;
|
||||
void (*load_gl) (void);
|
||||
void (*unload_gl) (struct gl_ctx_s *ctx);
|
||||
void (*load_gl) (struct gl_ctx_s *ctx);
|
||||
void (*choose_visual) (struct gl_ctx_s *ctx);
|
||||
void (*create_context) (struct gl_ctx_s *ctx, int core);
|
||||
void (*init_gl) (void);
|
||||
|
|
|
@ -15,19 +15,21 @@ typedef struct vid_system_s {
|
|||
extern vid_system_t vid_system;
|
||||
|
||||
typedef struct vid_internal_s {
|
||||
void (*flush_caches) (void *data);
|
||||
void (*init_buffers) (void *data);
|
||||
void (*set_palette) (void *data, const byte *palette);
|
||||
void (*set_colormap) (void *data, const byte *colormap);
|
||||
void (*flush_caches) (void *ctx);
|
||||
void (*init_buffers) (void *ctx);
|
||||
void (*set_palette) (void *ctx, const byte *palette);
|
||||
void (*set_colormap) (void *ctx, const byte *colormap);
|
||||
|
||||
void (*choose_visual) (void *data);
|
||||
void (*create_context) (void *data);
|
||||
void (*choose_visual) (void *ctx);
|
||||
void (*create_context) (void *ctx);
|
||||
|
||||
void *data;
|
||||
void *ctx;
|
||||
|
||||
struct gl_ctx_s *(*gl_context) (void);
|
||||
struct sw_ctx_s *(*sw_context) (void);
|
||||
struct vulkan_ctx_s *(*vulkan_context) (void);
|
||||
struct gl_ctx_s *(*gl_context) (struct vid_internal_s *);
|
||||
struct sw_ctx_s *(*sw_context) (struct vid_internal_s *);
|
||||
struct vulkan_ctx_s *(*vulkan_context) (struct vid_internal_s *);
|
||||
|
||||
void (*unload) (void *data);
|
||||
} vid_internal_t;
|
||||
|
||||
extern int vid_fullscreen;
|
||||
|
|
|
@ -55,12 +55,12 @@ d_vidsize_listener (void *data, const viddef_t *vid)
|
|||
int cachesize = D_SurfaceCacheForRes (vid->width, vid->height);
|
||||
|
||||
if (surfcache) {
|
||||
D_FlushCaches (vid->vid_internal->data);
|
||||
D_FlushCaches (vid->vid_internal->ctx);
|
||||
free (surfcache);
|
||||
surfcache = 0;
|
||||
}
|
||||
surfcache = calloc (cachesize, 1);
|
||||
vid->vid_internal->init_buffers (vid->vid_internal->data);
|
||||
vid->vid_internal->init_buffers (vid->vid_internal->ctx);
|
||||
D_InitCaches (surfcache, cachesize);
|
||||
|
||||
viddef.recalc_refdef = 1;
|
||||
|
|
|
@ -1019,7 +1019,7 @@ Draw_BlendScreen (quat_t color)
|
|||
newpal[2] = vid.gammatable[b];
|
||||
newpal += 3;
|
||||
}
|
||||
vid.vid_internal->set_palette (vid.vid_internal->data, pal);
|
||||
vid.vid_internal->set_palette (vid.vid_internal->ctx, pal);
|
||||
}
|
||||
|
||||
int
|
||||
|
|
|
@ -183,17 +183,17 @@ static vid_model_funcs_t model_funcs = {
|
|||
static void
|
||||
gl_vid_render_init (void)
|
||||
{
|
||||
if (!vr_data.vid->vid_internal->sw_context) {
|
||||
if (!vr_data.vid->vid_internal->gl_context) {
|
||||
Sys_Error ("Sorry, OpenGL not supported by this program.");
|
||||
}
|
||||
gl_ctx = vr_data.vid->vid_internal->gl_context ();
|
||||
vid_internal_t *vi = vr_data.vid->vid_internal;
|
||||
gl_ctx = vi->gl_context (vi);
|
||||
gl_ctx->init_gl = GL_Init_Common;
|
||||
gl_ctx->load_gl ();
|
||||
gl_ctx->load_gl (gl_ctx);
|
||||
|
||||
vr_data.vid->vid_internal->data = gl_ctx;
|
||||
vr_data.vid->vid_internal->set_palette = GL_SetPalette;
|
||||
vr_data.vid->vid_internal->choose_visual = gl_vid_render_choose_visual;
|
||||
vr_data.vid->vid_internal->create_context = gl_vid_render_create_context;
|
||||
vi->set_palette = GL_SetPalette;
|
||||
vi->choose_visual = gl_vid_render_choose_visual;
|
||||
vi->create_context = gl_vid_render_create_context;
|
||||
|
||||
vr_funcs = &gl_vid_render_funcs;
|
||||
m_funcs = &model_funcs;
|
||||
|
|
|
@ -94,17 +94,17 @@ static vid_model_funcs_t model_funcs = {
|
|||
static void
|
||||
glsl_vid_render_init (void)
|
||||
{
|
||||
if (!vr_data.vid->vid_internal->sw_context) {
|
||||
if (!vr_data.vid->vid_internal->gl_context) {
|
||||
Sys_Error ("Sorry, OpenGL (GLSL) not supported by this program.");
|
||||
}
|
||||
glsl_ctx = vr_data.vid->vid_internal->gl_context ();
|
||||
vid_internal_t *vi = vr_data.vid->vid_internal;
|
||||
glsl_ctx = vi->gl_context (vi);
|
||||
glsl_ctx->init_gl = GLSL_Init_Common;
|
||||
glsl_ctx->load_gl ();
|
||||
glsl_ctx->load_gl (glsl_ctx);
|
||||
|
||||
vr_data.vid->vid_internal->data = glsl_ctx;
|
||||
vr_data.vid->vid_internal->set_palette = GLSL_SetPalette;
|
||||
vr_data.vid->vid_internal->choose_visual = glsl_vid_render_choose_visual;
|
||||
vr_data.vid->vid_internal->create_context = glsl_vid_render_create_context;
|
||||
vi->set_palette = GLSL_SetPalette;
|
||||
vi->choose_visual = glsl_vid_render_choose_visual;
|
||||
vi->create_context = glsl_vid_render_create_context;
|
||||
vr_funcs = &glsl_vid_render_funcs;
|
||||
m_funcs = &model_funcs;
|
||||
}
|
||||
|
@ -114,8 +114,6 @@ glsl_vid_render_shutdown (void)
|
|||
{
|
||||
glsl_R_Shutdown ();
|
||||
GLSL_Shutdown_Common ();
|
||||
|
||||
glsl_ctx->unload_gl (glsl_ctx);
|
||||
}
|
||||
|
||||
static unsigned int GLErr_InvalidEnum;
|
||||
|
|
|
@ -106,9 +106,8 @@ sw_vid_render_init (void)
|
|||
if (!vr_data.vid->vid_internal->sw_context) {
|
||||
Sys_Error ("Sorry, software rendering not supported by this program.");
|
||||
}
|
||||
sw_ctx = vr_data.vid->vid_internal->sw_context ();
|
||||
sw_ctx = vr_data.vid->vid_internal->sw_context (vr_data.vid->vid_internal);
|
||||
|
||||
vr_data.vid->vid_internal->data = sw_ctx;
|
||||
vr_data.vid->vid_internal->set_palette = sw_vid_render_set_palette;
|
||||
vr_data.vid->vid_internal->set_colormap = sw_vid_render_set_colormap;
|
||||
vr_data.vid->vid_internal->choose_visual = sw_vid_render_choose_visual;
|
||||
|
|
|
@ -699,15 +699,15 @@ vulkan_vid_render_init (void)
|
|||
if (!vr_data.vid->vid_internal->vulkan_context) {
|
||||
Sys_Error ("Sorry, Vulkan not supported by this program.");
|
||||
}
|
||||
vulkan_ctx = vr_data.vid->vid_internal->vulkan_context ();
|
||||
vid_internal_t *vi = vr_data.vid->vid_internal;
|
||||
vulkan_ctx = vi->vulkan_context (vi);
|
||||
vulkan_ctx->load_vulkan (vulkan_ctx);
|
||||
|
||||
Vulkan_Init_Common (vulkan_ctx);
|
||||
|
||||
vr_data.vid->vid_internal->data = vulkan_ctx;
|
||||
vr_data.vid->vid_internal->set_palette = set_palette;
|
||||
vr_data.vid->vid_internal->choose_visual = vulkan_vid_render_choose_visual;
|
||||
vr_data.vid->vid_internal->create_context = vulkan_vid_render_create_context;
|
||||
vi->set_palette = set_palette;
|
||||
vi->choose_visual = vulkan_vid_render_choose_visual;
|
||||
vi->create_context = vulkan_vid_render_create_context;
|
||||
|
||||
vr_funcs = &vulkan_vid_render_funcs;
|
||||
m_funcs = &model_funcs;
|
||||
|
|
|
@ -224,7 +224,7 @@ VID_UpdateGamma (void)
|
|||
}
|
||||
p32[-1] = 0; // color 255 is transparent
|
||||
// update with the new palette
|
||||
vi->set_palette (vi->data, viddef.palette);
|
||||
vi->set_palette (vi->ctx, viddef.palette);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -276,7 +276,7 @@ void
|
|||
VID_ClearMemory (void)
|
||||
{
|
||||
if (vi->flush_caches) {
|
||||
vi->flush_caches (vi->data);
|
||||
vi->flush_caches (vi->ctx);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -123,7 +123,7 @@ Win_VID_SetPalette (byte *palette, byte *colormap)
|
|||
viddef.colormap8 = colormap;
|
||||
viddef.fullbright = 256 - viddef.colormap8[256 * VID_GRADES];
|
||||
if (vid_internal.set_colormap) {
|
||||
vid_internal.set_colormap (vid_internal.data, colormap);
|
||||
vid_internal.set_colormap (vid_internal.ctx, colormap);
|
||||
}
|
||||
|
||||
VID_InitGamma (palette);
|
||||
|
|
|
@ -177,7 +177,7 @@ wgl_end_rendering (void)
|
|||
}
|
||||
|
||||
static void
|
||||
wgl_load_gl (void)
|
||||
wgl_load_gl (gl_ctx_t *ctx)
|
||||
{
|
||||
libgl_handle = LoadLibrary (gl_driver);
|
||||
if (!libgl_handle) {
|
||||
|
@ -198,7 +198,7 @@ wgl_load_gl (void)
|
|||
}
|
||||
|
||||
gl_ctx_t *
|
||||
Win_GL_Context (void)
|
||||
Win_GL_Context (vid_internal_t *vi)
|
||||
{
|
||||
gl_ctx_t *ctx = calloc (1, sizeof (gl_ctx_t));
|
||||
ctx->load_gl = wgl_load_gl;
|
||||
|
@ -206,6 +206,8 @@ Win_GL_Context (void)
|
|||
ctx->create_context = wgl_create_context;
|
||||
ctx->get_proc_address = QFGL_ProcAddress;
|
||||
ctx->end_rendering = wgl_end_rendering;
|
||||
|
||||
vi->ctx = ctx;
|
||||
return ctx;
|
||||
}
|
||||
|
||||
|
|
|
@ -233,7 +233,7 @@ VID_CreateGDIDriver (int width, int height, const byte *palette, byte **buffer,
|
|||
|
||||
// create a palette
|
||||
VID_InitGamma (palette);
|
||||
viddef.vid_internal->set_palette (viddef.vid_internal->data, palette);
|
||||
viddef.vid_internal->set_palette (viddef.vid_internal->ctx, palette);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -478,13 +478,15 @@ win_create_context (sw_ctx_t *ctx)
|
|||
}
|
||||
|
||||
sw_ctx_t *
|
||||
Win_SW_Context (void)
|
||||
Win_SW_Context (vid_internal_t *vi)
|
||||
{
|
||||
sw_ctx_t *ctx = calloc (1, sizeof (sw_ctx_t));
|
||||
ctx->set_palette = win_set_palette;
|
||||
ctx->choose_visual = win_choose_visual;
|
||||
ctx->create_context = win_create_context;
|
||||
ctx->update = win_sw_update;
|
||||
|
||||
vi->ctx = ctx;
|
||||
return ctx;
|
||||
}
|
||||
|
||||
|
|
|
@ -174,7 +174,7 @@ win_vulkan_create_surface (vulkan_ctx_t *ctx)
|
|||
}
|
||||
|
||||
vulkan_ctx_t *
|
||||
Win_Vulkan_Context (void)
|
||||
Win_Vulkan_Context (vid_internal_t *vi)
|
||||
{
|
||||
vulkan_ctx_t *ctx = calloc (1, sizeof (vulkan_ctx_t));
|
||||
ctx->load_vulkan = load_vulkan_library;
|
||||
|
@ -186,6 +186,8 @@ Win_Vulkan_Context (void)
|
|||
ctx->required_extensions = required_extensions;
|
||||
ctx->va_ctx = va_create_context (4);
|
||||
ctx->twod_scale = 1;
|
||||
|
||||
vi->ctx = ctx;
|
||||
return ctx;
|
||||
}
|
||||
|
||||
|
|
|
@ -86,6 +86,9 @@ X11_VID_Shutdown (void)
|
|||
{
|
||||
Sys_MaskPrintf (SYS_vid, "X11_VID_shutdown\n");
|
||||
X11_CloseDisplay ();
|
||||
if (vid_internal.unload) {
|
||||
vid_internal.unload (vid_internal.ctx);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -94,11 +97,11 @@ X11_VID_SetPalette (byte *palette, byte *colormap)
|
|||
viddef.colormap8 = colormap;
|
||||
viddef.fullbright = 256 - viddef.colormap8[256 * VID_GRADES];
|
||||
if (vid_internal.set_colormap) {
|
||||
vid_internal.set_colormap (vid_internal.data, colormap);
|
||||
vid_internal.set_colormap (vid_internal.ctx, colormap);
|
||||
}
|
||||
|
||||
VID_InitGamma (palette);
|
||||
vid_internal.set_palette (vid_internal.data, viddef.palette);
|
||||
vid_internal.set_palette (vid_internal.ctx, viddef.palette);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -123,11 +126,11 @@ X11_VID_Init (byte *palette, byte *colormap)
|
|||
|
||||
VID_GetWindowSize (640, 480);
|
||||
X11_OpenDisplay ();
|
||||
vid_internal.choose_visual (vid_internal.data);
|
||||
vid_internal.choose_visual (vid_internal.ctx);
|
||||
X11_SetVidMode (viddef.width, viddef.height);
|
||||
X11_CreateWindow (viddef.width, viddef.height);
|
||||
X11_CreateNullCursor (); // hide mouse pointer
|
||||
vid_internal.create_context (vid_internal.data);
|
||||
vid_internal.create_context (vid_internal.ctx);
|
||||
|
||||
X11_VID_SetPalette (palette, colormap);
|
||||
|
||||
|
|
|
@ -103,6 +103,7 @@ static GLXContext (*qfglXCreateContextAttribsARB) (Display *dpy,
|
|||
GLXContext ctx,
|
||||
Bool direct,
|
||||
const int *attribs);
|
||||
static void (*qfglXDestroyContext) ( Display *dpy, GLXContext ctx );
|
||||
static GLXFBConfig *(*qfglXChooseFBConfig) (Display *dpy, int screen,
|
||||
const int *attribs, int *nitems);
|
||||
static XVisualInfo *(*qfglXGetVisualFromFBConfig) (Display *dpy,
|
||||
|
@ -191,8 +192,8 @@ glx_choose_visual (gl_ctx_t *ctx)
|
|||
}
|
||||
Sys_MaskPrintf (SYS_vid, "Found %d matching FB configs.\n", fbcount);
|
||||
glx_cfg = fbc[0];
|
||||
XFree (fbc);
|
||||
x_visinfo = qfglXGetVisualFromFBConfig (x_disp, glx_cfg);
|
||||
XFree (fbc);
|
||||
if (!x_visinfo) {
|
||||
Sys_Error ("Error couldn't get an RGB, Double-buffered, Depth visual");
|
||||
}
|
||||
|
@ -225,7 +226,7 @@ glx_end_rendering (void)
|
|||
}
|
||||
|
||||
static void
|
||||
glx_load_gl (void)
|
||||
glx_load_gl (gl_ctx_t *ctx)
|
||||
{
|
||||
libgl_handle = dlopen (gl_driver, RTLD_NOW);
|
||||
if (!libgl_handle) {
|
||||
|
@ -241,6 +242,7 @@ glx_load_gl (void)
|
|||
qfglXGetVisualFromFBConfig = QFGL_ProcAddress ("glXGetVisualFromFBConfig", true);
|
||||
qfglXGetFBConfigAttrib = QFGL_ProcAddress ("glXGetFBConfigAttrib", true);
|
||||
qfglXCreateContextAttribsARB = QFGL_ProcAddress ("glXCreateContextAttribsARB", true);
|
||||
qfglXDestroyContext = QFGL_ProcAddress ("glXDestroyContext", true);
|
||||
qfglXMakeCurrent = QFGL_ProcAddress ("glXMakeCurrent", true);
|
||||
|
||||
use_gl_procaddress = 1;
|
||||
|
@ -249,22 +251,28 @@ glx_load_gl (void)
|
|||
}
|
||||
|
||||
static void
|
||||
glx_unload_gl (gl_ctx_t *ctx)
|
||||
glx_unload_gl (void *_ctx)
|
||||
{
|
||||
gl_ctx_t *ctx = _ctx;
|
||||
if (libgl_handle) {
|
||||
dlclose (libgl_handle);
|
||||
libgl_handle = 0;
|
||||
}
|
||||
free (ctx);
|
||||
}
|
||||
|
||||
gl_ctx_t *
|
||||
X11_GL_Context (void)
|
||||
X11_GL_Context (vid_internal_t *vi)
|
||||
{
|
||||
gl_ctx_t *ctx = calloc (1, sizeof (gl_ctx_t));
|
||||
ctx->load_gl = glx_load_gl;
|
||||
ctx->unload_gl = glx_unload_gl;
|
||||
ctx->choose_visual = glx_choose_visual;
|
||||
ctx->create_context = glx_create_context;
|
||||
ctx->get_proc_address = QFGL_ProcAddress;
|
||||
ctx->end_rendering = glx_end_rendering;
|
||||
|
||||
vi->unload = glx_unload_gl;
|
||||
vi->ctx = ctx;
|
||||
return ctx;
|
||||
}
|
||||
|
||||
|
|
|
@ -693,13 +693,15 @@ x11_create_context (sw_ctx_t *ctx)
|
|||
}
|
||||
|
||||
sw_ctx_t *
|
||||
X11_SW_Context (void)
|
||||
X11_SW_Context (vid_internal_t *vi)
|
||||
{
|
||||
sw_ctx_t *ctx = calloc (1, sizeof (sw_ctx_t));
|
||||
ctx->set_palette = x11_set_palette;
|
||||
ctx->choose_visual = x11_choose_visual;
|
||||
ctx->create_context = x11_create_context;
|
||||
ctx->update = x11_sw8_8_update;
|
||||
|
||||
vi->ctx = ctx;
|
||||
return ctx;
|
||||
}
|
||||
|
||||
|
|
|
@ -213,7 +213,7 @@ x11_vulkan_create_surface (vulkan_ctx_t *ctx)
|
|||
}
|
||||
|
||||
vulkan_ctx_t *
|
||||
X11_Vulkan_Context (void)
|
||||
X11_Vulkan_Context (vid_internal_t *vi)
|
||||
{
|
||||
vulkan_ctx_t *ctx = calloc (1, sizeof (vulkan_ctx_t));
|
||||
ctx->load_vulkan = load_vulkan_library;
|
||||
|
@ -225,6 +225,8 @@ X11_Vulkan_Context (void)
|
|||
ctx->required_extensions = required_extensions;
|
||||
ctx->va_ctx = va_create_context (32);
|
||||
ctx->twod_scale = 1;
|
||||
|
||||
vi->ctx = ctx;
|
||||
return ctx;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue