From 6299d07c0ac2b96ae99325b0accad61c9b4bba4d Mon Sep 17 00:00:00 2001
From: Spoike <acceptthis@users.sourceforge.net>
Date: Tue, 12 Mar 2013 22:49:04 +0000
Subject: [PATCH] 
 ------------------------------------------------------------------------
 r4192 | acceptthis | 2013-02-10 17:21:31 +0000 (Sun, 10 Feb 2013) | 1 line

-DUSE_EGL no longer excludes the use of glx
------------------------------------------------------------------------


git-svn-id: https://svn.code.sf.net/p/fteqw/code/trunk@4190 fc73d0e0-1445-4013-8a0c-d673dee63da5
---
 engine/Makefile            |   2 +-
 engine/client/renderer.c   |   3 +-
 engine/gl/gl_videgl.c      |  45 ++++++-
 engine/gl/gl_videgl.h      |   2 +-
 engine/gl/gl_vidlinuxglx.c | 262 ++++++++++++++++++++++++++++---------
 5 files changed, 246 insertions(+), 68 deletions(-)

diff --git a/engine/Makefile b/engine/Makefile
index 01a4d31c9..8814688b1 100644
--- a/engine/Makefile
+++ b/engine/Makefile
@@ -920,7 +920,7 @@ ifneq ($(shell echo $(FTE_TARGET)|grep linux),)
 	SV_LDFLAGS=-lz
 	SV_EXE_NAME=../fteqw.sv$(BITS)
 
-	GLCL_OBJS=$(GL_OBJS) $(D3DGL_OBJS) $(GLQUAKE_OBJS) $(BOTLIB_OBJS) $(SPEEX_OBJS) gl_vidlinuxglx.o snd_alsa.o snd_linux.o cd_linux.o sys_linux.o
+	GLCL_OBJS=$(GL_OBJS) $(D3DGL_OBJS) $(GLQUAKE_OBJS) $(BOTLIB_OBJS) $(SPEEX_OBJS) gl_vidlinuxglx.o gl_videgl.o snd_alsa.o snd_linux.o cd_linux.o sys_linux.o
 	GL_EXE_NAME=../fteqw.gl$(BITS)
 	GLCL_EXE_NAME=../fteqwcl.gl$(BITS)
 	GL_LDFLAGS=$(GLLDFLAGS) $(GLXLDFLAGS) $(OGGVORBISLDFLAGS) -lXxf86vm -lXxf86dga -lz
