1 /*
2 Copyright (C) 1997-2001 Id Software, Inc.
3 
4 This program is free software; you can redistribute it and/or
5 modify it under the terms of the GNU General Public License
6 as published by the Free Software Foundation; either version 2
7 of the License, or (at your option) any later version.
8 
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12 
13 See the GNU General Public License for more details.
14 
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18 */
19 
20 //
21 // rf_init.c
22 //
23 
24 #include "rf_local.h"
25 
26 cVar_t	*e_test_0;
27 cVar_t	*e_test_1;
28 
29 cVar_t	*gl_bitdepth;
30 cVar_t	*gl_clear;
31 cVar_t	*gl_cull;
32 cVar_t	*gl_drawbuffer;
33 cVar_t	*gl_driver;
34 cVar_t	*gl_dynamic;
35 cVar_t	*gl_errorcheck;
36 
37 cVar_t	*r_allowExtensions;
38 cVar_t	*r_ext_BGRA;
39 cVar_t	*r_ext_compiledVertexArray;
40 cVar_t	*r_ext_drawRangeElements;
41 cVar_t	*r_ext_fragmentProgram;
42 cVar_t	*r_ext_generateMipmap;
43 cVar_t	*r_ext_maxAnisotropy;
44 cVar_t	*r_ext_multitexture;
45 cVar_t	*r_ext_stencilTwoSide;
46 cVar_t	*r_ext_stencilWrap;
47 cVar_t	*r_ext_swapInterval;
48 cVar_t	*r_ext_texture3D;
49 cVar_t	*r_ext_textureCompression;
50 cVar_t	*r_ext_textureCubeMap;
51 cVar_t	*r_ext_textureEdgeClamp;
52 cVar_t	*r_ext_textureEnvAdd;
53 cVar_t	*r_ext_textureEnvCombine;
54 cVar_t	*r_ext_textureEnvCombineNV4;
55 cVar_t	*r_ext_textureEnvDot3;
56 cVar_t	*r_ext_textureFilterAnisotropic;
57 cVar_t	*r_ext_vertexBufferObject;
58 cVar_t	*r_ext_vertexProgram;
59 
60 cVar_t	*gl_finish;
61 cVar_t	*gl_flashblend;
62 cVar_t	*gl_lightmap;
63 cVar_t	*gl_lockpvs;
64 cVar_t	*gl_log;
65 cVar_t	*gl_maxTexSize;
66 cVar_t	*gl_mode;
67 cVar_t	*gl_modulate;
68 
69 cVar_t	*gl_shadows;
70 cVar_t	*gl_shownormals;
71 cVar_t	*gl_showtris;
72 
73 cVar_t	*qgl_debug;
74 
75 cVar_t	*r_caustics;
76 cVar_t	*r_colorMipLevels;
77 cVar_t	*r_debugBatching;
78 cVar_t	*r_debugCulling;
79 cVar_t	*r_debugLighting;
80 cVar_t	*r_debugSorting;
81 cVar_t	*r_defaultFont;
82 cVar_t	*r_detailTextures;
83 cVar_t	*r_displayFreq;
84 cVar_t	*r_drawDecals;
85 cVar_t	*r_drawEntities;
86 cVar_t	*r_drawPolys;
87 cVar_t	*r_drawworld;
88 cVar_t	*r_facePlaneCull;
89 cVar_t	*r_flares;
90 cVar_t	*r_flareFade;
91 cVar_t	*r_flareSize;
92 cVar_t	*r_fontScale;
93 cVar_t	*r_fullbright;
94 cVar_t	*r_hwGamma;
95 cVar_t	*r_lerpmodels;
96 cVar_t	*r_lightlevel;
97 cVar_t	*r_lmMaxBlockSize;
98 cVar_t	*r_lmModulate;
99 cVar_t	*r_lmPacking;
100 cVar_t	*r_noCull;
101 cVar_t	*r_noRefresh;
102 cVar_t	*r_noVis;
103 cVar_t	*r_offsetFactor;
104 cVar_t	*r_offsetUnits;
105 cVar_t	*r_patchDivLevel;
106 cVar_t	*r_roundImagesDown;
107 cVar_t	*r_skipBackend;
108 cVar_t	*r_speeds;
109 cVar_t	*r_sphereCull;
110 cVar_t	*r_swapInterval;
111 cVar_t	*r_textureBits;
112 cVar_t	*r_times;
113 cVar_t	*r_vertexLighting;
114 cVar_t	*r_zFarAbs;
115 cVar_t	*r_zFarMin;
116 cVar_t	*r_zNear;
117 
118 cVar_t	*r_alphabits;
119 cVar_t	*r_colorbits;
120 cVar_t	*r_depthbits;
121 cVar_t	*r_stencilbits;
122 cVar_t	*cl_stereo;
123 cVar_t	*gl_allow_software;
124 cVar_t	*gl_stencilbuffer;
125 
126 cVar_t	*vid_gamma;
127 cVar_t	*vid_gammapics;
128 cVar_t	*vid_width;
129 cVar_t	*vid_height;
130 
131 cVar_t	*intensity;
132 
133 cVar_t	*gl_jpgquality;
134 cVar_t	*gl_nobind;
135 cVar_t	*gl_picmip;
136 cVar_t	*gl_screenshot;
137 cVar_t	*gl_texturemode;
138 
139 static void	*cmd_gfxInfo;
140 static void	*cmd_rendererClass;
141 static void	*cmd_eglRenderer;
142 static void	*cmd_eglVersion;
143 
144 /*
145 =============================================================================
146 
147 	CONSOLE COMMANDS
148 
149 =============================================================================
150 */
151 
152 /*
153 ==================
154 R_RendererClass
155 ==================
156 */
R_RendererClass(void)157 static char *R_RendererClass (void)
158 {
159 	switch (ri.renderClass) {
160 	case REND_CLASS_DEFAULT:			return "Default";
161 	case REND_CLASS_MCD:				return "MCD";
162 
163 	case REND_CLASS_3DLABS_GLINT_MX:	return "3DLabs GLIntMX";
164 	case REND_CLASS_3DLABS_PERMEDIA:	return "3DLabs Permedia";
165 	case REND_CLASS_3DLABS_REALIZM:		return "3DLabs Realizm";
166 	case REND_CLASS_ATI:				return "ATi";
167 	case REND_CLASS_ATI_RADEON:			return "ATi Radeon";
168 	case REND_CLASS_INTEL:				return "Intel";
169 	case REND_CLASS_NVIDIA:				return "nVidia";
170 	case REND_CLASS_NVIDIA_GEFORCE:		return "nVidia GeForce";
171 	case REND_CLASS_PMX:				return "PMX";
172 	case REND_CLASS_POWERVR_PCX1:		return "PowerVR PCX1";
173 	case REND_CLASS_POWERVR_PCX2:		return "PowerVR PCX2";
174 	case REND_CLASS_RENDITION:			return "Rendition";
175 	case REND_CLASS_S3:					return "S3";
176 	case REND_CLASS_SGI:				return "SGI";
177 	case REND_CLASS_SIS:				return "SiS";
178 	case REND_CLASS_VOODOO:				return "Voodoo";
179 	}
180 
181 	return "";
182 }
183 
184 
185 /*
186 ==================
187 R_RendererClass_f
188 ==================
189 */
R_RendererClass_f(void)190 static void R_RendererClass_f (void)
191 {
192 	Com_Printf (0, "Renderer Class: %s\n", R_RendererClass ());
193 }
194 
195 
196 /*
197 ==================
198 R_GfxInfo_f
199 ==================
200 */
R_GfxInfo_f(void)201 static void R_GfxInfo_f (void)
202 {
203 	Com_Printf (0, "----------------------------------------\n");
204 
205 	Com_Printf (0, "EGL v%s:\n" "GL_PFD: c(%d-bits) a(%d-bits) z(%d-bit) s(%d-bit)\n",
206 				EGL_VERSTR,
207 				ri.cColorBits, ri.cAlphaBits, ri.cDepthBits, ri.cStencilBits);
208 
209 	Com_Printf (0, "Renderer Class: %s\n", R_RendererClass ());
210 
211 	Com_Printf (0, "----------------------------------------\n");
212 
213 	Com_Printf (0, "GL_VENDOR: %s\n",		ri.vendorString);
214 	Com_Printf (0, "GL_RENDERER: %s\n",		ri.rendererString);
215 	Com_Printf (0, "GL_VERSION: %s\n",		ri.versionString);
216 	Com_Printf (0, "GL_EXTENSIONS: %s\n",	ri.extensionString);
217 
218 	Com_Printf (0, "----------------------------------------\n");
219 
220 	Com_Printf (0, "Extensions:\n");
221 	Com_Printf (0, "...ARB Multitexture: %s\n",				ri.config.extArbMultitexture ? "On" : "Off");
222 
223 	Com_Printf (0, "...BGRA: %s\n",							ri.config.extBGRA ? "On" : "Off");
224 	Com_Printf (0, "...Compiled Vertex Array: %s\n",		ri.config.extCompiledVertArray ? "On" : "Off");
225 
226 	Com_Printf (0, "...Draw Range Elements: %s\n",			ri.config.extDrawRangeElements ? "On" : "Off");
227 	if (ri.config.extDrawRangeElements) {
228 		Com_Printf (0, "...* Max element vertices: %i\n",	ri.config.maxElementVerts);
229 		Com_Printf (0, "...* Max element indices: %i\n",	ri.config.maxElementIndices);
230 	}
231 
232 	Com_Printf (0, "...Fragment programs: %s\n",			ri.config.extFragmentProgram ? "On" : "Off");
233 	if (ri.config.extFragmentProgram) {
234 		Com_Printf (0, "...* Max texture coordinates: %i\n",ri.config.maxTexCoords);
235 		Com_Printf (0, "...* Max texture image units: %i\n",ri.config.maxTexImageUnits);
236 	}
237 
238 	Com_Printf (0, "...nVidia Texture Env Combine4: %s\n",	ri.config.extNVTexEnvCombine4 ? "On" : "Off");
239 	Com_Printf (0, "...SGIS Mipmap Generation: %s\n",		ri.config.extSGISGenMipmap ? "On" : "Off");
240 	Com_Printf (0, "...SGIS Multitexture: %s\n",			ri.config.extSGISMultiTexture ? "On" : ri.config.extArbMultitexture ? "Deprecated for ARB Multitexture" : "Off");
241 	Com_Printf (0, "...Stencil Two Side: %s\n",				ri.config.extStencilTwoSide ? "On" : "Off");
242 	Com_Printf (0, "...Stencil Wrap: %s\n",					ri.config.extStencilWrap ? "On" : "Off");
243 
244 	Com_Printf (0, "...Texture Cube Map: %s\n",				ri.config.extTexCubeMap ? "On" : "Off");
245 	if (ri.config.extTexCubeMap)
246 		Com_Printf (0, "...* Max cubemap texture size: %i\n",ri.config.maxCMTexSize);
247 
248 	Com_Printf (0, "...Texture Compression: %s\n",			ri.config.extTexCompression ? "On" : "Off");
249 	Com_Printf (0, "...Texture 3D: %s\n",					ri.config.extTex3D ? "On" : "Off");
250 	Com_Printf (0, "...Texture Edge Clamp: %s\n",			ri.config.extTexEdgeClamp ? "On" : "Off");
251 	Com_Printf (0, "...Texture Env Add: %s\n",				ri.config.extTexEnvAdd ? "On" : "Off");
252 	Com_Printf (0, "...Texture Env Combine: %s\n",			ri.config.extTexEnvCombine ? "On" : "Off");
253 	Com_Printf (0, "...Texture Env DOT3: %s\n",				ri.config.extTexEnvDot3 ? "On" : "Off");
254 
255 	Com_Printf (0, "...Texture Filter Anisotropic: %s\n",	ri.config.extTexFilterAniso ? "On" : "Off");
256 	if (ri.config.extTexFilterAniso)
257 		Com_Printf (0, "...* Max texture anisotropy: %i\n",	ri.config.maxAniso);
258 
259 	Com_Printf (0, "...Vertex Buffer Objects: %s\n",		ri.config.extVertexBufferObject ? "On" : "Off");
260 	Com_Printf (0, "...Vertex programs: %s\n",				ri.config.extVertexProgram ? "On" : "Off");
261 
262 	Com_Printf (0, "----------------------------------------\n");
263 
264 	GL_TextureMode (qTrue, qTrue);
265 	GL_TextureBits (qTrue, qTrue);
266 
267 	Com_Printf (0, "----------------------------------------\n");
268 
269 	Com_Printf (0, "Max texture size: %i\n", ri.config.maxTexSize);
270 	Com_Printf (0, "Max texture units: %i\n", ri.config.maxTexUnits);
271 
272 	Com_Printf (0, "----------------------------------------\n");
273 }
274 
275 
276 /*
277 ==================
278 R_RendererMsg_f
279 ==================
280 */
R_RendererMsg_f(void)281 static void R_RendererMsg_f (void)
282 {
283 	Cbuf_AddText (Q_VarArgs ("say [EGL v%s]: [%s: %s v%s] GL_PFD[c%d/a%d/z%d/s%d] RES[%dx%dx%d]\n",
284 		EGL_VERSTR,
285 		ri.vendorString, ri.rendererString, ri.versionString,
286 		ri.cColorBits, ri.cAlphaBits, ri.cDepthBits, ri.cStencilBits,
287 		ri.config.vidWidth, ri.config.vidHeight, ri.config.vidBitDepth));
288 }
289 
290 
291 /*
292 ==================
293 R_VersionMsg_f
294 ==================
295 */
R_VersionMsg_f(void)296 static void R_VersionMsg_f (void)
297 {
298 	Cbuf_AddText (Q_VarArgs ("say [EGL v%s (%s-%s) by Echon] [http://egl.quakedev.com/]\n",
299 		EGL_VERSTR, BUILDSTRING, CPUSTRING));
300 }
301 
302 /*
303 =============================================================================
304 
305 	INIT / SHUTDOWN
306 
307 =============================================================================
308 */
309 
310 /*
311 ==================
312 R_MediaInit
313 ==================
314 */
R_MediaInit(void)315 void R_MediaInit (void)
316 {
317 	// Chars image/shaders
318 	R_CheckFont ();
319 
320 	// World Caustic shaders
321 	ri.media.worldLavaCaustics = R_RegisterTexture ("egl/lavacaustics", -1);
322 	ri.media.worldSlimeCaustics = R_RegisterTexture ("egl/slimecaustics", -1);
323 	ri.media.worldWaterCaustics = R_RegisterTexture ("egl/watercaustics", -1);
324 }
325 
326 
327 /*
328 ===============
329 ExtensionFound
330 ===============
331 */
ExtensionFound(const byte * extensionList,const char * extension)332 static qBool ExtensionFound (const byte *extensionList, const char *extension)
333 {
334 	const byte	*start;
335 	byte		*where, *terminator;
336 
337 	// Extension names should not have spaces
338 	where = (byte *) strchr (extension, ' ');
339 	if (where || *extension == '\0')
340 		return qFalse;
341 
342 	start = extensionList;
343 	for ( ; ; ) {
344 		where = (byte *) strstr ((const char *)start, extension);
345 		if (!where)
346 			break;
347 		terminator = where + strlen (extension);
348 		if (where == start || (*(where - 1) == ' ')) {
349 			if (*terminator == ' ' || *terminator == '\0') {
350 				return qTrue;
351 			}
352 		}
353 		start = terminator;
354 	}
355 	return qFalse;
356 }
357 
358 
359 /*
360 ============
361 R_GetInfoForMode
362 ============
363 */
364 typedef struct vidMode_s {
365 	char		*info;
366 
367 	int			width;
368 	int			height;
369 
370 	int			mode;
371 } vidMode_t;
372 
373 static vidMode_t r_vidModes[] = {
374 	{"Mode 0: 320 x 240",			320,	240,	0 },
375 	{"Mode 1: 400 x 300",			400,	300,	1 },
376 	{"Mode 2: 512 x 384",			512,	384,	2 },
377 	{"Mode 3: 640 x 480",			640,	480,	3 },
378 	{"Mode 4: 800 x 600",			800,	600,	4 },
379 	{"Mode 5: 960 x 720",			960,	720,	5 },
380 	{"Mode 6: 1024 x 768",			1024,	768,	6 },
381 	{"Mode 7: 1152 x 864",			1152,	864,	7 },
382 	{"Mode 8: 1280 x 960",			1280,	960,	8 },
383 	{"Mode 9: 1600 x 1200",			1600,	1200,	9 },
384 	{"Mode 10: 1920 x 1440",		1920,	1440,	10},
385 	{"Mode 11: 2048 x 1536",		2048,	1536,	11},
386 
387 	{"Mode 12: 1280 x 800 (ws)",	1280,	800,	12},
388 	{"Mode 13: 1440 x 900 (ws)",	1440,	900,	13}
389 };
390 
391 #define NUM_VIDMODES (sizeof (r_vidModes) / sizeof (r_vidModes[0]))
R_GetInfoForMode(int mode,int * width,int * height)392 qBool R_GetInfoForMode (int mode, int *width, int *height)
393 {
394 	if (mode < 0 || mode >= NUM_VIDMODES)
395 		return qFalse;
396 
397 	*width  = r_vidModes[mode].width;
398 	*height = r_vidModes[mode].height;
399 	return qTrue;
400 }
401 
402 
403 /*
404 ==================
405 R_SetMode
406 ==================
407 */
408 #define SAFE_MODE	3
R_SetMode(void)409 static qBool R_SetMode (void)
410 {
411 	int		width, height;
412 	qBool	fullScreen;
413 
414 	Com_Printf (0, "Setting video mode\n");
415 
416 	// Find the mode info
417 	fullScreen = vid_fullscreen->intVal ? qTrue : qFalse;
418 	if (vid_width->intVal > 0 && vid_height->intVal > 0) {
419 		width = vid_width->intVal;
420 		height = vid_height->intVal;
421 	}
422 	else if (!R_GetInfoForMode (gl_mode->intVal, &width, &height)) {
423 		Com_Printf (PRNT_ERROR, "...bad mode '%i', forcing safe mode\n", gl_mode->intVal);
424 		Cvar_VariableSetValue (gl_mode, (float)SAFE_MODE, qTrue);
425 		if (!R_GetInfoForMode (SAFE_MODE, &width, &height))
426 			return qFalse;	// This should *never* happen if SAFE_MODE is a sane value
427 	}
428 
429 	// Attempt the desired mode
430 	if (GLimp_AttemptMode (fullScreen, width, height)) {
431 		Cvar_VariableSetValue (vid_fullscreen, (float)ri.config.vidFullScreen, qTrue);
432 		return qTrue;
433 	}
434 
435 	// Bad mode, fall out of fullscreen if it was attempted
436 	if (fullScreen) {
437 		Com_Printf (PRNT_ERROR, "...failed to set fullscreen, attempting windowed\n");
438 
439 		if (GLimp_AttemptMode (qFalse, width, height)) {
440 			Cvar_VariableSetValue (vid_fullscreen, (float)ri.config.vidFullScreen, qTrue);
441 			return qTrue;
442 		}
443 	}
444 
445 	// Don't attempt the last valid safe mode if the user is already using it
446 	if (ri.lastValidMode != -1 && ri.lastValidMode != gl_mode->intVal) {
447 		Com_Printf (PRNT_ERROR, "...failed to set mode, attempted the last valid mode\n");
448 		Cvar_VariableSetValue (gl_mode, (float)ri.lastValidMode, qTrue);
449 
450 		if (GLimp_AttemptMode (qFalse, width, height)) {
451 			Cvar_VariableSetValue (vid_fullscreen, (float)ri.config.vidFullScreen, qTrue);
452 			return qTrue;
453 		}
454 	}
455 
456 	// Don't attempt safe mode if the user is already using it
457 	if (gl_mode->intVal == SAFE_MODE) {
458 		Com_Printf (PRNT_ERROR, "...already using the safe mode, exiting\n");
459 		return qFalse;
460 	}
461 
462 	// Bad mode period, fall back to safe mode
463 	Com_Printf (PRNT_ERROR, "...failed to set mode, attempting safe mode '%d'\n", SAFE_MODE);
464 	Cvar_VariableSetValue (gl_mode, (float)SAFE_MODE, qTrue);
465 
466 	// Try setting it back to something safe
467 	R_GetInfoForMode (gl_mode->intVal, &width, &height);
468 	if (GLimp_AttemptMode (fullScreen, width, height)) {
469 		Cvar_VariableSetValue (vid_fullscreen, (float)ri.config.vidFullScreen, qTrue);
470 		return qTrue;
471 	}
472 
473 	Com_Printf (PRNT_ERROR, "...could not revert to safe mode\n");
474 	return qFalse;
475 }
476 
477 
478 /*
479 ===============
480 GL_InitExtensions
481 ===============
482 */
GL_InitExtensions(void)483 static void GL_InitExtensions (void)
484 {
485 	// Check for gl errors
486 	GL_CheckForError ("GL_InitExtensions");
487 
488 	/*
489 	** GL_ARB_multitexture
490 	** GL_SGIS_multitexture
491 	*/
492 	if (r_ext_multitexture->intVal) {
493 		// GL_ARB_multitexture
494 		if (ExtensionFound (ri.extensionString, "GL_ARB_multitexture")) {
495 			qglActiveTextureARB = QGL_GetProcAddress ("glActiveTextureARB");
496 			if (qglActiveTextureARB)	qglClientActiveTextureARB = QGL_GetProcAddress ("glClientActiveTextureARB");
497 
498 			if (!qglClientActiveTextureARB) {
499 				Com_Printf (PRNT_ERROR, "...GL_ARB_multitexture not properly supported!\n");
500 				qglActiveTextureARB			= NULL;
501 				qglClientActiveTextureARB	= NULL;
502 			}
503 			else {
504 				Com_Printf (0, "...enabling GL_ARB_multitexture\n");
505 				ri.config.extArbMultitexture = qTrue;
506 			}
507 		}
508 		else
509 			Com_Printf (0, "...GL_ARB_multitexture not found\n");
510 
511 		// GL_SGIS_multitexture
512 		if (!ri.config.extArbMultitexture) {
513 			Com_Printf (0, "...attempting GL_SGIS_multitexture\n");
514 
515 			if (ExtensionFound (ri.extensionString, "GL_SGIS_multitexture")) {
516 				qglSelectTextureSGIS = QGL_GetProcAddress ("glSelectTextureSGIS");
517 
518 				if (!qglSelectTextureSGIS) {
519 					Com_Printf (PRNT_ERROR, "...GL_SGIS_multitexture not properly supported!\n");
520 					qglSelectTextureSGIS	= NULL;
521 				}
522 				else {
523 					Com_Printf (0, "...enabling GL_SGIS_multitexture\n");
524 					ri.config.extSGISMultiTexture = qTrue;
525 				}
526 			}
527 			else
528 				Com_Printf (0, "...GL_SGIS_multitexture not found\n");
529 		}
530 	}
531 	else {
532 		qglActiveTextureARB			= NULL;
533 		qglClientActiveTextureARB	= NULL;
534 		qglSelectTextureSGIS		= NULL;
535 
536 		Com_Printf (0, "...ignoring GL_ARB/SGIS_multitexture\n");
537 		Com_Printf (PRNT_WARNING, "WARNING: Disabling multitexture is not recommended!\n");
538 	}
539 
540 	// Keep texture unit counts in check
541 	if (ri.config.extSGISMultiTexture || ri.config.extArbMultitexture) {
542 		qglGetIntegerv (GL_MAX_TEXTURE_UNITS, &ri.config.maxTexUnits);
543 
544 		if (ri.config.maxTexUnits < 2) {
545 			Com_Printf (0, "...not using GL_ARB/SGIS_multitexture, < 2 texture units\n");
546 
547 			ri.config.maxTexUnits = 1;
548 			qglActiveTextureARB				= NULL;
549 			qglClientActiveTextureARB		= NULL;
550 			qglSelectTextureSGIS			= NULL;
551 			ri.config.extArbMultitexture	= qFalse;
552 			ri.config.extSGISMultiTexture	= qFalse;
553 		}
554 		else {
555 			if (ri.config.extSGISMultiTexture && ri.config.maxTexUnits > 2) {
556 				// GL_SGIS_multitexture doesn't support more than 2 units does it?
557 				ri.config.maxTexUnits = 2;
558 				Com_Printf (0, "...* GL_SGIS_multitexture clamped to 2 texture units\n");
559 			}
560 			else if (ri.config.maxTexUnits > MAX_TEXUNITS) {
561 				// Clamp at the maximum amount the engine supports
562 				ri.config.maxTexUnits = MAX_TEXUNITS;
563 				Com_Printf (0, "...* clamped to engine maximum of %i texture units\n", ri.config.maxTexUnits);
564 			}
565 			else
566 				Com_Printf (0, "...* using video card maximum of %i texture units\n", ri.config.maxTexUnits);
567 		}
568 	}
569 	else {
570 		ri.config.maxTexUnits = 1;
571 	}
572 
573 	/*
574 	** GL_ARB_texture_compression
575 	** GL_EXT_texture_compression_s3tc
576 	** GL_S3_s3tc
577 	*/
578 	if (r_ext_textureCompression->intVal) {
579 		while (r_ext_textureCompression->intVal) {
580 			switch (r_ext_textureCompression->intVal) {
581 			case 1:
582 				if (!ExtensionFound (ri.extensionString, "GL_ARB_texture_compression")) {
583 					Com_Printf (0, "...GL_ARB_texture_compression not found\n");
584 					Cvar_VariableSetValue (r_ext_textureCompression, 2, qTrue);
585 					break;
586 				}
587 
588 				Com_Printf (0, "...enabling GL_ARB_texture_compression\n");
589 				ri.config.extTexCompression = qTrue;
590 
591 				ri.rgbFormatCompressed = GL_COMPRESSED_RGB_ARB;
592 				ri.rgbaFormatCompressed = GL_COMPRESSED_RGBA_ARB;
593 				break;
594 
595 			case 2:
596 			case 3:
597 			case 4:
598 				if (!ExtensionFound (ri.extensionString, "GL_EXT_texture_compression_s3tc")) {
599 					Com_Printf (0, "...GL_EXT_texture_compression_s3tc not found\n");
600 					Cvar_VariableSetValue (r_ext_textureCompression, 5, qTrue);
601 					break;
602 				}
603 
604 				Com_Printf (0, "...enabling GL_EXT_texture_compression_s3tc\n");
605 				ri.config.extTexCompression = qTrue;
606 
607 				ri.rgbFormatCompressed = GL_COMPRESSED_RGB_S3TC_DXT1_EXT;
608 				switch (r_ext_textureCompression->intVal) {
609 				case 2:
610 					ri.rgbaFormatCompressed = GL_COMPRESSED_RGBA_S3TC_DXT1_EXT;
611 					Com_Printf (0, "...* using S3TC_DXT1\n");
612 					break;
613 
614 				case 3:
615 					ri.rgbaFormatCompressed = GL_COMPRESSED_RGBA_S3TC_DXT3_EXT;
616 					Com_Printf (0, "...* using S3TC_DXT3\n");
617 					break;
618 
619 				case 4:
620 					ri.rgbaFormatCompressed = GL_COMPRESSED_RGBA_S3TC_DXT5_EXT;
621 					Com_Printf (0, "...* using S3TC_DXT5\n");
622 					break;
623 				}
624 				break;
625 
626 			case 5:
627 				if (!ExtensionFound (ri.extensionString, "GL_S3_s3tc")) {
628 					Com_Printf (0, "...GL_S3_s3tc not found\n");
629 					Cvar_VariableSetValue (r_ext_textureCompression, 0, qTrue);
630 					break;
631 				}
632 
633 				Com_Printf (0, "...enabling GL_S3_s3tc\n");
634 				ri.config.extTexCompression = qTrue;
635 
636 				ri.rgbFormatCompressed = GL_RGB_S3TC;
637 				ri.rgbaFormatCompressed = GL_RGBA_S3TC;
638 				break;
639 
640 			default:
641 				Cvar_VariableSetValue (r_ext_textureCompression, 0, qTrue);
642 				break;
643 			}
644 
645 			if (ri.config.extTexCompression || !r_ext_textureCompression->intVal)
646 				break;
647 		}
648 	}
649 	else {
650 		Com_Printf (0, "...ignoring GL_ARB_texture_compression\n");
651 		Com_Printf (0, "...ignoring GL_EXT_texture_compression_s3tc\n");
652 		Com_Printf (0, "...ignoring GL_S3_s3tc\n");
653 	}
654 
655 	/*
656 	** GL_ARB_texture_cube_map
657 	*/
658 	if (r_ext_textureCubeMap->intVal) {
659 		if (ExtensionFound (ri.extensionString, "GL_ARB_texture_cube_map")) {
660 			qglGetIntegerv (GL_MAX_CUBE_MAP_TEXTURE_SIZE_ARB, &ri.config.maxCMTexSize);
661 
662 			if (ri.config.maxCMTexSize <= 0) {
663 				Com_Printf (PRNT_ERROR, "GL_ARB_texture_cube_map not properly supported!\n");
664 				ri.config.maxCMTexSize = 0;
665 			}
666 			else {
667 				Q_NearestPow (&ri.config.maxCMTexSize, qTrue);
668 
669 				Com_Printf (0, "...enabling GL_ARB_texture_cube_map\n");
670 				Com_Printf (0, "...* Max cubemap texture size: %i\n", ri.config.maxCMTexSize);
671 				ri.config.extTexCubeMap = qTrue;
672 			}
673 		}
674 		else
675 			Com_Printf (0, "...GL_ARB_texture_cube_map not found\n");
676 	}
677 	else
678 		Com_Printf (0, "...ignoring GL_ARB_texture_cube_map\n");
679 
680 	/*
681 	** GL_ARB_texture_env_add
682 	*/
683 	if (r_ext_textureEnvAdd->intVal) {
684 		if (ExtensionFound (ri.extensionString, "GL_ARB_texture_env_add")) {
685 			if (ri.config.extSGISMultiTexture || ri.config.extArbMultitexture) {
686 				Com_Printf (0, "...enabling GL_ARB_texture_env_add\n");
687 				ri.config.extTexEnvAdd = qTrue;
688 			}
689 			else
690 				Com_Printf (0, "...ignoring GL_ARB_texture_env_add (no multitexture)\n");
691 		}
692 		else
693 			Com_Printf (0, "...GL_ARB_texture_env_add not found\n");
694 	}
695 	else
696 		Com_Printf (0, "...ignoring GL_ARB_texture_env_add\n");
697 
698 	/*
699 	** GL_ARB_texture_env_combine
700 	** GL_EXT_texture_env_combine
701 	*/
702 	if (r_ext_textureEnvCombine->intVal) {
703 		if (ExtensionFound (ri.extensionString, "GL_ARB_texture_env_combine") ||
704 			ExtensionFound (ri.extensionString, "GL_EXT_texture_env_combine")) {
705 			if (ri.config.extSGISMultiTexture || ri.config.extArbMultitexture) {
706 				Com_Printf (0, "...enabling GL_ARB/EXT_texture_env_combine\n");
707 				ri.config.extTexEnvCombine = qTrue;
708 			}
709 			else
710 				Com_Printf (0, "...ignoring GL_ARB/EXT_texture_env_combine (no multitexture)\n");
711 		}
712 		else
713 			Com_Printf (0, "...GL_ARB/EXT_texture_env_combine not found\n");
714 	}
715 	else
716 		Com_Printf (0, "...ignoring GL_ARB/EXT_texture_env_combine\n");
717 
718 	/*
719 	** GL_NV_texture_env_combine4
720 	*/
721 	if (r_ext_textureEnvCombineNV4->intVal) {
722 		if (ExtensionFound (ri.extensionString, "NV_texture_env_combine4")) {
723 			if (ri.config.extTexEnvCombine) {
724 				Com_Printf (0, "...enabling GL_NV_texture_env_combine4\n");
725 				ri.config.extNVTexEnvCombine4 = qTrue;
726 			}
727 			else
728 				Com_Printf (0, "...ignoring GL_NV_texture_env_combine4 (no combine)\n");
729 		}
730 		else
731 			Com_Printf (0, "...GL_NV_texture_env_combine4 not found\n");
732 	}
733 	else
734 		Com_Printf (0, "...ignoring GL_NV_texture_env_combine4\n");
735 
736 	/*
737 	** GL_ARB_texture_env_dot3
738 	*/
739 	if (r_ext_textureEnvDot3->intVal) {
740 		if (ExtensionFound (ri.extensionString, "GL_ARB_texture_env_dot3")) {
741 			if (ri.config.extTexEnvCombine) {
742 				Com_Printf (0, "...enabling GL_ARB_texture_env_dot3\n");
743 				ri.config.extTexEnvDot3 = qTrue;
744 			}
745 			else
746 				Com_Printf (0, "...ignoring GL_ARB_texture_env_dot3 (no combine)\n");
747 		}
748 		else
749 			Com_Printf (0, "...GL_ARB_texture_env_dot3 not found\n");
750 	}
751 	else
752 		Com_Printf (0, "...ignoring GL_ARB_texture_env_dot3\n");
753 
754 	/*
755 	** GL_ARB_vertex_program
756 	*/
757 	if (r_ext_vertexProgram->intVal) {
758 		if (ExtensionFound (ri.extensionString, "GL_ARB_vertex_program")) {
759 			qglVertexAttribPointerARB = QGL_GetProcAddress("glVertexAttribPointerARB");
760 			if (qglVertexAttribPointerARB)		qglEnableVertexAttribArrayARB = QGL_GetProcAddress("glEnableVertexAttribArrayARB");
761 			if (qglEnableVertexAttribArrayARB)	qglDisableVertexAttribArrayARB = QGL_GetProcAddress("glDisableVertexAttribArrayARB");
762 			if (qglDisableVertexAttribArrayARB)	qglBindProgramARB = QGL_GetProcAddress("glBindProgramARB");
763 			if (qglBindProgramARB)				qglDeleteProgramsARB = QGL_GetProcAddress("glDeleteProgramsARB");
764 			if (qglDeleteProgramsARB)			qglGenProgramsARB = QGL_GetProcAddress("glGenProgramsARB");
765 			if (qglGenProgramsARB)				qglProgramStringARB = QGL_GetProcAddress("glProgramStringARB");
766 			if (qglProgramStringARB)			qglProgramEnvParameter4fARB = QGL_GetProcAddress("glProgramEnvParameter4fARB");
767 			if (qglProgramEnvParameter4fARB)	qglProgramEnvParameter4fvARB = QGL_GetProcAddress("glProgramEnvParameter4fvARB");
768 			if (qglProgramEnvParameter4fvARB)	qglProgramLocalParameter4fARB = QGL_GetProcAddress("glProgramLocalParameter4fARB");
769 			if (qglProgramLocalParameter4fARB)	qglProgramLocalParameter4fvARB = QGL_GetProcAddress("glProgramLocalParameter4fvARB");
770 			if (qglProgramLocalParameter4fvARB)	qglGetProgramivARB = QGL_GetProcAddress("glGetProgramivARB");
771 
772 			if (!qglGetProgramivARB) {
773 				Com_Printf (PRNT_ERROR, "GL_ARB_vertex_program not properly supported!\n");
774 				qglVertexAttribPointerARB		= NULL;
775 				qglEnableVertexAttribArrayARB	= NULL;
776 				qglDisableVertexAttribArrayARB	= NULL;
777 				qglBindProgramARB				= NULL;
778 				qglDeleteProgramsARB			= NULL;
779 				qglGenProgramsARB				= NULL;
780 				qglProgramStringARB				= NULL;
781 				qglProgramEnvParameter4fARB		= NULL;
782 				qglProgramEnvParameter4fvARB	= NULL;
783 				qglProgramLocalParameter4fARB	= NULL;
784 				qglProgramLocalParameter4fvARB	= NULL;
785 				qglGetProgramivARB				= NULL;
786 			}
787 			else {
788 				Com_Printf (0, "...enabling GL_ARB_vertex_program\n");
789 				ri.config.extVertexProgram = qTrue;
790 			}
791 		}
792 		else
793 			Com_Printf (0, "...GL_ARB_vertex_program not found\n");
794 	}
795 	else
796 		Com_Printf (0, "...ignoring GL_ARB_vertex_program\n");
797 
798 	/*
799 	** GL_ARB_fragment_program
800 	*/
801 	if (r_ext_fragmentProgram->intVal) {
802 		if (ExtensionFound (ri.extensionString, "GL_ARB_fragment_program")) {
803 			qglGetIntegerv (GL_MAX_TEXTURE_COORDS_ARB, &ri.config.maxTexCoords);
804 			qglGetIntegerv (GL_MAX_TEXTURE_IMAGE_UNITS_ARB, &ri.config.maxTexImageUnits);
805 
806 			qglBindProgramARB = QGL_GetProcAddress("glBindProgramARB");
807 			if (qglBindProgramARB)				qglDeleteProgramsARB = QGL_GetProcAddress("glDeleteProgramsARB");
808 			if (qglDeleteProgramsARB)			qglGenProgramsARB = QGL_GetProcAddress("glGenProgramsARB");
809 			if (qglGenProgramsARB)				qglProgramStringARB = QGL_GetProcAddress("glProgramStringARB");
810 			if (qglProgramStringARB)			qglProgramEnvParameter4fARB = QGL_GetProcAddress("glProgramEnvParameter4fARB");
811 			if (qglProgramEnvParameter4fARB)	qglProgramEnvParameter4fvARB = QGL_GetProcAddress("glProgramEnvParameter4fvARB");
812 			if (qglProgramEnvParameter4fvARB)	qglProgramLocalParameter4fARB = QGL_GetProcAddress("glProgramLocalParameter4fARB");
813 			if (qglProgramLocalParameter4fARB)	qglProgramLocalParameter4fvARB = QGL_GetProcAddress("glProgramLocalParameter4fvARB");
814 			if (qglProgramLocalParameter4fvARB)	qglGetProgramivARB = QGL_GetProcAddress("glGetProgramivARB");
815 
816 			if (!qglGetProgramivARB) {
817 				Com_Printf (PRNT_ERROR, "GL_ARB_fragment_program not properly supported!\n");
818 				qglBindProgramARB				= NULL;
819 				qglDeleteProgramsARB			= NULL;
820 				qglGenProgramsARB				= NULL;
821 				qglProgramStringARB				= NULL;
822 				qglProgramEnvParameter4fARB		= NULL;
823 				qglProgramEnvParameter4fvARB	= NULL;
824 				qglProgramLocalParameter4fARB	= NULL;
825 				qglProgramLocalParameter4fvARB	= NULL;
826 				qglGetProgramivARB				= NULL;
827 			}
828 			else {
829 				Com_Printf (0, "...enabling GL_ARB_fragment_program\n");
830 				Com_Printf (0, "...* Max texture coordinates: %i\n", ri.config.maxTexCoords);
831 				Com_Printf (0, "...* Max texture image units: %i\n", ri.config.maxTexImageUnits);
832 				ri.config.extFragmentProgram = qTrue;
833 			}
834 		}
835 		else
836 			Com_Printf (0, "...GL_ARB_fragment_program not found\n");
837 	}
838 	else
839 		Com_Printf (0, "...ignoring GL_ARB_fragment_program\n");
840 
841 	/*
842 	** GL_ARB_vertex_buffer_object
843 	*/
844 	if (r_ext_vertexBufferObject->intVal) {
845 		if (ExtensionFound (ri.extensionString, "GL_ARB_vertex_buffer_object")) {
846 			qglBindBufferARB = QGL_GetProcAddress ("glBindBufferARB");
847 			if (qglBindBufferARB)		qglDeleteBuffersARB = QGL_GetProcAddress ("glDeleteBuffersARB");
848 			if (qglDeleteBuffersARB)	qglGenBuffersARB = QGL_GetProcAddress ("glGenBuffersARB");
849 			if (qglGenBuffersARB)		qglIsBufferARB = QGL_GetProcAddress ("glIsBufferARB");
850 			if (qglIsBufferARB)			qglMapBufferARB = QGL_GetProcAddress ("glMapBufferARB");
851 			if (qglMapBufferARB)		qglUnmapBufferARB = QGL_GetProcAddress ("glUnmapBufferARB");
852 			if (qglUnmapBufferARB)		qglBufferDataARB = QGL_GetProcAddress ("glBufferDataARB");
853 			if (qglBufferDataARB)		qglBufferSubDataARB = QGL_GetProcAddress ("glBufferSubDataARB");
854 
855 			if (!qglBufferSubDataARB) {
856 				Com_Printf (PRNT_ERROR, "GL_ARB_vertex_buffer_object not properly supported!\n");
857 				qglBindBufferARB	= NULL;
858 				qglDeleteBuffersARB	= NULL;
859 				qglGenBuffersARB	= NULL;
860 				qglIsBufferARB		= NULL;
861 				qglMapBufferARB		= NULL;
862 				qglUnmapBufferARB	= NULL;
863 				qglBufferDataARB	= NULL;
864 				qglBufferSubDataARB	= NULL;
865 			}
866 			else {
867 				Com_Printf (0, "...enabling GL_ARB_vertex_buffer_object\n");
868 				ri.config.extVertexBufferObject = qTrue;
869 			}
870 		}
871 		else
872 			Com_Printf (0, "...GL_ARB_vertex_buffer_object not found\n");
873 	}
874 	else
875 		Com_Printf (0, "...ignoring GL_ARB_vertex_buffer_object\n");
876 
877 	/*
878 	** GL_EXT_bgra
879 	*/
880 	if (r_ext_BGRA->intVal) {
881 		if (ExtensionFound (ri.extensionString, "GL_EXT_bgra")) {
882 			Com_Printf (0, "...enabling GL_EXT_bgra\n");
883 			ri.config.extBGRA = qTrue;
884 		}
885 		else
886 			Com_Printf (0, "...GL_EXT_bgra not found\n");
887 	}
888 	else
889 		Com_Printf (0, "...ignoring GL_EXT_bgra\n");
890 
891 	/*
892 	** GL_EXT_compiled_vertex_array
893 	** GL_SGI_compiled_vertex_array
894 	*/
895 	if (r_ext_compiledVertexArray->intVal) {
896 		if (ExtensionFound (ri.extensionString, "GL_EXT_compiled_vertex_array")
897 		|| ExtensionFound (ri.extensionString, "GL_SGI_compiled_vertex_array")) {
898 			if (r_ext_compiledVertexArray->intVal != 2
899 			&& (ri.renderClass == REND_CLASS_INTEL || ri.renderClass == REND_CLASS_S3 || ri.renderClass == REND_CLASS_SIS)) {
900 				Com_Printf (PRNT_WARNING, "...forcibly ignoring GL_EXT/SGI_compiled_vertex_array\n"
901 								"...* Your card is known for not supporting it properly\n"
902 								"...* If you would like it enabled, set r_ext_compiledVertexArray to 2\n");
903 			}
904 			else {
905 				qglLockArraysEXT = QGL_GetProcAddress ("glLockArraysEXT");
906 				if (qglLockArraysEXT)	qglUnlockArraysEXT = QGL_GetProcAddress ("glUnlockArraysEXT");
907 
908 				if (!qglUnlockArraysEXT) {
909 					Com_Printf (PRNT_ERROR, "...GL_EXT/SGI_compiled_vertex_array not properly supported!\n");
910 					qglLockArraysEXT	= NULL;
911 					qglUnlockArraysEXT	= NULL;
912 				}
913 				else {
914 					Com_Printf (0, "...enabling GL_EXT/SGI_compiled_vertex_array\n");
915 					ri.config.extCompiledVertArray = qTrue;
916 				}
917 			}
918 		}
919 		else
920 			Com_Printf (0, "...GL_EXT/SGI_compiled_vertex_array not found\n");
921 	}
922 	else
923 		Com_Printf (0, "...ignoring GL_EXT/SGI_compiled_vertex_array\n");
924 
925 	/*
926 	** GL_EXT_draw_range_elements
927 	*/
928 	if (r_ext_drawRangeElements->intVal) {
929 		if (ExtensionFound (ri.extensionString, "GL_EXT_draw_range_elements")) {
930 			// These are not actual maximums, but rather recommendations for performance...
931 			qglGetIntegerv (GL_MAX_ELEMENTS_VERTICES_EXT, &ri.config.maxElementVerts);
932 			qglGetIntegerv (GL_MAX_ELEMENTS_INDICES_EXT, &ri.config.maxElementIndices);
933 
934 			if (ri.config.maxElementVerts > 0 && ri.config.maxElementIndices > 0) {
935 				qglDrawRangeElementsEXT = QGL_GetProcAddress ("glDrawRangeElementsEXT");
936 				if (!qglDrawRangeElementsEXT)
937 					qglDrawRangeElementsEXT = QGL_GetProcAddress ("glDrawRangeElements");
938 			}
939 
940 			if (!qglDrawRangeElementsEXT) {
941 				Com_Printf (PRNT_ERROR, "...GL_EXT_draw_range_elements not properly supported!\n");
942 				qglDrawRangeElementsEXT		= NULL;
943 				ri.config.maxElementIndices	= 0;
944 				ri.config.maxElementVerts	= 0;
945 			}
946 			else {
947 				Com_Printf (0, "...enabling GL_EXT_draw_range_elements\n");
948 				Com_Printf (0, "...* Max element vertices: %i\n", ri.config.maxElementVerts);
949 				Com_Printf (0, "...* Max element indices: %i\n", ri.config.maxElementIndices);
950 				ri.config.extDrawRangeElements = qTrue;
951 			}
952 		}
953 		else
954 			Com_Printf (0, "...GL_EXT_draw_range_elements not found\n");
955 	}
956 	else
957 		Com_Printf (0, "...ignoring GL_EXT_draw_range_elements\n");
958 
959 	/*
960 	** GL_EXT_texture3D
961 	*/
962 	if (r_ext_texture3D->intVal) {
963 		if (ExtensionFound (ri.extensionString, "GL_EXT_texture3D")) {
964 			qglTexImage3D = QGL_GetProcAddress ("glTexImage3D");
965 			if (qglTexImage3D) qglTexSubImage3D = QGL_GetProcAddress ("glTexSubImage3D");
966 			if (qglTexSubImage3D) qglGetIntegerv (GL_MAX_3D_TEXTURE_SIZE, &ri.config.max3DTexSize);
967 
968 			if (!ri.config.max3DTexSize) {
969 				Com_Printf (PRNT_ERROR, "...GL_EXT_texture3D not properly supported!\n");
970 				qglTexImage3D		= NULL;
971 				qglTexSubImage3D	= NULL;
972 			}
973 			else {
974 				Com_Printf (0, "...enabling GL_EXT_texture3D\n");
975 				ri.config.extTex3D = qTrue;
976 			}
977 		}
978 		else
979 			Com_Printf (0, "...GL_EXT_texture3D not found\n");
980 	}
981 	else
982 		Com_Printf (0, "...ignoring GL_EXT_texture3D\n");
983 
984 	/*
985 	** GL_EXT_texture_edge_clamp
986 	*/
987 	if (r_ext_textureEdgeClamp->intVal) {
988 		if (ExtensionFound (ri.extensionString, "GL_EXT_texture_edge_clamp")) {
989 			Com_Printf (0, "...enabling GL_EXT_texture_edge_clamp\n");
990 			ri.config.extTexEdgeClamp = qTrue;
991 		}
992 		else
993 			Com_Printf (0, "...GL_EXT_texture_edge_clamp not found\n");
994 	}
995 	else
996 		Com_Printf (0, "...ignoring GL_EXT_texture_edge_clamp\n");
997 
998 	/*
999 	** GL_EXT_texture_filter_anisotropic
1000 	*/
1001 	if (r_ext_textureFilterAnisotropic->intVal) {
1002 		if (ExtensionFound (ri.extensionString, "GL_EXT_texture_filter_anisotropic")) {
1003 			qglGetIntegerv (GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &ri.config.maxAniso);
1004 			if (ri.config.maxAniso <= 0) {
1005 				Com_Printf (PRNT_ERROR, "...GL_EXT_texture_filter_anisotropic not properly supported!\n");
1006 				ri.config.maxAniso = 0;
1007 			}
1008 			else {
1009 				Com_Printf (0, "...enabling GL_EXT_texture_filter_anisotropic\n");
1010 				Com_Printf (0, "...* Max texture anisotropy: %i\n", ri.config.maxAniso);
1011 				ri.config.extTexFilterAniso = qTrue;
1012 			}
1013 		}
1014 		else
1015 			Com_Printf (0, "...GL_EXT_texture_filter_anisotropic not found\n");
1016 	}
1017 	else {
1018 		if (ExtensionFound (ri.extensionString, "GL_EXT_texture_filter_anisotropic"))
1019 			qglGetIntegerv (GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &ri.config.maxAniso);
1020 
1021 		Com_Printf (0, "...ignoring GL_EXT_texture_filter_anisotropic\n");
1022 	}
1023 
1024 	/*
1025 	** GL_SGIS_generate_mipmap
1026 	*/
1027 	if (r_ext_generateMipmap->intVal) {
1028 		if (ExtensionFound (ri.extensionString, "GL_SGIS_generate_mipmap")) {
1029 			if (r_ext_generateMipmap->intVal != 2
1030 			&& (ri.renderClass == REND_CLASS_ATI || ri.renderClass == REND_CLASS_ATI_RADEON)) {
1031 				Com_Printf (PRNT_WARNING, "...forcibly ignoring GL_SGIS_generate_mipmap\n"
1032 								"...* ATi is known for not supporting it properly\n"
1033 								"...* If you would like it enabled, set r_ext_generateMipmap to 2\n");
1034 			}
1035 			else {
1036 				if (r_colorMipLevels->intVal) {
1037 					Com_Printf (PRNT_WARNING, "...ignoring GL_SGIS_generate_mipmap because of r_colorMipLevels\n");
1038 				}
1039 				else {
1040 					Com_Printf (0, "...enabling GL_SGIS_generate_mipmap\n");
1041 					ri.config.extSGISGenMipmap = qTrue;
1042 				}
1043 			}
1044 		}
1045 		else
1046 			Com_Printf (0, "...GL_SGIS_generate_mipmap not found\n");
1047 	}
1048 	else
1049 		Com_Printf (0, "...ignoring GL_SGIS_generate_mipmap\n");
1050 
1051 	/*
1052 	** GL_EXT_stencil_two_side
1053 	*/
1054 	if (r_ext_stencilTwoSide->intVal) {
1055 		if (ExtensionFound (ri.extensionString, "GL_EXT_stencil_two_side")) {
1056 			qglActiveStencilFaceEXT = QGL_GetProcAddress ("glActiveStencilFaceEXT");
1057 
1058 			if (!qglActiveStencilFaceEXT) {
1059 				Com_Printf (PRNT_ERROR, "...GL_EXT_stencil_two_side not properly supported!\n");
1060 				qglActiveStencilFaceEXT		= NULL;
1061 			}
1062 			else {
1063 				Com_Printf (0, "...enabling GL_EXT_stencil_two_side\n");
1064 				ri.config.extStencilTwoSide = qTrue;
1065 			}
1066 		}
1067 		else
1068 			Com_Printf (0, "...GL_EXT_stencil_two_side not found\n");
1069 	}
1070 	else
1071 		Com_Printf (0, "...ignoring GL_EXT_stencil_two_side\n");
1072 
1073 	/*
1074 	** GL_EXT_stencil_wrap
1075 	*/
1076 	if (r_ext_stencilWrap->intVal) {
1077 		if (ExtensionFound (ri.extensionString, "GL_EXT_stencil_wrap")) {
1078 			Com_Printf (0, "...enabling GL_EXT_stencil_wrap\n");
1079 			ri.config.extStencilWrap = qTrue;
1080 		}
1081 		else
1082 			Com_Printf (0, "...GL_EXT_stencil_wrap not found\n");
1083 	}
1084 	else
1085 		Com_Printf (0, "...ignoring GL_EXT_stencil_wrap\n");
1086 
1087 #ifdef WIN32
1088 	/*
1089 	** WGL_3DFX_gamma_control
1090 	*/
1091 	if (ExtensionFound (ri.extensionString, "WGL_3DFX_gamma_control")) {
1092 		qwglGetDeviceGammaRamp3DFX = QGL_GetProcAddress ("wglGetDeviceGammaRamp3DFX");
1093 		if (qwglGetDeviceGammaRamp3DFX) qwglSetDeviceGammaRamp3DFX = QGL_GetProcAddress ("wglSetDeviceGammaRamp3DFX");
1094 
1095 		if (!qwglSetDeviceGammaRamp3DFX) {
1096 			Com_Printf (PRNT_ERROR, "...WGL_3DFX_gamma_control not properly supported!\n");
1097 			qwglGetDeviceGammaRamp3DFX		= NULL;
1098 			qwglSetDeviceGammaRamp3DFX		= NULL;
1099 		}
1100 	}
1101 
1102 	/*
1103 	** WGL_EXT_swap_control
1104 	*/
1105 	if (r_ext_swapInterval->intVal) {
1106 		if (ExtensionFound (ri.extensionString, "WGL_EXT_swap_control")) {
1107 			if (!ri.config.extWinSwapInterval) {
1108 				qwglSwapIntervalEXT = QGL_GetProcAddress ("wglSwapIntervalEXT");
1109 
1110 				if (!qwglSwapIntervalEXT) {
1111 					Com_Printf (PRNT_ERROR, "...WGL_EXT_swap_control not properly supported!\n");
1112 					qwglSwapIntervalEXT		= NULL;
1113 				}
1114 				else {
1115 					Com_Printf (0, "...enabling WGL_EXT_swap_control\n");
1116 					ri.config.extWinSwapInterval = qTrue;
1117 				}
1118 			}
1119 		}
1120 		else
1121 			Com_Printf (0, "...WGL_EXT_swap_control not found\n");
1122 	}
1123 	else
1124 		Com_Printf (0, "...ignoring WGL_EXT_swap_control\n");
1125 #endif // WIN32
1126 }
1127 
1128 
1129 /*
1130 ==================
1131 R_Register
1132 
1133 Registers the renderer's cvars/commands and gets
1134 the latched ones during a vid_restart
1135 ==================
1136 */
R_Register(void)1137 static void R_Register (void)
1138 {
1139 	Cvar_GetLatchedVars (CVAR_LATCH_VIDEO);
1140 
1141 	e_test_0			= Cvar_Register ("e_test_0",			"0",			0);
1142 	e_test_1			= Cvar_Register ("e_test_1",			"0",			0);
1143 
1144 	gl_bitdepth			= Cvar_Register ("gl_bitdepth",			"0",			CVAR_LATCH_VIDEO);
1145 	gl_clear			= Cvar_Register ("gl_clear",			"0",			0);
1146 	gl_cull				= Cvar_Register ("gl_cull",				"1",			0);
1147 	gl_drawbuffer		= Cvar_Register ("gl_drawbuffer",		"GL_BACK",		0);
1148 	gl_driver			= Cvar_Register ("gl_driver",			GL_DRIVERNAME,	CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1149 	gl_dynamic			= Cvar_Register ("gl_dynamic",			"1",			0);
1150 	gl_errorcheck		= Cvar_Register ("gl_errorcheck",		"1",			CVAR_ARCHIVE);
1151 
1152 	r_allowExtensions				= Cvar_Register ("r_allowExtensions",				"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1153 	r_ext_BGRA						= Cvar_Register ("r_ext_BGRA",						"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1154 	r_ext_compiledVertexArray		= Cvar_Register ("r_ext_compiledVertexArray",		"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1155 	r_ext_drawRangeElements			= Cvar_Register ("r_ext_drawRangeElements",			"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1156 	r_ext_fragmentProgram			= Cvar_Register ("r_ext_fragmentProgram",			"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1157 	r_ext_generateMipmap			= Cvar_Register ("r_ext_generateMipmap",			"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1158 	r_ext_maxAnisotropy				= Cvar_Register ("r_ext_maxAnisotropy",				"2",		CVAR_ARCHIVE);
1159 	r_ext_multitexture				= Cvar_Register ("r_ext_multitexture",				"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1160 	r_ext_stencilTwoSide			= Cvar_Register ("r_ext_stencilTwoSide",			"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1161 	r_ext_stencilWrap				= Cvar_Register ("r_ext_stencilWrap",				"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1162 	r_ext_swapInterval				= Cvar_Register ("r_ext_swapInterval",				"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1163 	r_ext_texture3D					= Cvar_Register ("r_ext_texture3D",					"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1164 	r_ext_textureCompression		= Cvar_Register ("r_ext_textureCompression",		"0",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1165 	r_ext_textureCubeMap			= Cvar_Register ("r_ext_textureCubeMap",			"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1166 	r_ext_textureEdgeClamp			= Cvar_Register ("r_ext_textureEdgeClamp",			"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1167 	r_ext_textureEnvAdd				= Cvar_Register ("r_ext_textureEnvAdd",				"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1168 	r_ext_textureEnvCombine			= Cvar_Register ("r_ext_textureEnvCombine",			"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1169 	r_ext_textureEnvCombineNV4		= Cvar_Register ("r_ext_textureEnvCombineNV4",		"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1170 	r_ext_textureEnvDot3			= Cvar_Register ("r_ext_textureEnvDot3",			"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1171 	r_ext_textureFilterAnisotropic	= Cvar_Register ("r_ext_textureFilterAnisotropic",	"0",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1172 	r_ext_vertexBufferObject		= Cvar_Register ("r_ext_vertexBufferObject",		"0",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1173 	r_ext_vertexProgram				= Cvar_Register ("r_ext_vertexProgram",				"1",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1174 
1175 	gl_finish			= Cvar_Register ("gl_finish",			"0",			CVAR_ARCHIVE);
1176 	gl_flashblend		= Cvar_Register ("gl_flashblend",		"0",			CVAR_ARCHIVE);
1177 	gl_lightmap			= Cvar_Register ("gl_lightmap",			"0",			CVAR_CHEAT);
1178 	gl_lockpvs			= Cvar_Register ("gl_lockpvs",			"0",			CVAR_CHEAT);
1179 	gl_log				= Cvar_Register ("gl_log",				"0",			0);
1180 	gl_maxTexSize		= Cvar_Register ("gl_maxTexSize",		"0",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1181 	gl_mode				= Cvar_Register ("gl_mode",				"3",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1182 	gl_modulate			= Cvar_Register ("gl_modulate",			"1",			CVAR_ARCHIVE);
1183 
1184 	gl_shadows			= Cvar_Register ("gl_shadows",			"0",			CVAR_ARCHIVE);
1185 	gl_shownormals		= Cvar_Register ("gl_shownormals",		"0",			CVAR_CHEAT);
1186 	gl_showtris			= Cvar_Register ("gl_showtris",			"0",			CVAR_CHEAT);
1187 
1188 	qgl_debug			= Cvar_Register ("qgl_debug",			"0",			0);
1189 
1190 	r_caustics			= Cvar_Register ("r_caustics",			"1",			CVAR_ARCHIVE);
1191 	r_colorMipLevels	= Cvar_Register ("r_colorMipLevels",	"0",			CVAR_CHEAT|CVAR_LATCH_VIDEO);
1192 	r_debugBatching		= Cvar_Register ("r_debugBatching",		"0",			0);
1193 	r_debugCulling		= Cvar_Register ("r_debugCulling",		"0",			CVAR_CHEAT);
1194 	r_debugLighting		= Cvar_Register ("r_debugLighting",		"0",			CVAR_CHEAT);
1195 	r_debugSorting		= Cvar_Register ("r_debugSorting",		"0",			CVAR_CHEAT);
1196 	r_defaultFont		= Cvar_Register ("r_defaultFont",		"default",		CVAR_ARCHIVE);
1197 	r_detailTextures	= Cvar_Register ("r_detailTextures",	"1",			CVAR_ARCHIVE);
1198 	r_displayFreq		= Cvar_Register ("r_displayfreq",		"0",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1199 	r_drawDecals		= Cvar_Register ("r_drawDecals",		"1",			CVAR_CHEAT);
1200 	r_drawEntities		= Cvar_Register ("r_drawEntities",		"1",			CVAR_CHEAT);
1201 	r_drawPolys			= Cvar_Register ("r_drawPolys",			"1",			CVAR_CHEAT);
1202 	r_drawworld			= Cvar_Register ("r_drawworld",			"1",			CVAR_CHEAT);
1203 	r_facePlaneCull		= Cvar_Register ("r_facePlaneCull",		"1",			0);
1204 	r_flares			= Cvar_Register ("r_flares",			"1",			CVAR_ARCHIVE);
1205 	r_flareFade			= Cvar_Register ("r_flareFade",			"7",			CVAR_ARCHIVE);
1206 	r_flareSize			= Cvar_Register ("r_flareSize",			"40",			CVAR_ARCHIVE);
1207 	r_fontScale			= Cvar_Register ("r_fontScale",			"1",			CVAR_ARCHIVE);
1208 	r_fullbright		= Cvar_Register ("r_fullbright",		"0",			CVAR_CHEAT);
1209 	r_hwGamma			= Cvar_Register ("r_hwGamma",			"0",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1210 	r_lerpmodels		= Cvar_Register ("r_lerpmodels",		"1",			0);
1211 	r_lightlevel		= Cvar_Register ("r_lightlevel",		"0",			0);
1212 	r_lmMaxBlockSize	= Cvar_Register ("r_lmMaxBlockSize",	"4096",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1213 	r_lmModulate		= Cvar_Register ("r_lmModulate",		"2",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1214 	r_lmPacking			= Cvar_Register ("r_lmPacking",			"1",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1215 	r_noCull			= Cvar_Register ("r_noCull",			"0",			0);
1216 	r_noRefresh			= Cvar_Register ("r_noRefresh",			"0",			0);
1217 	r_noVis				= Cvar_Register ("r_noVis",				"0",			0);
1218 	r_offsetFactor		= Cvar_Register ("r_offsetFactor",		"-1",			CVAR_CHEAT);
1219 	r_offsetUnits		= Cvar_Register ("r_offsetUnits",		"-2",			CVAR_CHEAT);
1220 	r_patchDivLevel		= Cvar_Register ("r_patchDivLevel",		"4",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1221 	r_roundImagesDown	= Cvar_Register ("r_roundImagesDown",	"0",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1222 	r_skipBackend		= Cvar_Register ("r_skipBackend",		"0",			CVAR_CHEAT);
1223 	r_speeds			= Cvar_Register ("r_speeds",			"0",			0);
1224 	r_sphereCull		= Cvar_Register ("r_sphereCull",		"1",			0);
1225 	r_swapInterval		= Cvar_Register ("r_swapInterval",		"0",			CVAR_ARCHIVE);
1226 	r_textureBits		= Cvar_Register ("r_textureBits",		"default",		CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1227 	r_times				= Cvar_Register ("r_times",				"0",			0);
1228 	r_vertexLighting	= Cvar_Register ("r_vertexLighting",	"0",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1229 	r_zFarAbs			= Cvar_Register ("r_zFarAbs",			"0",			CVAR_CHEAT);
1230 	r_zFarMin			= Cvar_Register ("r_zFarMin",			"256",			CVAR_CHEAT);
1231 	r_zNear				= Cvar_Register ("r_zNear",				"4",			CVAR_CHEAT);
1232 
1233 	r_alphabits			= Cvar_Register ("r_alphabits",			"0",			CVAR_LATCH_VIDEO);
1234 	r_colorbits			= Cvar_Register ("r_colorbits",			"0",			CVAR_LATCH_VIDEO);
1235 	r_depthbits			= Cvar_Register ("r_depthbits",			"0",			CVAR_LATCH_VIDEO);
1236 	r_stencilbits		= Cvar_Register ("r_stencilbits",		"8",			CVAR_LATCH_VIDEO);
1237 	cl_stereo			= Cvar_Register ("cl_stereo",			"0",			CVAR_LATCH_VIDEO);
1238 	gl_allow_software	= Cvar_Register ("gl_allow_software",	"0",			CVAR_LATCH_VIDEO);
1239 	gl_stencilbuffer	= Cvar_Register ("gl_stencilbuffer",	"1",			CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1240 
1241 	vid_gamma			= Cvar_Register ("vid_gamma",			"1.0",						CVAR_ARCHIVE);
1242 	vid_gammapics		= Cvar_Register ("vid_gammapics",		"0",						CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1243 	vid_width			= Cvar_Register ("vid_width",			"0",						CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1244 	vid_height			= Cvar_Register ("vid_height",			"0",						CVAR_ARCHIVE|CVAR_LATCH_VIDEO);
1245 
1246 	intensity			= Cvar_Register ("intensity",			"2",						CVAR_ARCHIVE);
1247 
1248 	gl_jpgquality		= Cvar_Register ("gl_jpgquality",		"85",						CVAR_ARCHIVE);
1249 	gl_nobind			= Cvar_Register ("gl_nobind",			"0",						CVAR_CHEAT);
1250 	gl_picmip			= Cvar_Register ("gl_picmip",			"0",						CVAR_LATCH_VIDEO);
1251 	gl_screenshot		= Cvar_Register ("gl_screenshot",		"tga",						CVAR_ARCHIVE);
1252 
1253 	gl_texturemode		= Cvar_Register ("gl_texturemode",		"GL_LINEAR_MIPMAP_NEAREST",	CVAR_ARCHIVE);
1254 
1255 	// Force these to update next endframe
1256 	r_swapInterval->modified = qTrue;
1257 	gl_drawbuffer->modified = qTrue;
1258 	gl_texturemode->modified = qTrue;
1259 	r_ext_maxAnisotropy->modified = qTrue;
1260 	r_defaultFont->modified = qTrue;
1261 	vid_gamma->modified = qTrue;
1262 
1263 	// Add the various commands
1264 	cmd_gfxInfo			= Cmd_AddCommand ("gfxinfo",		R_GfxInfo_f,			"Prints out renderer information");
1265 	cmd_rendererClass	= Cmd_AddCommand ("rendererclass",	R_RendererClass_f,		"Prints out the renderer class");
1266 	cmd_eglRenderer		= Cmd_AddCommand ("egl_renderer",	R_RendererMsg_f,		"Spams to the server your renderer information");
1267 	cmd_eglVersion		= Cmd_AddCommand ("egl_version",	R_VersionMsg_f,			"Spams to the server your client version");
1268 }
1269 
1270 
1271 /*
1272 ===============
1273 R_Init
1274 ===============
1275 */
R_Init(void)1276 rInit_t R_Init (void)
1277 {
1278 	char	*rendererBuffer;
1279 	char	*vendorBuffer;
1280 	uint32	initTime;
1281 
1282 	initTime = Sys_UMilliseconds ();
1283 	Com_Printf (0, "\n-------- Refresh Initialization --------\n");
1284 
1285 	ri.frameCount = 1;
1286 	ri.reg.registerFrame = 1;
1287 
1288 	// Register renderer cvars
1289 	R_Register ();
1290 
1291 	// Set extension/max defaults
1292 	ri.config.extArbMultitexture = qFalse;
1293 	ri.config.extBGRA = qFalse;
1294 	ri.config.extCompiledVertArray = qFalse;
1295 	ri.config.extDrawRangeElements = qFalse;
1296 	ri.config.extFragmentProgram = qFalse;
1297 	ri.config.extSGISGenMipmap = qFalse;
1298 	ri.config.extSGISMultiTexture = qFalse;
1299 	ri.config.extStencilTwoSide = qFalse;
1300 	ri.config.extStencilWrap = qFalse;
1301 	ri.config.extTex3D = qFalse;
1302 	ri.config.extTexCompression = qFalse;
1303 	ri.config.extTexCubeMap = qFalse;
1304 	ri.config.extTexEdgeClamp = qFalse;
1305 	ri.config.extTexEnvAdd = qFalse;
1306 	ri.config.extTexEnvCombine = qFalse;
1307 	ri.config.extNVTexEnvCombine4 = qFalse;
1308 	ri.config.extTexEnvDot3 = qFalse;
1309 	ri.config.extTexFilterAniso = qFalse;
1310 	ri.config.extVertexBufferObject = qFalse;
1311 	ri.config.extVertexProgram = qFalse;
1312 	ri.config.extWinSwapInterval = qFalse;
1313 
1314 	ri.config.max3DTexSize = 0;
1315 	ri.config.maxAniso = 0;
1316 	ri.config.maxCMTexSize = 0;
1317 	ri.config.maxElementVerts = 0;
1318 	ri.config.maxElementIndices = 0;
1319 	ri.config.maxTexCoords = 0;
1320 	ri.config.maxTexImageUnits = 0;
1321 	ri.config.maxTexSize = 256;
1322 	ri.config.maxTexUnits = 1;
1323 
1324 	// Reset static refresh info
1325 	ri.lastValidMode = -1;
1326 	ri.useStencil = qFalse;
1327 	ri.cColorBits = 0;
1328 	ri.cAlphaBits = 0;
1329 	ri.cDepthBits = 0;
1330 	ri.cStencilBits = 0;
1331 
1332 	// Create memory pools
1333 	ri.decalSysPool = Mem_CreatePool ("Refresh: Decal system");
1334 	ri.fontSysPool = Mem_CreatePool ("Refresh: Font system");
1335 	ri.genericPool = Mem_CreatePool ("Refresh: Generic");
1336 	ri.imageSysPool = Mem_CreatePool ("Refresh: Image system");
1337 	ri.lightSysPool = Mem_CreatePool ("Refresh: Light system");
1338 	ri.modelSysPool = Mem_CreatePool ("Refresh: Model system");
1339 	ri.programSysPool = Mem_CreatePool ("Refresh: Program system");
1340 	ri.shaderSysPool = Mem_CreatePool ("Refresh: Shader system");
1341 
1342 	// Initialize our QGL dynamic bindings
1343 	if (!QGL_Init (gl_driver->string)) {
1344 		Com_Printf (PRNT_ERROR, "...could not load \"%s\"\n", gl_driver->string);
1345 		QGL_Shutdown ();
1346 		return R_INIT_QGL_FAIL;
1347 	}
1348 
1349 	// Initialize OS-specific parts of OpenGL
1350 	if (!GLimp_Init ()) {
1351 		Com_Printf (PRNT_ERROR, "...unable to init gl implementation\n");
1352 		QGL_Shutdown ();
1353 		return R_INIT_OS_FAIL;
1354 	}
1355 
1356 	// Create the window and set up the context
1357 	if (!R_SetMode ()) {
1358 		Com_Printf (PRNT_ERROR, "...could not set video mode\n");
1359 		QGL_Shutdown ();
1360 		return R_INIT_MODE_FAIL;
1361 	}
1362 
1363 	// Vendor string
1364 	ri.vendorString = qglGetString (GL_VENDOR);
1365 	Com_Printf (0, "GL_VENDOR: %s\n", ri.vendorString);
1366 
1367 	vendorBuffer = Mem_PoolStrDup ((char *)ri.vendorString, ri.genericPool, 0);
1368 	Q_strlwr (vendorBuffer);
1369 
1370 	// Renderer string
1371 	ri.rendererString = qglGetString (GL_RENDERER);
1372 	Com_Printf (0, "GL_RENDERER: %s\n", ri.rendererString);
1373 
1374 	rendererBuffer = Mem_PoolStrDup ((char *)ri.rendererString, ri.genericPool, 0);
1375 	Q_strlwr (rendererBuffer);
1376 
1377 	// Version string
1378 	ri.versionString = qglGetString (GL_VERSION);
1379 	Com_Printf (0, "GL_VERSION: %s\n", ri.versionString);
1380 
1381 	// Extension string
1382 	ri.extensionString = qglGetString (GL_EXTENSIONS);
1383 
1384 	// Decide on a renderer class
1385 	if (strstr (rendererBuffer, "glint"))			ri.renderClass = REND_CLASS_3DLABS_GLINT_MX;
1386 	else if (strstr (rendererBuffer, "permedia"))	ri.renderClass = REND_CLASS_3DLABS_PERMEDIA;
1387 	else if (strstr (rendererBuffer, "glzicd"))		ri.renderClass = REND_CLASS_3DLABS_REALIZM;
1388 	else if (strstr (vendorBuffer, "ati ")) {
1389 		if (strstr (vendorBuffer, "radeon"))
1390 			ri.renderClass = REND_CLASS_ATI_RADEON;
1391 		else
1392 			ri.renderClass = REND_CLASS_ATI;
1393 	}
1394 	else if (strstr (vendorBuffer, "intel"))		ri.renderClass = REND_CLASS_INTEL;
1395 	else if (strstr (vendorBuffer, "nvidia")) {
1396 		if (strstr (rendererBuffer, "geforce"))
1397 			ri.renderClass = REND_CLASS_NVIDIA_GEFORCE;
1398 		else
1399 			ri.renderClass = REND_CLASS_NVIDIA;
1400 	}
1401 	else if (strstr	(rendererBuffer, "pmx"))		ri.renderClass = REND_CLASS_PMX;
1402 	else if (strstr	(rendererBuffer, "pcx1"))		ri.renderClass = REND_CLASS_POWERVR_PCX1;
1403 	else if (strstr	(rendererBuffer, "pcx2"))		ri.renderClass = REND_CLASS_POWERVR_PCX2;
1404 	else if (strstr	(rendererBuffer, "verite"))		ri.renderClass = REND_CLASS_RENDITION;
1405 	else if (strstr (vendorBuffer, "s3"))			ri.renderClass = REND_CLASS_S3;
1406 	else if (strstr (rendererBuffer, "prosavage"))	ri.renderClass = REND_CLASS_S3;
1407 	else if (strstr (rendererBuffer, "twister"))	ri.renderClass = REND_CLASS_S3;
1408 	else if (strstr	(vendorBuffer, "sgi"))			ri.renderClass = REND_CLASS_SGI;
1409 	else if (strstr	(vendorBuffer, "sis"))			ri.renderClass = REND_CLASS_SIS;
1410 	else if (strstr (rendererBuffer, "voodoo"))		ri.renderClass = REND_CLASS_VOODOO;
1411 	else {
1412 		if (strstr (rendererBuffer, "gdi generic")) {
1413 			ri.renderClass = REND_CLASS_MCD;
1414 
1415 			// MCD has buffering issues
1416 			Cvar_VariableSetValue (gl_finish, 1, qTrue);
1417 		}
1418 		else
1419 			ri.renderClass = REND_CLASS_DEFAULT;
1420 	}
1421 
1422 	// Print the renderer class
1423 	Com_Printf (0, "Renderer Class: %s\n", R_RendererClass ());
1424 
1425 #ifdef GL_FORCEFINISH
1426 	Cvar_VariableSetValue (gl_finish, 1, qTrue);
1427 #endif
1428 
1429 	// Check stencil buffer availability and usability
1430 	Com_Printf (0, "...stencil buffer ");
1431 	if (gl_stencilbuffer->intVal && ri.cStencilBits > 0) {
1432 		if (ri.renderClass == REND_CLASS_VOODOO)
1433 			Com_Printf (0, "ignored\n");
1434 		else {
1435 			Com_Printf (0, "available\n");
1436 			ri.useStencil = qTrue;
1437 		}
1438 	}
1439 	else {
1440 		Com_Printf (0, "disabled\n");
1441 	}
1442 
1443 	// Grab opengl extensions
1444 	if (r_allowExtensions->intVal)
1445 		GL_InitExtensions ();
1446 	else
1447 		Com_Printf (0, "...ignoring OpenGL extensions\n");
1448 
1449 	// Map overbrights
1450 	ri.pow2MapOvrbr = r_lmModulate->intVal;
1451 	if (ri.pow2MapOvrbr > 0)
1452 		ri.pow2MapOvrbr = pow (2, ri.pow2MapOvrbr) / 255.0f;
1453 	else
1454 		ri.pow2MapOvrbr = 1.0f / 255.0f;
1455 
1456 	// Retreive generic information
1457 	if (gl_maxTexSize->intVal >= 256) {
1458 		ri.config.maxTexSize = gl_maxTexSize->intVal;
1459 		Q_NearestPow (&ri.config.maxTexSize, qTrue);
1460 
1461 		Com_Printf (0, "Using forced maximum texture size of: %ix%i\n", ri.config.maxTexSize, ri.config.maxTexSize);
1462 	}
1463 	else {
1464 		qglGetIntegerv (GL_MAX_TEXTURE_SIZE, &ri.config.maxTexSize);
1465 		Q_NearestPow (&ri.config.maxTexSize, qTrue);
1466 		if (ri.config.maxTexSize < 256) {
1467 			Com_Printf (0, "Maximum texture size forced up to 256x256 from %i\n", ri.config.maxTexSize);
1468 			ri.config.maxTexSize = 256;
1469 		}
1470 		else
1471 			Com_Printf (0, "Using video card maximum texture size of %ix%i\n", ri.config.maxTexSize, ri.config.maxTexSize);
1472 	}
1473 
1474 	Com_Printf (0, "----------------------------------------\n");
1475 
1476 	// Set the default state
1477 	RB_SetDefaultState ();
1478 
1479 	// Sub-system init
1480 	Swap_Init();
1481 	R_ImageInit ();
1482 	R_ProgramInit ();
1483 	R_ShaderInit ();
1484 	R_FontInit ();
1485 	R_MediaInit ();
1486 	R_ModelInit ();
1487 	R_EntityInit ();
1488 	R_WorldInit ();
1489 	R_PolyInit ();
1490 	R_DecalInit ();
1491 	RB_Init ();
1492 	RF_2DInit ();
1493 
1494 	// Check for gl errors
1495 	GL_CheckForError ("R_Init");
1496 
1497 	Com_Printf (0, "----- Refresh Initialized %6ums -----\n", Sys_UMilliseconds()-initTime);
1498 
1499 	Mem_Free (rendererBuffer);
1500 	Mem_Free (vendorBuffer);
1501 
1502 	return R_INIT_SUCCESS;
1503 }
1504 
1505 
1506 /*
1507 ===============
1508 R_Shutdown
1509 ===============
1510 */
R_Shutdown(qBool full)1511 void R_Shutdown (qBool full)
1512 {
1513 	Com_Printf (0, "\n----------- Refresh Shutdown -----------\n");
1514 
1515 	// Remove commands
1516 	Cmd_RemoveCommand ("gfxinfo", cmd_gfxInfo);
1517 	Cmd_RemoveCommand ("rendererclass", cmd_rendererClass);
1518 	Cmd_RemoveCommand ("egl_renderer", cmd_eglRenderer);
1519 	Cmd_RemoveCommand ("egl_version", cmd_eglVersion);
1520 
1521 	// Shutdown subsystems
1522 	R_FontShutdown ();
1523 	R_ShaderShutdown ();
1524 	R_ProgramShutdown ();
1525 	R_ImageShutdown ();
1526 	R_ModelShutdown ();
1527 	R_WorldShutdown ();
1528 	RB_Shutdown ();
1529 
1530 	Com_Printf (0, "----------------------------------------\n");
1531 
1532 	// Shutdown OS specific OpenGL stuff like contexts, etc
1533 	GLimp_Shutdown (full);
1534 
1535 	// Shutdown our QGL subsystem
1536 	QGL_Shutdown ();
1537 
1538 	Com_Printf (0, "----------------------------------------\n");
1539 }
1540