diff --git a/engine/client/renderer.c b/engine/client/renderer.c
index 491e27f7d..1db09a970 100644
--- a/engine/client/renderer.c
+++ b/engine/client/renderer.c
@@ -872,7 +872,7 @@ rendererinfo_t dedicatedrendererinfo = {
 rendererinfo_t *pdedicatedrendererinfo = &dedicatedrendererinfo;
 
 rendererinfo_t openglrendererinfo;
-
+rendererinfo_t eglrendererinfo;
 rendererinfo_t d3d9rendererinfo;
 rendererinfo_t d3d11rendererinfo;
 rendererinfo_t swrendererinfo;
@@ -884,6 +884,7 @@ rendererinfo_t *rendererinfo[] =
 #endif
 #ifdef GLQUAKE
 	&openglrendererinfo,
+	&eglrendererinfo,
 #endif
 #ifdef D3DQUAKE
 	&d3d9rendererinfo,
diff --git a/engine/gl/gl_videgl.c b/engine/gl/gl_videgl.c
index 35174571b..4025f3215 100644
--- a/engine/gl/gl_videgl.c
+++ b/engine/gl/gl_videgl.c
@@ -1,3 +1,5 @@
+#include "bothdefs.h"
+#if defined(GLQUAKE) && defined(USE_EGL)
 #include "gl_videgl.h"
 
 EGLContext eglctx = EGL_NO_CONTEXT;
@@ -88,17 +90,44 @@ void EGL_UnloadLibrary(void)
 qboolean EGL_LoadLibrary(char *driver)
 {
 	/* apps seem to load glesv2 first for dependency issues */
+	Sys_Printf("Attempting to dlopen libGLESv2... ");
 	eslibrary = Sys_LoadLibrary("libGLESv2", NULL);
 	if (!eslibrary)
-		return false;
+	{
+		Sys_Printf("failed\n");
+//		return false;
+	}
+	else
+		Sys_Printf("success\n");
+	if (!eslibrary)
+	{
+		eslibrary = dlopen("libGL", RTLD_NOW|RTLD_GLOBAL);
+		if (eslibrary) Sys_Printf("Loaded libGL\n");
+	}
+	if (!eslibrary)
+	{
+		eslibrary = dlopen("libGL.so.1.2", RTLD_NOW|RTLD_GLOBAL);
+		if (eslibrary) Sys_Printf("Loaded libGL.so.1.2\n");
+	}
+	if (!eslibrary)
+	{
+		eslibrary = dlopen("libGL.so.1", RTLD_NOW|RTLD_GLOBAL);
+		if (eslibrary) Sys_Printf("Loaded libGL.so.1\n");
+	}
+	if (!eslibrary)
+		Sys_Printf("unable to load some libGL\n");
 	
+	Sys_Printf("Attempting to dlopen libEGL... ");
 	egllibrary = Sys_LoadLibrary("libEGL", qeglfuncs);
 	if (!egllibrary)
 	{
+		Sys_Printf("failed\n");
+		Con_Printf("libEGL library not loadable\n");
 		/* TODO: some implementations combine EGL/GLESv2 into single library... */
 		Sys_CloseLibrary(eslibrary);
 		return false;
 	}
+	Sys_Printf("success\n");
 
 	return true;
 }
@@ -132,10 +161,11 @@ void EGL_EndRendering (void)
 	/* TODO: check result? */
 }
 
-qboolean EGL_Init (rendererstate_t *info, unsigned char *palette, EGLNativeWindowType window)
+qboolean EGL_Init (rendererstate_t *info, unsigned char *palette, EGLNativeWindowType window, EGLNativeDisplayType dpy)
 {
 	EGLint numconfig;
 	EGLConfig cfg;
+	EGLint major, minor;
 	EGLint attrib[] =
 	{
 		EGL_BUFFER_SIZE, info->bpp,
@@ -152,20 +182,21 @@ qboolean EGL_Init (rendererstate_t *info, unsigned char *palette, EGLNativeWindo
 		EGL_NONE, EGL_NONE
 	};
 
-	if (!EGL_LoadLibrary(""))
+/*	if (!EGL_LoadLibrary(""))
 	{
 		Con_Printf(CON_ERROR "EGL: unable to load library!\n");
 		return false;
 	}
-
-	egldpy = qeglGetDisplay(EGL_DEFAULT_DISPLAY);
+*/
+	egldpy = qeglGetDisplay(dpy);
 	if (egldpy == EGL_NO_DISPLAY)
 	{
 		Con_Printf(CON_ERROR "EGL: can't get display!\n");
 		return false;
 	}
 
-	if (!qeglInitialize(egldpy, NULL, NULL))
+	//NOTE: mesa's egl really loves to crash on this call, and I define crash as 'anything that fails to return to caller', which fucks everything up.
+	if (!qeglInitialize(egldpy, &major, &minor))
 	{
 		Con_Printf(CON_ERROR "EGL: can't initialize display!");
 		return false;
@@ -207,3 +238,5 @@ qboolean EGL_Init (rendererstate_t *info, unsigned char *palette, EGLNativeWindo
 
 	return true;
 }
+#endif
+
diff --git a/engine/gl/gl_videgl.h b/engine/gl/gl_videgl.h
index db20fd256..34e1257e7 100644
--- a/engine/gl/gl_videgl.h
+++ b/engine/gl/gl_videgl.h
@@ -12,6 +12,6 @@ qboolean EGL_LoadLibrary(char *driver);
 void EGL_Shutdown(void);
 void EGL_BeginRendering (void);
 void EGL_EndRendering (void);
-qboolean EGL_Init (rendererstate_t *info, unsigned char *palette, EGLNativeWindowType window);
+qboolean EGL_Init (rendererstate_t *info, unsigned char *palette, EGLNativeWindowType window, EGLNativeDisplayType dpy);
 
 #endif
diff --git a/engine/gl/gl_vidlinuxglx.c b/engine/gl/gl_vidlinuxglx.c
index 53d4ecb84..f8ee04b11 100644
--- a/engine/gl/gl_vidlinuxglx.c
+++ b/engine/gl/gl_vidlinuxglx.c
@@ -61,6 +61,14 @@ static Window vid_decoywindow;	//for legacy mode, this is a boring window that w
 static Window vid_root;
 static GLXContext ctx = NULL;
 static int scrnum;
+static enum
+{
+	PSL_NONE,
+#ifdef USE_EGL
+	PSL_EGL,
+#endif
+	PSL_GLX
+} currentpsl;
 
 extern cvar_t vid_conautoscale;
 
@@ -620,9 +628,6 @@ static void GetEvent(void)
 
 void GLVID_Shutdown(void)
 {
-#ifdef USE_EGL
-	EGL_Shutdown();
-#else
 	printf("GLVID_Shutdown\n");
 	if (!vid_dpy)
 		return;
@@ -631,17 +636,30 @@ void GLVID_Shutdown(void)
 	if (old_windowed_mouse)
 		uninstall_grabs();
 
-	if (ctx)
-	{
-		qglXDestroyContext(vid_dpy, ctx);
-		ctx = NULL;
-	}
-
 #ifdef WITH_VMODE
 	if (originalapplied)
 		XF86VidModeSetGammaRamp(vid_dpy, scrnum, 256, originalramps[0], originalramps[1], originalramps[2]);
 #endif
 
+
+	switch(currentpsl)
+	{
+#ifdef USE_EGL
+	case PSL_EGL:
+		EGL_Shutdown();
+		break;
+#endif
+	case PSL_GLX:
+		if (ctx)
+		{
+			qglXDestroyContext(vid_dpy, ctx);
+			ctx = NULL;
+		}
+		break;
+	case PSL_NONE:
+		break;
+	}
+
 	if (vid_window)
 		XDestroyWindow(vid_dpy, vid_window);
 	if (vid_nullcursor)
@@ -662,7 +680,7 @@ void GLVID_Shutdown(void)
 	XCloseDisplay(vid_dpy);
 	vid_dpy = NULL;
 	vid_window = (Window)NULL;
-#endif
+	currentpsl = PSL_NONE;
 }
 
 void GLVID_DeInit(void)	//FIXME:....
@@ -780,22 +798,37 @@ GL_BeginRendering
 */
 void GL_BeginRendering (void)
 {
+	switch(currentpsl)
+	{
 #ifdef USE_EGL
-	EGL_BeginRendering();
+	case PSL_EGL:
+		EGL_BeginRendering();
+		break;
 #endif
+	case PSL_GLX:
+	case PSL_NONE:
+		break;
+	}
 }
 
 
 void GL_EndRendering (void)
 {
+	switch(currentpsl)
+	{
 #ifdef USE_EGL
-	EGL_EndRendering();
-#else
-//return;
-//we don't need the flush, XSawpBuffers does it for us.
-//chances are, it's version is more suitable anyway. At least there's the chance that it might be.
-	qglXSwapBuffers(vid_dpy, vid_window);
+	case PSL_EGL:
+		EGL_EndRendering();
+		break;
 #endif
+	case PSL_GLX:
+		//we don't need to flush, XSawpBuffers does it for us.
+		//chances are, it's version is more suitable anyway. At least there's the chance that it might be.
+		qglXSwapBuffers(vid_dpy, vid_window);
+		break;
+	case PSL_NONE:
+		break;
+	}
 }
 
 #include "bymorphed.h"
@@ -968,7 +1001,7 @@ Window X_CreateWindow(qboolean override, XVisualInfo *visinfo, unsigned int widt
 	return wnd;
 }
 
-qboolean GLVID_Init (rendererstate_t *info, unsigned char *palette)
+qboolean X11VID_Init (rendererstate_t *info, unsigned char *palette, int psl)
 {
 	int width = info->width;	//can override these if vmode isn't available
 	int height = info->height;
@@ -999,19 +1032,29 @@ qboolean GLVID_Init (rendererstate_t *info, unsigned char *palette)
 
 	S_Startup();
 
+	currentpsl = psl;
+
+	switch(currentpsl)
+	{
 #ifdef USE_EGL
-	if (!EGL_LoadLibrary(info->glrenderer))
-	{
-		Con_Printf("couldn't load EGL library\n");
-		return false;
-	}
-#else
-	if (!GLX_InitLibrary(info->glrenderer))
-	{
-		Con_Printf("Couldn't intialise GLX\nEither your drivers are not installed or you need to specify the library name with the gl_driver cvar\n");
-		return false;
-	}
+	case PSL_EGL:
+		if (!EGL_LoadLibrary(info->glrenderer))
+		{
+			Con_Printf("couldn't load EGL library\n");
+			return false;
+		}
+		break;
 #endif
+	case PSL_GLX:
+		if (!GLX_InitLibrary(info->glrenderer))
+		{
+			Con_Printf("Couldn't intialise GLX\nEither your drivers are not installed or you need to specify the library name with the gl_driver cvar\n");
+			return false;
+		}
+		break;
+	case PSL_NONE:
+		return false;
+	}
 
 	if (!vid_dpy)
 		vid_dpy = XOpenDisplay(NULL);
@@ -1105,20 +1148,28 @@ qboolean GLVID_Init (rendererstate_t *info, unsigned char *palette)
                         fullscreenflags |= FULLSCREEN_LEGACY;
 	}
 
+	switch(currentpsl)
+	{
 #ifdef USE_EGL
-	visinfo = &vinfodef;
-	if (!XMatchVisualInfo(vid_dpy, scrnum, info->bpp, TrueColor, visinfo))
-//	if (!XMatchVisualInfo(vid_dpy, scrnum, DefaultDepth(vid_dpy, scrnum), TrueColor, &visinfo))
-	{
-		Sys_Error("Couldn't choose visual for EGL\n");
-	}
-#else
-	visinfo = qglXChooseVisual(vid_dpy, scrnum, attrib);
-	if (!visinfo)
-	{
-		Sys_Error("qkHack: Error couldn't get an RGB, Double-buffered, Depth visual\n");
-	}
+	case PSL_EGL:
+		visinfo = &vinfodef;
+		if (!XMatchVisualInfo(vid_dpy, scrnum, info->bpp, TrueColor, visinfo))
+	//	if (!XMatchVisualInfo(vid_dpy, scrnum, DefaultDepth(vid_dpy, scrnum), TrueColor, &visinfo))
+		{
+			Sys_Error("Couldn't choose visual for EGL\n");
+		}
+		break;
 #endif
+	case PSL_GLX:
+		visinfo = qglXChooseVisual(vid_dpy, scrnum, attrib);
+		if (!visinfo)
+		{
+			Sys_Error("qkHack: Error couldn't get an RGB, Double-buffered, Depth visual\n");
+		}
+		break;
+	case PSL_NONE:
+		break;	//erm
+	}
 
 	ActiveApp = false;
 	if (fullscreenflags & FULLSCREEN_LEGACY)
@@ -1147,7 +1198,6 @@ qboolean GLVID_Init (rendererstate_t *info, unsigned char *palette)
 
 	XFlush(vid_dpy);
 
-#ifndef USE_EGL
 #ifdef WITH_VMODE
 	if (vidmode_ext >= 2)
 	{
@@ -1165,27 +1215,35 @@ qboolean GLVID_Init (rendererstate_t *info, unsigned char *palette)
 		originalapplied = false;
 #endif
 
-	ctx = qglXCreateContext(vid_dpy, visinfo, NULL, True);
-	if (!ctx)
+	switch(currentpsl)
 	{
-		Con_Printf("Failed to create GLX context.\n");
-		GLVID_Shutdown();
-		return false;
-	}
+	case PSL_GLX:
+		ctx = qglXCreateContext(vid_dpy, visinfo, NULL, True);
+		if (!ctx)
+		{
+			Con_Printf("Failed to create GLX context.\n");
+			GLVID_Shutdown();
+			return false;
+		}
 
-	if (!qglXMakeCurrent(vid_dpy, vid_window, ctx))
-	{
-		Con_Printf("glXMakeCurrent failed\n");
-		GLVID_Shutdown();
-		return false;
-	}
+		if (!qglXMakeCurrent(vid_dpy, vid_window, ctx))
+		{
+			Con_Printf("glXMakeCurrent failed\n");
+			GLVID_Shutdown();
+			return false;
+		}
 
-	GL_Init(&GLX_GetSymbol);
-
-#else
-	EGL_Init(info, palette, vid_window);
-	GL_Init(&EGL_Proc);
+		GL_Init(&GLX_GetSymbol);
+		break;
+#ifdef USE_EGL
+	case PSL_EGL:
+		EGL_Init(info, palette, vid_window, vid_dpy);
+		GL_Init(&EGL_Proc);
+		break;
 #endif
+	case PSL_NONE:
+		break;
+	}
 
 	GLVID_SetPalette(palette);
 	GLVID_ShiftPalette(palette);
@@ -1223,6 +1281,14 @@ qboolean GLVID_Init (rendererstate_t *info, unsigned char *palette)
 
 	return true;
 }
+qboolean GLVID_Init (rendererstate_t *info, unsigned char *palette)
+{
+	return X11VID_Init(info, palette, PSL_GLX);
+}
+qboolean EGLVID_Init (rendererstate_t *info, unsigned char *palette)
+{
+	return X11VID_Init(info, palette, PSL_EGL);
+}
 
 void Sys_SendKeyEvents(void)
 {
@@ -1376,6 +1442,84 @@ void GLVID_SetCaption(char *text)
 	XStoreName(vid_dpy, vid_window, text);
 }
 
+#ifdef USE_EGL
+#include "shader.h"
+#include "gl_draw.h"
+rendererinfo_t eglrendererinfo =
+{
+	"EGL",
+	{
+		"egl"
+	},
+	QR_OPENGL,
+
+	GLDraw_Init,
+	GLDraw_DeInit,
+
+	GL_LoadTextureFmt,
+	GL_LoadTexture8Pal24,
+	GL_LoadTexture8Pal32,
+	GL_LoadCompressed,
+	GL_FindTexture,
+	GL_AllocNewTexture,
+	GL_UploadFmt,
+	GL_DestroyTexture,
+
+	GLR_Init,
+	GLR_DeInit,
+	GLR_RenderView,
+
+	GLR_NewMap,
+	GLR_PreNewMap,
+
+	Surf_AddStain,
+	Surf_LessenStains,
+
+	RMod_Init,
+	RMod_Shutdown,
+	RMod_ClearAll,
+	RMod_ForName,
+	RMod_FindName,
+	RMod_Extradata,
+	RMod_TouchModel,
+
+	RMod_NowLoadExternal,
+	RMod_Think,
+
+	Mod_GetTag,
+	Mod_TagNumForName,
+	Mod_SkinNumForName,
+	Mod_FrameNumForName,
+	Mod_FrameDuration,
+
+	EGLVID_Init,
+	GLVID_DeInit,
+	GLVID_SetPalette,
+	GLVID_ShiftPalette,
+	GLVID_GetRGBInfo,
+
+	GLVID_SetCaption,       //setcaption
+
+
+	GLSCR_UpdateScreen,
+
+	GLBE_SelectMode,
+	GLBE_DrawMesh_List,
+	GLBE_DrawMesh_Single,
+	GLBE_SubmitBatch,
+	GLBE_GetTempBatch,
+	GLBE_DrawWorld,
+	GLBE_Init,
+	GLBE_GenBrushModelVBO,
+	GLBE_ClearVBO,
+	GLBE_UploadAllLightmaps,
+	GLBE_SelectEntity,
+	GLBE_SelectDLight,
+	GLBE_LightCullModel,
+
+	""
+};
+#endif
 
 #if 1
 char *Sys_GetClipboard(void)