00001
00032
00033
00034
00035 #define GLH_EXT_SINGLE_FILE
00036
00037 #include "linden_common.h"
00038
00039 #include "boost/tokenizer.hpp"
00040
00041 #include "llsys.h"
00042
00043 #include "llgl.h"
00044 #include "llglimmediate.h"
00045
00046 #include "llerror.h"
00047 #include "llquaternion.h"
00048 #include "llmath.h"
00049 #include "m4math.h"
00050 #include "llstring.h"
00051
00052 #include "llglheaders.h"
00053
00054 #ifdef _DEBUG
00055
00056 #endif
00057
00058 BOOL gDebugGL = FALSE;
00059 BOOL gClothRipple = FALSE;
00060 BOOL gNoRender = FALSE;
00061 LLMatrix4 gGLObliqueProjectionInverse;
00062
00063 LLGLNamePool::pool_list_t LLGLNamePool::sInstances;
00064
00065 #if (LL_WINDOWS || LL_LINUX) && !LL_MESA_HEADLESS
00066
00067
00068 PFNGLWEIGHTPOINTERARBPROC glWeightPointerARB = NULL;
00069 PFNGLVERTEXBLENDARBPROC glVertexBlendARB = NULL;
00070 PFNGLWEIGHTFVARBPROC glWeightfvARB = NULL;
00071
00072
00073 PFNGLBINDBUFFERARBPROC glBindBufferARB = NULL;
00074 PFNGLDELETEBUFFERSARBPROC glDeleteBuffersARB = NULL;
00075 PFNGLGENBUFFERSARBPROC glGenBuffersARB = NULL;
00076 PFNGLISBUFFERARBPROC glIsBufferARB = NULL;
00077 PFNGLBUFFERDATAARBPROC glBufferDataARB = NULL;
00078 PFNGLBUFFERSUBDATAARBPROC glBufferSubDataARB = NULL;
00079 PFNGLGETBUFFERSUBDATAARBPROC glGetBufferSubDataARB = NULL;
00080 PFNGLMAPBUFFERARBPROC glMapBufferARB = NULL;
00081 PFNGLUNMAPBUFFERARBPROC glUnmapBufferARB = NULL;
00082 PFNGLGETBUFFERPARAMETERIVARBPROC glGetBufferParameterivARB = NULL;
00083 PFNGLGETBUFFERPOINTERVARBPROC glGetBufferPointervARB = NULL;
00084
00085
00086 PFNGLNEWOBJECTBUFFERATIPROC glNewObjectBufferATI = NULL;
00087 PFNGLISOBJECTBUFFERATIPROC glIsObjectBufferATI = NULL;
00088 PFNGLUPDATEOBJECTBUFFERATIPROC glUpdateObjectBufferATI = NULL;
00089 PFNGLGETOBJECTBUFFERFVATIPROC glGetObjectBufferfvATI = NULL;
00090 PFNGLGETOBJECTBUFFERIVATIPROC glGetObjectBufferivATI = NULL;
00091 PFNGLFREEOBJECTBUFFERATIPROC glFreeObjectBufferATI = NULL;
00092 PFNGLARRAYOBJECTATIPROC glArrayObjectATI = NULL;
00093 PFNGLVERTEXATTRIBARRAYOBJECTATIPROC glVertexAttribArrayObjectATI = NULL;
00094 PFNGLGETARRAYOBJECTFVATIPROC glGetArrayObjectfvATI = NULL;
00095 PFNGLGETARRAYOBJECTIVATIPROC glGetArrayObjectivATI = NULL;
00096 PFNGLVARIANTARRAYOBJECTATIPROC glVariantObjectArrayATI = NULL;
00097 PFNGLGETVARIANTARRAYOBJECTFVATIPROC glGetVariantArrayObjectfvATI = NULL;
00098 PFNGLGETVARIANTARRAYOBJECTIVATIPROC glGetVariantArrayObjectivATI = NULL;
00099
00100
00101 PFNGLGENQUERIESARBPROC glGenQueriesARB = NULL;
00102 PFNGLDELETEQUERIESARBPROC glDeleteQueriesARB = NULL;
00103 PFNGLISQUERYARBPROC glIsQueryARB = NULL;
00104 PFNGLBEGINQUERYARBPROC glBeginQueryARB = NULL;
00105 PFNGLENDQUERYARBPROC glEndQueryARB = NULL;
00106 PFNGLGETQUERYIVARBPROC glGetQueryivARB = NULL;
00107 PFNGLGETQUERYOBJECTIVARBPROC glGetQueryObjectivARB = NULL;
00108 PFNGLGETQUERYOBJECTUIVARBPROC glGetQueryObjectuivARB = NULL;
00109
00110
00111 PFNGLPOINTPARAMETERFARBPROC glPointParameterfARB = NULL;
00112 PFNGLPOINTPARAMETERFVARBPROC glPointParameterfvARB = NULL;
00113
00114
00115 PFNGLISRENDERBUFFEREXTPROC glIsRenderbufferEXT = NULL;
00116 PFNGLBINDRENDERBUFFEREXTPROC glBindRenderbufferEXT = NULL;
00117 PFNGLDELETERENDERBUFFERSEXTPROC glDeleteRenderbuffersEXT = NULL;
00118 PFNGLGENRENDERBUFFERSEXTPROC glGenRenderbuffersEXT = NULL;
00119 PFNGLRENDERBUFFERSTORAGEEXTPROC glRenderbufferStorageEXT = NULL;
00120 PFNGLGETRENDERBUFFERPARAMETERIVEXTPROC glGetRenderbufferParameterivEXT = NULL;
00121 PFNGLISFRAMEBUFFEREXTPROC glIsFramebufferEXT = NULL;
00122 PFNGLBINDFRAMEBUFFEREXTPROC glBindFramebufferEXT = NULL;
00123 PFNGLDELETEFRAMEBUFFERSEXTPROC glDeleteFramebuffersEXT = NULL;
00124 PFNGLGENFRAMEBUFFERSEXTPROC glGenFramebuffersEXT = NULL;
00125 PFNGLCHECKFRAMEBUFFERSTATUSEXTPROC glCheckFramebufferStatusEXT = NULL;
00126 PFNGLFRAMEBUFFERTEXTURE1DEXTPROC glFramebufferTexture1DEXT = NULL;
00127 PFNGLFRAMEBUFFERTEXTURE2DEXTPROC glFramebufferTexture2DEXT = NULL;
00128 PFNGLFRAMEBUFFERTEXTURE3DEXTPROC glFramebufferTexture3DEXT = NULL;
00129 PFNGLFRAMEBUFFERRENDERBUFFEREXTPROC glFramebufferRenderbufferEXT = NULL;
00130 PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVEXTPROC glGetFramebufferAttachmentParameterivEXT = NULL;
00131 PFNGLGENERATEMIPMAPEXTPROC glGenerateMipmapEXT = NULL;
00132
00133
00134 PFNGLDELETEOBJECTARBPROC glDeleteObjectARB = NULL;
00135 PFNGLGETHANDLEARBPROC glGetHandleARB = NULL;
00136 PFNGLDETACHOBJECTARBPROC glDetachObjectARB = NULL;
00137 PFNGLCREATESHADEROBJECTARBPROC glCreateShaderObjectARB = NULL;
00138 PFNGLSHADERSOURCEARBPROC glShaderSourceARB = NULL;
00139 PFNGLCOMPILESHADERARBPROC glCompileShaderARB = NULL;
00140 PFNGLCREATEPROGRAMOBJECTARBPROC glCreateProgramObjectARB = NULL;
00141 PFNGLATTACHOBJECTARBPROC glAttachObjectARB = NULL;
00142 PFNGLLINKPROGRAMARBPROC glLinkProgramARB = NULL;
00143 PFNGLUSEPROGRAMOBJECTARBPROC glUseProgramObjectARB = NULL;
00144 PFNGLVALIDATEPROGRAMARBPROC glValidateProgramARB = NULL;
00145 PFNGLUNIFORM1FARBPROC glUniform1fARB = NULL;
00146 PFNGLUNIFORM2FARBPROC glUniform2fARB = NULL;
00147 PFNGLUNIFORM3FARBPROC glUniform3fARB = NULL;
00148 PFNGLUNIFORM4FARBPROC glUniform4fARB = NULL;
00149 PFNGLUNIFORM1IARBPROC glUniform1iARB = NULL;
00150 PFNGLUNIFORM2IARBPROC glUniform2iARB = NULL;
00151 PFNGLUNIFORM3IARBPROC glUniform3iARB = NULL;
00152 PFNGLUNIFORM4IARBPROC glUniform4iARB = NULL;
00153 PFNGLUNIFORM1FVARBPROC glUniform1fvARB = NULL;
00154 PFNGLUNIFORM2FVARBPROC glUniform2fvARB = NULL;
00155 PFNGLUNIFORM3FVARBPROC glUniform3fvARB = NULL;
00156 PFNGLUNIFORM4FVARBPROC glUniform4fvARB = NULL;
00157 PFNGLUNIFORM1IVARBPROC glUniform1ivARB = NULL;
00158 PFNGLUNIFORM2IVARBPROC glUniform2ivARB = NULL;
00159 PFNGLUNIFORM3IVARBPROC glUniform3ivARB = NULL;
00160 PFNGLUNIFORM4IVARBPROC glUniform4ivARB = NULL;
00161 PFNGLUNIFORMMATRIX2FVARBPROC glUniformMatrix2fvARB = NULL;
00162 PFNGLUNIFORMMATRIX3FVARBPROC glUniformMatrix3fvARB = NULL;
00163 PFNGLUNIFORMMATRIX4FVARBPROC glUniformMatrix4fvARB = NULL;
00164 PFNGLGETOBJECTPARAMETERFVARBPROC glGetObjectParameterfvARB = NULL;
00165 PFNGLGETOBJECTPARAMETERIVARBPROC glGetObjectParameterivARB = NULL;
00166 PFNGLGETINFOLOGARBPROC glGetInfoLogARB = NULL;
00167 PFNGLGETATTACHEDOBJECTSARBPROC glGetAttachedObjectsARB = NULL;
00168 PFNGLGETUNIFORMLOCATIONARBPROC glGetUniformLocationARB = NULL;
00169 PFNGLGETACTIVEUNIFORMARBPROC glGetActiveUniformARB = NULL;
00170 PFNGLGETUNIFORMFVARBPROC glGetUniformfvARB = NULL;
00171 PFNGLGETUNIFORMIVARBPROC glGetUniformivARB = NULL;
00172 PFNGLGETSHADERSOURCEARBPROC glGetShaderSourceARB = NULL;
00173
00174
00175 #if LL_LINUX
00176 PFNGLVERTEXATTRIB1DARBPROC glVertexAttrib1dARB = NULL;
00177 PFNGLVERTEXATTRIB1DVARBPROC glVertexAttrib1dvARB = NULL;
00178 PFNGLVERTEXATTRIB1FARBPROC glVertexAttrib1fARB = NULL;
00179 PFNGLVERTEXATTRIB1FVARBPROC glVertexAttrib1fvARB = NULL;
00180 PFNGLVERTEXATTRIB1SARBPROC glVertexAttrib1sARB = NULL;
00181 PFNGLVERTEXATTRIB1SVARBPROC glVertexAttrib1svARB = NULL;
00182 PFNGLVERTEXATTRIB2DARBPROC glVertexAttrib2dARB = NULL;
00183 PFNGLVERTEXATTRIB2DVARBPROC glVertexAttrib2dvARB = NULL;
00184 PFNGLVERTEXATTRIB2FARBPROC glVertexAttrib2fARB = NULL;
00185 PFNGLVERTEXATTRIB2FVARBPROC glVertexAttrib2fvARB = NULL;
00186 PFNGLVERTEXATTRIB2SARBPROC glVertexAttrib2sARB = NULL;
00187 PFNGLVERTEXATTRIB2SVARBPROC glVertexAttrib2svARB = NULL;
00188 PFNGLVERTEXATTRIB3DARBPROC glVertexAttrib3dARB = NULL;
00189 PFNGLVERTEXATTRIB3DVARBPROC glVertexAttrib3dvARB = NULL;
00190 PFNGLVERTEXATTRIB3FARBPROC glVertexAttrib3fARB = NULL;
00191 PFNGLVERTEXATTRIB3FVARBPROC glVertexAttrib3fvARB = NULL;
00192 PFNGLVERTEXATTRIB3SARBPROC glVertexAttrib3sARB = NULL;
00193 PFNGLVERTEXATTRIB3SVARBPROC glVertexAttrib3svARB = NULL;
00194 #endif // LL_LINUX
00195 PFNGLVERTEXATTRIB4NBVARBPROC glVertexAttrib4nbvARB = NULL;
00196 PFNGLVERTEXATTRIB4NIVARBPROC glVertexAttrib4nivARB = NULL;
00197 PFNGLVERTEXATTRIB4NSVARBPROC glVertexAttrib4nsvARB = NULL;
00198 PFNGLVERTEXATTRIB4NUBARBPROC glVertexAttrib4nubARB = NULL;
00199 PFNGLVERTEXATTRIB4NUBVARBPROC glVertexAttrib4nubvARB = NULL;
00200 PFNGLVERTEXATTRIB4NUIVARBPROC glVertexAttrib4nuivARB = NULL;
00201 PFNGLVERTEXATTRIB4NUSVARBPROC glVertexAttrib4nusvARB = NULL;
00202 #if LL_LINUX
00203 PFNGLVERTEXATTRIB4BVARBPROC glVertexAttrib4bvARB = NULL;
00204 PFNGLVERTEXATTRIB4DARBPROC glVertexAttrib4dARB = NULL;
00205 PFNGLVERTEXATTRIB4DVARBPROC glVertexAttrib4dvARB = NULL;
00206 PFNGLVERTEXATTRIB4FARBPROC glVertexAttrib4fARB = NULL;
00207 PFNGLVERTEXATTRIB4FVARBPROC glVertexAttrib4fvARB = NULL;
00208 PFNGLVERTEXATTRIB4IVARBPROC glVertexAttrib4ivARB = NULL;
00209 PFNGLVERTEXATTRIB4SARBPROC glVertexAttrib4sARB = NULL;
00210 PFNGLVERTEXATTRIB4SVARBPROC glVertexAttrib4svARB = NULL;
00211 PFNGLVERTEXATTRIB4UBVARBPROC glVertexAttrib4ubvARB = NULL;
00212 PFNGLVERTEXATTRIB4UIVARBPROC glVertexAttrib4uivARB = NULL;
00213 PFNGLVERTEXATTRIB4USVARBPROC glVertexAttrib4usvARB = NULL;
00214 PFNGLVERTEXATTRIBPOINTERARBPROC glVertexAttribPointerARB = NULL;
00215 PFNGLENABLEVERTEXATTRIBARRAYARBPROC glEnableVertexAttribArrayARB = NULL;
00216 PFNGLDISABLEVERTEXATTRIBARRAYARBPROC glDisableVertexAttribArrayARB = NULL;
00217 PFNGLPROGRAMSTRINGARBPROC glProgramStringARB = NULL;
00218 PFNGLBINDPROGRAMARBPROC glBindProgramARB = NULL;
00219 PFNGLDELETEPROGRAMSARBPROC glDeleteProgramsARB = NULL;
00220 PFNGLGENPROGRAMSARBPROC glGenProgramsARB = NULL;
00221 PFNGLPROGRAMENVPARAMETER4DARBPROC glProgramEnvParameter4dARB = NULL;
00222 PFNGLPROGRAMENVPARAMETER4DVARBPROC glProgramEnvParameter4dvARB = NULL;
00223 PFNGLPROGRAMENVPARAMETER4FARBPROC glProgramEnvParameter4fARB = NULL;
00224 PFNGLPROGRAMENVPARAMETER4FVARBPROC glProgramEnvParameter4fvARB = NULL;
00225 PFNGLPROGRAMLOCALPARAMETER4DARBPROC glProgramLocalParameter4dARB = NULL;
00226 PFNGLPROGRAMLOCALPARAMETER4DVARBPROC glProgramLocalParameter4dvARB = NULL;
00227 PFNGLPROGRAMLOCALPARAMETER4FARBPROC glProgramLocalParameter4fARB = NULL;
00228 PFNGLPROGRAMLOCALPARAMETER4FVARBPROC glProgramLocalParameter4fvARB = NULL;
00229 PFNGLGETPROGRAMENVPARAMETERDVARBPROC glGetProgramEnvParameterdvARB = NULL;
00230 PFNGLGETPROGRAMENVPARAMETERFVARBPROC glGetProgramEnvParameterfvARB = NULL;
00231 PFNGLGETPROGRAMLOCALPARAMETERDVARBPROC glGetProgramLocalParameterdvARB = NULL;
00232 PFNGLGETPROGRAMLOCALPARAMETERFVARBPROC glGetProgramLocalParameterfvARB = NULL;
00233 PFNGLGETPROGRAMIVARBPROC glGetProgramivARB = NULL;
00234 PFNGLGETPROGRAMSTRINGARBPROC glGetProgramStringARB = NULL;
00235 PFNGLGETVERTEXATTRIBDVARBPROC glGetVertexAttribdvARB = NULL;
00236 PFNGLGETVERTEXATTRIBFVARBPROC glGetVertexAttribfvARB = NULL;
00237 PFNGLGETVERTEXATTRIBIVARBPROC glGetVertexAttribivARB = NULL;
00238 PFNGLGETVERTEXATTRIBPOINTERVARBPROC glGetVertexAttribPointervARB = NULL;
00239 PFNGLISPROGRAMARBPROC glIsProgramARB = NULL;
00240 #endif // LL_LINUX
00241 PFNGLBINDATTRIBLOCATIONARBPROC glBindAttribLocationARB = NULL;
00242 PFNGLGETACTIVEATTRIBARBPROC glGetActiveAttribARB = NULL;
00243 PFNGLGETATTRIBLOCATIONARBPROC glGetAttribLocationARB = NULL;
00244
00245 #if LL_WINDOWS
00246 PFNWGLSWAPINTERVALEXTPROC wglSwapIntervalEXT = NULL;
00247 #endif
00248
00249 #if LL_LINUX
00250 PFNGLCOLORTABLEEXTPROC glColorTableEXT = NULL;
00251 #endif // LL_LINUX
00252
00253 #endif
00254
00255 LLGLManager gGLManager;
00256
00257 LLGLManager::LLGLManager() :
00258 mInited(FALSE),
00259 mIsDisabled(FALSE),
00260
00261 mHasMultitexture(FALSE),
00262 mNumTextureUnits(1),
00263 mHasMipMapGeneration(FALSE),
00264 mHasPalettedTextures(FALSE),
00265 mHasCompressedTextures(FALSE),
00266 mHasFramebufferObject(FALSE),
00267
00268 mHasVertexBufferObject(FALSE),
00269 mHasPBuffer(FALSE),
00270 mHasShaderObjects(FALSE),
00271 mHasVertexShader(FALSE),
00272 mHasFragmentShader(FALSE),
00273 mHasOcclusionQuery(FALSE),
00274 mHasPointParameters(FALSE),
00275
00276 mHasAnisotropic(FALSE),
00277 mHasARBEnvCombine(FALSE),
00278 mHasCubeMap(FALSE),
00279
00280 mIsATI(FALSE),
00281 mIsNVIDIA(FALSE),
00282 mIsIntel(FALSE),
00283 mIsGF2or4MX(FALSE),
00284 mIsGF3(FALSE),
00285 mIsGFFX(FALSE),
00286 mATIOffsetVerticalLines(FALSE),
00287
00288 mHasRequirements(TRUE),
00289
00290 mHasSeparateSpecularColor(FALSE),
00291
00292 mDriverVersionMajor(1),
00293 mDriverVersionMinor(0),
00294 mDriverVersionRelease(0),
00295 mGLVersion(1.0f),
00296
00297 mVRAM(0),
00298 mGLMaxVertexRange(0),
00299 mGLMaxIndexRange(0)
00300 {
00301 }
00302
00303
00304
00305
00306 void LLGLManager::initWGL()
00307 {
00308 mHasPBuffer = FALSE;
00309 #if LL_WINDOWS && !LL_MESA_HEADLESS
00310 if (!glh_init_extensions("WGL_ARB_pixel_format"))
00311 {
00312 LL_WARNS("RenderInit") << "No ARB pixel format extensions" << LL_ENDL;
00313 }
00314
00315 if (ExtensionExists("WGL_EXT_swap_control", gGLHExts.mSysExts))
00316 {
00317 GLH_EXT_NAME(wglSwapIntervalEXT) = (PFNWGLSWAPINTERVALEXTPROC)GLH_EXT_GET_PROC_ADDRESS("wglSwapIntervalEXT");
00318 }
00319
00320 if( !glh_init_extensions("WGL_ARB_pbuffer") )
00321 {
00322 LL_WARNS("RenderInit") << "No ARB WGL PBuffer extensions" << LL_ENDL;
00323 }
00324
00325 if( !glh_init_extensions("WGL_ARB_render_texture") )
00326 {
00327 LL_WARNS("RenderInit") << "No ARB WGL render texture extensions" << LL_ENDL;
00328 }
00329
00330 mHasPBuffer = ExtensionExists("WGL_ARB_pbuffer", gGLHExts.mSysExts) &&
00331 ExtensionExists("WGL_ARB_render_texture", gGLHExts.mSysExts) &&
00332 ExtensionExists("WGL_ARB_pixel_format", gGLHExts.mSysExts);
00333 #endif
00334 }
00335
00336
00337 bool LLGLManager::initGL()
00338 {
00339 if (mInited)
00340 {
00341 LL_ERRS("RenderInit") << "Calling init on LLGLManager after already initialized!" << LL_ENDL;
00342 }
00343
00344 GLint alpha_bits;
00345 glGetIntegerv( GL_ALPHA_BITS, &alpha_bits );
00346 if( 8 != alpha_bits )
00347 {
00348 LL_WARNS("RenderInit") << "Frame buffer has less than 8 bits of alpha. Avatar texture compositing will fail." << LL_ENDL;
00349 }
00350
00351
00352
00353 mGLVendor = LLString((const char *)glGetString(GL_VENDOR));
00354 LLString::toUpper(mGLVendor);
00355
00356 mGLRenderer = LLString((const char *)glGetString(GL_RENDERER));
00357 LLString::toUpper(mGLRenderer);
00358
00359 parse_gl_version( &mDriverVersionMajor,
00360 &mDriverVersionMinor,
00361 &mDriverVersionRelease,
00362 &mDriverVersionVendorString );
00363
00364 mGLVersion = mDriverVersionMajor + mDriverVersionMinor * .1f;
00365
00366
00367
00368 if (mGLVendor.substr(0,4) == "ATI ")
00369 {
00370 mGLVendorShort = "ATI";
00371 BOOL mobile = FALSE;
00372 if (mGLRenderer.find("MOBILITY") != LLString::npos)
00373 {
00374 mobile = TRUE;
00375 }
00376 mIsATI = TRUE;
00377
00378 #if LL_WINDOWS && !LL_MESA_HEADLESS
00379 if (mDriverVersionRelease < 3842)
00380 {
00381 mATIOffsetVerticalLines = TRUE;
00382 }
00383 #endif // LL_WINDOWS
00384 }
00385 else if (mGLVendor.find("NVIDIA ") != LLString::npos)
00386 {
00387 mGLVendorShort = "NVIDIA";
00388 mIsNVIDIA = TRUE;
00389 if ( mGLRenderer.find("GEFORCE4 MX") != LLString::npos
00390 || mGLRenderer.find("GEFORCE2") != LLString::npos
00391 || mGLRenderer.find("GEFORCE 2") != LLString::npos
00392 || mGLRenderer.find("GEFORCE4 460 GO") != LLString::npos
00393 || mGLRenderer.find("GEFORCE4 440 GO") != LLString::npos
00394 || mGLRenderer.find("GEFORCE4 420 GO") != LLString::npos)
00395 {
00396 mIsGF2or4MX = TRUE;
00397 }
00398 else if (mGLRenderer.find("GEFORCE FX") != LLString::npos
00399 || mGLRenderer.find("QUADRO FX") != LLString::npos
00400 || mGLRenderer.find("NV34") != LLString::npos)
00401 {
00402 mIsGFFX = TRUE;
00403 }
00404 else if(mGLRenderer.find("GEFORCE3") != LLString::npos)
00405 {
00406 mIsGF3 = TRUE;
00407 }
00408
00409 }
00410 else if (mGLVendor.find("INTEL") != LLString::npos
00411 #if LL_LINUX
00412
00413
00414 || mGLRenderer.find("INTEL") != LLString::npos
00415 #endif //LL_LINUX
00416 )
00417 {
00418 mGLVendorShort = "INTEL";
00419 mIsIntel = TRUE;
00420 }
00421 else
00422 {
00423 mGLVendorShort = "MISC";
00424 }
00425
00426
00427 initExtensions();
00428
00429 if (mHasMultitexture)
00430 {
00431 GLint num_tex_units;
00432 glGetIntegerv(GL_MAX_TEXTURE_UNITS_ARB, &num_tex_units);
00433 mNumTextureUnits = llmin(num_tex_units, (GLint)MAX_GL_TEXTURE_UNITS);
00434 if (mIsIntel)
00435 {
00436 mNumTextureUnits = llmin(mNumTextureUnits, 2);
00437 }
00438 }
00439 else
00440 {
00441 mHasRequirements = FALSE;
00442
00443
00444 LL_WARNS("RenderInit") << "GL Drivers do not support GL_ARB_multitexture" << LL_ENDL;
00445 return false;
00446 }
00447
00448
00449 initGLStates();
00450 return true;
00451 }
00452
00453 void LLGLManager::getGLInfo(LLSD& info)
00454 {
00455 info["GLInfo"]["GLVendor"] = LLString((const char *)glGetString(GL_VENDOR));
00456 info["GLInfo"]["GLRenderer"] = LLString((const char *)glGetString(GL_RENDERER));
00457 info["GLInfo"]["GLVersion"] = LLString((const char *)glGetString(GL_VERSION));
00458
00459 #if !LL_MESA_HEADLESS
00460 LLString all_exts = (const char *)gGLHExts.mSysExts;
00461 boost::char_separator<char> sep(" ");
00462 boost::tokenizer<boost::char_separator<char> > tok(all_exts, sep);
00463 for(boost::tokenizer<boost::char_separator<char> >::iterator i = tok.begin(); i != tok.end(); ++i)
00464 {
00465 info["GLInfo"]["GLExtensions"].append(*i);
00466 }
00467 #endif
00468 }
00469
00470 LLString LLGLManager::getGLInfoString()
00471 {
00472 LLString info_str;
00473 LLString all_exts, line;
00474
00475 info_str += LLString("GL_VENDOR ") + LLString((const char *)glGetString(GL_VENDOR)) + LLString("\n");
00476 info_str += LLString("GL_RENDERER ") + LLString((const char *)glGetString(GL_RENDERER)) + LLString("\n");
00477 info_str += LLString("GL_VERSION ") + LLString((const char *)glGetString(GL_VERSION)) + LLString("\n");
00478
00479 #if !LL_MESA_HEADLESS
00480 all_exts = (const char *)gGLHExts.mSysExts;
00481 LLString::replaceChar(all_exts, ' ', '\n');
00482 info_str += LLString("GL_EXTENSIONS:\n") + all_exts + LLString("\n");
00483 #endif
00484
00485 return info_str;
00486 }
00487
00488 void LLGLManager::printGLInfoString()
00489 {
00490 LLString info_str;
00491 LLString all_exts, line;
00492
00493 LL_INFOS("RenderInit") << "GL_VENDOR: " << ((const char *)glGetString(GL_VENDOR)) << LL_ENDL;
00494 LL_INFOS("RenderInit") << "GL_RENDERER: " << ((const char *)glGetString(GL_RENDERER)) << LL_ENDL;
00495 LL_INFOS("RenderInit") << "GL_VERSION: " << ((const char *)glGetString(GL_VERSION)) << LL_ENDL;
00496
00497 #if !LL_MESA_HEADLESS
00498 all_exts = (const char *)gGLHExts.mSysExts;
00499 LLString::replaceChar(all_exts, ' ', '\n');
00500 LL_DEBUGS("RenderInit") << "GL_EXTENSIONS:\n" << all_exts << LL_ENDL;
00501 #endif
00502 }
00503
00504 LLString LLGLManager::getRawGLString()
00505 {
00506 LLString gl_string;
00507 gl_string.assign((char*)glGetString(GL_VENDOR));
00508 gl_string.append(" ");
00509 gl_string.append((char*)glGetString(GL_RENDERER));
00510 return gl_string;
00511 }
00512
00513 void LLGLManager::shutdownGL()
00514 {
00515 if (mInited)
00516 {
00517 glFinish();
00518 stop_glerror();
00519 mInited = FALSE;
00520 }
00521 }
00522
00523
00524
00525
00526 extern LLCPUInfo gSysCPU;
00527
00528 void LLGLManager::initExtensions()
00529 {
00530 #if LL_MESA_HEADLESS
00531 # if GL_ARB_multitexture
00532 mHasMultitexture = TRUE;
00533 # else
00534 mHasMultitexture = FALSE;
00535 # endif
00536 # if GL_ARB_texture_env_combine
00537 mHasARBEnvCombine = TRUE;
00538 # else
00539 mHasARBEnvCombine = FALSE;
00540 # endif
00541 # if GL_ARB_texture_compression
00542 mHasCompressedTextures = TRUE;
00543 # else
00544 mHasCompressedTextures = FALSE;
00545 # endif
00546 # if GL_ARB_vertex_buffer_object
00547 mHasVertexBufferObject = TRUE;
00548 # else
00549 mHasVertexBufferObject = FALSE;
00550 # endif
00551 # if GL_EXT_framebuffer_object
00552 mHasFramebufferObject = TRUE;
00553 # else
00554 mHasFramebufferObject = FALSE;
00555 # endif
00556 mHasMipMapGeneration = FALSE;
00557 mHasPalettedTextures = FALSE;
00558 mHasSeparateSpecularColor = FALSE;
00559 mHasAnisotropic = FALSE;
00560 mHasCubeMap = FALSE;
00561 mHasOcclusionQuery = FALSE;
00562 mHasPointParameters = FALSE;
00563 mHasShaderObjects = FALSE;
00564 mHasVertexShader = FALSE;
00565 mHasFragmentShader = FALSE;
00566 #else // LL_MESA_HEADLESS
00567 mHasMultitexture = glh_init_extensions("GL_ARB_multitexture");
00568 mHasMipMapGeneration = glh_init_extensions("GL_SGIS_generate_mipmap");
00569 mHasPalettedTextures = glh_init_extension("GL_EXT_paletted_texture");
00570 mHasSeparateSpecularColor = glh_init_extensions("GL_EXT_separate_specular_color");
00571 mHasAnisotropic = glh_init_extensions("GL_EXT_texture_filter_anisotropic");
00572 glh_init_extensions("GL_ARB_texture_cube_map");
00573 mHasCubeMap = ExtensionExists("GL_ARB_texture_cube_map", gGLHExts.mSysExts);
00574 mHasARBEnvCombine = ExtensionExists("GL_ARB_texture_env_combine", gGLHExts.mSysExts);
00575 mHasCompressedTextures = glh_init_extensions("GL_ARB_texture_compression");
00576 mHasOcclusionQuery = ExtensionExists("GL_ARB_occlusion_query", gGLHExts.mSysExts);
00577 mHasVertexBufferObject = ExtensionExists("GL_ARB_vertex_buffer_object", gGLHExts.mSysExts);
00578
00579 mHasFramebufferObject = ExtensionExists("GL_EXT_framebuffer_object", gGLHExts.mSysExts)
00580 && ExtensionExists("GL_EXT_packed_depth_stencil", gGLHExts.mSysExts);
00581 #if !LL_DARWIN
00582 mHasPointParameters = !mIsATI && ExtensionExists("GL_ARB_point_parameters", gGLHExts.mSysExts);
00583 #endif
00584 mHasShaderObjects = ExtensionExists("GL_ARB_shader_objects", gGLHExts.mSysExts) && ExtensionExists("GL_ARB_shading_language_100", gGLHExts.mSysExts);
00585 mHasVertexShader = ExtensionExists("GL_ARB_vertex_program", gGLHExts.mSysExts) && ExtensionExists("GL_ARB_vertex_shader", gGLHExts.mSysExts)
00586 && ExtensionExists("GL_ARB_shading_language_100", gGLHExts.mSysExts);
00587 mHasFragmentShader = ExtensionExists("GL_ARB_fragment_shader", gGLHExts.mSysExts) && ExtensionExists("GL_ARB_shading_language_100", gGLHExts.mSysExts);
00588 #endif
00589
00590 #if LL_LINUX
00591
00592
00593 if (getenv("LL_GL_NOEXT"))
00594 {
00595
00596 mHasARBEnvCombine = FALSE;
00597 mHasCompressedTextures = FALSE;
00598 mHasVertexBufferObject = FALSE;
00599 mHasFramebufferObject = FALSE;
00600 mHasMipMapGeneration = FALSE;
00601 mHasPalettedTextures = FALSE;
00602 mHasSeparateSpecularColor = FALSE;
00603 mHasAnisotropic = FALSE;
00604 mHasCubeMap = FALSE;
00605 mHasOcclusionQuery = FALSE;
00606 mHasPointParameters = FALSE;
00607 mHasShaderObjects = FALSE;
00608 mHasVertexShader = FALSE;
00609 mHasFragmentShader = FALSE;
00610 LL_WARNS("RenderInit") << "GL extension support DISABLED via LL_GL_NOEXT" << LL_ENDL;
00611 }
00612 else if (getenv("LL_GL_BASICEXT"))
00613 {
00614
00615
00616
00617
00618 mHasMipMapGeneration = FALSE;
00619 mHasPalettedTextures = FALSE;
00620 mHasAnisotropic = FALSE;
00621
00622
00623 mHasShaderObjects = FALSE;
00624 mHasVertexShader = FALSE;
00625 mHasFragmentShader = FALSE;
00626 LL_WARNS("RenderInit") << "GL extension support forced to SIMPLE level via LL_GL_BASICEXT" << LL_ENDL;
00627 }
00628 if (getenv("LL_GL_BLACKLIST"))
00629 {
00630
00631
00632
00633 const char *const blacklist = getenv("LL_GL_BLACKLIST");
00634 LL_WARNS("RenderInit") << "GL extension support partially disabled via LL_GL_BLACKLIST: " << blacklist << LL_ENDL;
00635 if (strchr(blacklist,'a')) mHasARBEnvCombine = FALSE;
00636 if (strchr(blacklist,'b')) mHasCompressedTextures = FALSE;
00637 if (strchr(blacklist,'c')) mHasVertexBufferObject = FALSE;
00638 if (strchr(blacklist,'d')) mHasMipMapGeneration = FALSE;
00639 if (strchr(blacklist,'e')) mHasPalettedTextures = FALSE;
00640
00641
00642 if (strchr(blacklist,'h')) mHasSeparateSpecularColor = FALSE;
00643 if (strchr(blacklist,'i')) mHasAnisotropic = FALSE;
00644 if (strchr(blacklist,'j')) mHasCubeMap = FALSE;
00645
00646 if (strchr(blacklist,'l')) mHasOcclusionQuery = FALSE;
00647 if (strchr(blacklist,'m')) mHasShaderObjects = FALSE;
00648 if (strchr(blacklist,'n')) mHasVertexShader = FALSE;
00649 if (strchr(blacklist,'o')) mHasFragmentShader = FALSE;
00650 if (strchr(blacklist,'p')) mHasPointParameters = FALSE;
00651 if (strchr(blacklist,'q')) mHasFramebufferObject = FALSE;
00652 }
00653 #endif // LL_LINUX
00654
00655 #if LL_DARWIN || LL_LINUX
00656
00657
00658
00659 mHasPalettedTextures = false;
00660 #endif
00661
00662 if (!mHasMultitexture)
00663 {
00664 LL_INFOS("RenderInit") << "Couldn't initialize multitexturing" << LL_ENDL;
00665 }
00666 if (!mHasMipMapGeneration)
00667 {
00668 LL_INFOS("RenderInit") << "Couldn't initialize mipmap generation" << LL_ENDL;
00669 }
00670 if (!mHasARBEnvCombine)
00671 {
00672 LL_INFOS("RenderInit") << "Couldn't initialize GL_ARB_texture_env_combine" << LL_ENDL;
00673 }
00674 if (!mHasPalettedTextures)
00675 {
00676 LL_INFOS("RenderInit") << "Couldn't initialize GL_EXT_paletted_texture" << LL_ENDL;
00677 }
00678 if (!mHasSeparateSpecularColor)
00679 {
00680 LL_INFOS("RenderInit") << "Couldn't initialize separate specular color" << LL_ENDL;
00681 }
00682 if (!mHasAnisotropic)
00683 {
00684 LL_INFOS("RenderInit") << "Couldn't initialize anisotropic filtering" << LL_ENDL;
00685 }
00686 if (!mHasCompressedTextures)
00687 {
00688 LL_INFOS("RenderInit") << "Couldn't initialize GL_ARB_texture_compression" << LL_ENDL;
00689 }
00690 if (!mHasOcclusionQuery)
00691 {
00692 LL_INFOS("RenderInit") << "Couldn't initialize GL_ARB_occlusion_query" << LL_ENDL;
00693 }
00694 if (!mHasPointParameters)
00695 {
00696 LL_INFOS("RenderInit") << "Couldn't initialize GL_ARB_point_parameters" << LL_ENDL;
00697 }
00698 if (!mHasShaderObjects)
00699 {
00700 LL_INFOS("RenderInit") << "Couldn't initialize GL_ARB_shader_objects" << LL_ENDL;
00701 }
00702 if (!mHasVertexShader)
00703 {
00704 LL_INFOS("RenderInit") << "Couldn't initialize GL_ARB_vertex_shader" << LL_ENDL;
00705 }
00706 if (!mHasFragmentShader)
00707 {
00708 LL_INFOS("RenderInit") << "Couldn't initialize GL_ARB_fragment_shader" << LL_ENDL;
00709 }
00710
00711
00712 if (mIsIntel && mHasMipMapGeneration)
00713 {
00714 LL_INFOS("RenderInit") << "Disabling mip-map generation for Intel GPUs" << LL_ENDL;
00715 mHasMipMapGeneration = FALSE;
00716 }
00717 if (mIsATI && mHasMipMapGeneration)
00718 {
00719 LL_INFOS("RenderInit") << "Disabling mip-map generation for ATI GPUs (performance opt)" << LL_ENDL;
00720 mHasMipMapGeneration = FALSE;
00721 }
00722
00723
00724 glGetIntegerv(GL_MAX_ELEMENTS_VERTICES, (GLint*) &mGLMaxVertexRange);
00725 glGetIntegerv(GL_MAX_ELEMENTS_INDICES, (GLint*) &mGLMaxIndexRange);
00726
00727 #if (LL_WINDOWS || LL_LINUX) && !LL_MESA_HEADLESS
00728 LL_DEBUGS("RenderInit") << "GL Probe: Getting symbols" << LL_ENDL;
00729 if (mHasVertexBufferObject)
00730 {
00731 glBindBufferARB = (PFNGLBINDBUFFERARBPROC)GLH_EXT_GET_PROC_ADDRESS("glBindBufferARB");
00732 if (glBindBufferARB)
00733 {
00734 glDeleteBuffersARB = (PFNGLDELETEBUFFERSARBPROC)GLH_EXT_GET_PROC_ADDRESS("glDeleteBuffersARB");
00735 glGenBuffersARB = (PFNGLGENBUFFERSARBPROC)GLH_EXT_GET_PROC_ADDRESS("glGenBuffersARB");
00736 glIsBufferARB = (PFNGLISBUFFERARBPROC)GLH_EXT_GET_PROC_ADDRESS("glIsBufferARB");
00737 glBufferDataARB = (PFNGLBUFFERDATAARBPROC)GLH_EXT_GET_PROC_ADDRESS("glBufferDataARB");
00738 glBufferSubDataARB = (PFNGLBUFFERSUBDATAARBPROC)GLH_EXT_GET_PROC_ADDRESS("glBufferSubDataARB");
00739 glGetBufferSubDataARB = (PFNGLGETBUFFERSUBDATAARBPROC)GLH_EXT_GET_PROC_ADDRESS("glGetBufferSubDataARB");
00740 glMapBufferARB = (PFNGLMAPBUFFERARBPROC)GLH_EXT_GET_PROC_ADDRESS("glMapBufferARB");
00741 glUnmapBufferARB = (PFNGLUNMAPBUFFERARBPROC)GLH_EXT_GET_PROC_ADDRESS("glUnmapBufferARB");
00742 glGetBufferParameterivARB = (PFNGLGETBUFFERPARAMETERIVARBPROC)GLH_EXT_GET_PROC_ADDRESS("glGetBufferParameterivARB");
00743 glGetBufferPointervARB = (PFNGLGETBUFFERPOINTERVARBPROC)GLH_EXT_GET_PROC_ADDRESS("glGetBufferPointervARB");
00744 }
00745 else
00746 {
00747 mHasVertexBufferObject = FALSE;
00748 }
00749 }
00750 if (mHasFramebufferObject)
00751 {
00752 glIsRenderbufferEXT = (PFNGLISRENDERBUFFEREXTPROC) GLH_EXT_GET_PROC_ADDRESS("glIsRenderbufferEXT");
00753 glBindRenderbufferEXT = (PFNGLBINDRENDERBUFFEREXTPROC) GLH_EXT_GET_PROC_ADDRESS("glBindRenderbufferEXT");
00754 glDeleteRenderbuffersEXT = (PFNGLDELETERENDERBUFFERSEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glDeleteRenderbuffersEXT");
00755 glGenRenderbuffersEXT = (PFNGLGENRENDERBUFFERSEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glGenRenderbuffersEXT");
00756 glRenderbufferStorageEXT = (PFNGLRENDERBUFFERSTORAGEEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glRenderbufferStorageEXT");
00757 glGetRenderbufferParameterivEXT = (PFNGLGETRENDERBUFFERPARAMETERIVEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glGetRenderbufferParameterivEXT");
00758 glIsFramebufferEXT = (PFNGLISFRAMEBUFFEREXTPROC) GLH_EXT_GET_PROC_ADDRESS("glIsFramebufferEXT");
00759 glBindFramebufferEXT = (PFNGLBINDFRAMEBUFFEREXTPROC) GLH_EXT_GET_PROC_ADDRESS("glBindFramebufferEXT");
00760 glDeleteFramebuffersEXT = (PFNGLDELETEFRAMEBUFFERSEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glDeleteFramebuffersEXT");
00761 glGenFramebuffersEXT = (PFNGLGENFRAMEBUFFERSEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glGenFramebuffersEXT");
00762 glCheckFramebufferStatusEXT = (PFNGLCHECKFRAMEBUFFERSTATUSEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glCheckFramebufferStatusEXT");
00763 glFramebufferTexture1DEXT = (PFNGLFRAMEBUFFERTEXTURE1DEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glFramebufferTexture1DEXT");
00764 glFramebufferTexture2DEXT = (PFNGLFRAMEBUFFERTEXTURE2DEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glFramebufferTexture2DEXT");
00765 glFramebufferTexture3DEXT = (PFNGLFRAMEBUFFERTEXTURE3DEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glFramebufferTexture3DEXT");
00766 glFramebufferRenderbufferEXT = (PFNGLFRAMEBUFFERRENDERBUFFEREXTPROC) GLH_EXT_GET_PROC_ADDRESS("glFramebufferRenderbufferEXT");
00767 glGetFramebufferAttachmentParameterivEXT = (PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glGetFramebufferAttachmentParameterivEXT");
00768 glGenerateMipmapEXT = (PFNGLGENERATEMIPMAPEXTPROC) GLH_EXT_GET_PROC_ADDRESS("glGenerateMipmapEXT");
00769 }
00770 #if !LL_LINUX
00771
00772 glDrawRangeElements = (PFNGLDRAWRANGEELEMENTSPROC)GLH_EXT_GET_PROC_ADDRESS("glDrawRangeElements");
00773 if (!glDrawRangeElements)
00774 {
00775 mGLMaxVertexRange = 0;
00776 mGLMaxIndexRange = 0;
00777 }
00778 #endif // !LL_LINUX
00779 #if LL_LINUX
00780
00781 if (mHasPalettedTextures)
00782 {
00783 glColorTableEXT = (PFNGLCOLORTABLEEXTPROC)GLH_EXT_GET_PROC_ADDRESS("glColorTableEXT");
00784 }
00785 #endif // LL_LINUX
00786 if (mHasOcclusionQuery)
00787 {
00788 glGenQueriesARB = (PFNGLGENQUERIESARBPROC)GLH_EXT_GET_PROC_ADDRESS("glGenQueriesARB");
00789 glDeleteQueriesARB = (PFNGLDELETEQUERIESARBPROC)GLH_EXT_GET_PROC_ADDRESS("glDeleteQueriesARB");
00790 glIsQueryARB = (PFNGLISQUERYARBPROC)GLH_EXT_GET_PROC_ADDRESS("glIsQueryARB");
00791 glBeginQueryARB = (PFNGLBEGINQUERYARBPROC)GLH_EXT_GET_PROC_ADDRESS("glBeginQueryARB");
00792 glEndQueryARB = (PFNGLENDQUERYARBPROC)GLH_EXT_GET_PROC_ADDRESS("glEndQueryARB");
00793 glGetQueryivARB = (PFNGLGETQUERYIVARBPROC)GLH_EXT_GET_PROC_ADDRESS("glGetQueryivARB");
00794 glGetQueryObjectivARB = (PFNGLGETQUERYOBJECTIVARBPROC)GLH_EXT_GET_PROC_ADDRESS("glGetQueryObjectivARB");
00795 glGetQueryObjectuivARB = (PFNGLGETQUERYOBJECTUIVARBPROC)GLH_EXT_GET_PROC_ADDRESS("glGetQueryObjectuivARB");
00796 }
00797 if (mHasPointParameters)
00798 {
00799 glPointParameterfARB = (PFNGLPOINTPARAMETERFARBPROC)GLH_EXT_GET_PROC_ADDRESS("glPointParameterfARB");
00800 glPointParameterfvARB = (PFNGLPOINTPARAMETERFVARBPROC)GLH_EXT_GET_PROC_ADDRESS("glPointParameterfvARB");
00801 }
00802 if (mHasShaderObjects)
00803 {
00804 glDeleteObjectARB = (PFNGLDELETEOBJECTARBPROC) GLH_EXT_GET_PROC_ADDRESS("glDeleteObjectARB");
00805 glGetHandleARB = (PFNGLGETHANDLEARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetHandleARB");
00806 glDetachObjectARB = (PFNGLDETACHOBJECTARBPROC) GLH_EXT_GET_PROC_ADDRESS("glDetachObjectARB");
00807 glCreateShaderObjectARB = (PFNGLCREATESHADEROBJECTARBPROC) GLH_EXT_GET_PROC_ADDRESS("glCreateShaderObjectARB");
00808 glShaderSourceARB = (PFNGLSHADERSOURCEARBPROC) GLH_EXT_GET_PROC_ADDRESS("glShaderSourceARB");
00809 glCompileShaderARB = (PFNGLCOMPILESHADERARBPROC) GLH_EXT_GET_PROC_ADDRESS("glCompileShaderARB");
00810 glCreateProgramObjectARB = (PFNGLCREATEPROGRAMOBJECTARBPROC) GLH_EXT_GET_PROC_ADDRESS("glCreateProgramObjectARB");
00811 glAttachObjectARB = (PFNGLATTACHOBJECTARBPROC) GLH_EXT_GET_PROC_ADDRESS("glAttachObjectARB");
00812 glLinkProgramARB = (PFNGLLINKPROGRAMARBPROC) GLH_EXT_GET_PROC_ADDRESS("glLinkProgramARB");
00813 glUseProgramObjectARB = (PFNGLUSEPROGRAMOBJECTARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUseProgramObjectARB");
00814 glValidateProgramARB = (PFNGLVALIDATEPROGRAMARBPROC) GLH_EXT_GET_PROC_ADDRESS("glValidateProgramARB");
00815 glUniform1fARB = (PFNGLUNIFORM1FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform1fARB");
00816 glUniform2fARB = (PFNGLUNIFORM2FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform2fARB");
00817 glUniform3fARB = (PFNGLUNIFORM3FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform3fARB");
00818 glUniform4fARB = (PFNGLUNIFORM4FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform4fARB");
00819 glUniform1iARB = (PFNGLUNIFORM1IARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform1iARB");
00820 glUniform2iARB = (PFNGLUNIFORM2IARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform2iARB");
00821 glUniform3iARB = (PFNGLUNIFORM3IARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform3iARB");
00822 glUniform4iARB = (PFNGLUNIFORM4IARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform4iARB");
00823 glUniform1fvARB = (PFNGLUNIFORM1FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform1fvARB");
00824 glUniform2fvARB = (PFNGLUNIFORM2FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform2fvARB");
00825 glUniform3fvARB = (PFNGLUNIFORM3FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform3fvARB");
00826 glUniform4fvARB = (PFNGLUNIFORM4FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform4fvARB");
00827 glUniform1ivARB = (PFNGLUNIFORM1IVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform1ivARB");
00828 glUniform2ivARB = (PFNGLUNIFORM2IVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform2ivARB");
00829 glUniform3ivARB = (PFNGLUNIFORM3IVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform3ivARB");
00830 glUniform4ivARB = (PFNGLUNIFORM4IVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniform4ivARB");
00831 glUniformMatrix2fvARB = (PFNGLUNIFORMMATRIX2FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniformMatrix2fvARB");
00832 glUniformMatrix3fvARB = (PFNGLUNIFORMMATRIX3FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniformMatrix3fvARB");
00833 glUniformMatrix4fvARB = (PFNGLUNIFORMMATRIX4FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glUniformMatrix4fvARB");
00834 glGetObjectParameterfvARB = (PFNGLGETOBJECTPARAMETERFVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetObjectParameterfvARB");
00835 glGetObjectParameterivARB = (PFNGLGETOBJECTPARAMETERIVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetObjectParameterivARB");
00836 glGetInfoLogARB = (PFNGLGETINFOLOGARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetInfoLogARB");
00837 glGetAttachedObjectsARB = (PFNGLGETATTACHEDOBJECTSARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetAttachedObjectsARB");
00838 glGetUniformLocationARB = (PFNGLGETUNIFORMLOCATIONARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetUniformLocationARB");
00839 glGetActiveUniformARB = (PFNGLGETACTIVEUNIFORMARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetActiveUniformARB");
00840 glGetUniformfvARB = (PFNGLGETUNIFORMFVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetUniformfvARB");
00841 glGetUniformivARB = (PFNGLGETUNIFORMIVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetUniformivARB");
00842 glGetShaderSourceARB = (PFNGLGETSHADERSOURCEARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetShaderSourceARB");
00843 }
00844 if (mHasVertexShader)
00845 {
00846 glGetAttribLocationARB = (PFNGLGETATTRIBLOCATIONARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetAttribLocationARB");
00847 glBindAttribLocationARB = (PFNGLBINDATTRIBLOCATIONARBPROC) GLH_EXT_GET_PROC_ADDRESS("glBindAttribLocationARB");
00848 glGetActiveAttribARB = (PFNGLGETACTIVEATTRIBARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetActiveAttribARB");
00849 glVertexAttrib1dARB = (PFNGLVERTEXATTRIB1DARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib1dARB");
00850 glVertexAttrib1dvARB = (PFNGLVERTEXATTRIB1DVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib1dvARB");
00851 glVertexAttrib1fARB = (PFNGLVERTEXATTRIB1FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib1fARB");
00852 glVertexAttrib1fvARB = (PFNGLVERTEXATTRIB1FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib1fvARB");
00853 glVertexAttrib1sARB = (PFNGLVERTEXATTRIB1SARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib1sARB");
00854 glVertexAttrib1svARB = (PFNGLVERTEXATTRIB1SVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib1svARB");
00855 glVertexAttrib2dARB = (PFNGLVERTEXATTRIB2DARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib2dARB");
00856 glVertexAttrib2dvARB = (PFNGLVERTEXATTRIB2DVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib2dvARB");
00857 glVertexAttrib2fARB = (PFNGLVERTEXATTRIB2FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib2fARB");
00858 glVertexAttrib2fvARB = (PFNGLVERTEXATTRIB2FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib2fvARB");
00859 glVertexAttrib2sARB = (PFNGLVERTEXATTRIB2SARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib2sARB");
00860 glVertexAttrib2svARB = (PFNGLVERTEXATTRIB2SVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib2svARB");
00861 glVertexAttrib3dARB = (PFNGLVERTEXATTRIB3DARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib3dARB");
00862 glVertexAttrib3dvARB = (PFNGLVERTEXATTRIB3DVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib3dvARB");
00863 glVertexAttrib3fARB = (PFNGLVERTEXATTRIB3FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib3fARB");
00864 glVertexAttrib3fvARB = (PFNGLVERTEXATTRIB3FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib3fvARB");
00865 glVertexAttrib3sARB = (PFNGLVERTEXATTRIB3SARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib3sARB");
00866 glVertexAttrib3svARB = (PFNGLVERTEXATTRIB3SVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib3svARB");
00867 glVertexAttrib4nbvARB = (PFNGLVERTEXATTRIB4NBVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4nbvARB");
00868 glVertexAttrib4nivARB = (PFNGLVERTEXATTRIB4NIVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4nivARB");
00869 glVertexAttrib4nsvARB = (PFNGLVERTEXATTRIB4NSVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4nsvARB");
00870 glVertexAttrib4nubARB = (PFNGLVERTEXATTRIB4NUBARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4nubARB");
00871 glVertexAttrib4nubvARB = (PFNGLVERTEXATTRIB4NUBVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4nubvARB");
00872 glVertexAttrib4nuivARB = (PFNGLVERTEXATTRIB4NUIVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4nuivARB");
00873 glVertexAttrib4nusvARB = (PFNGLVERTEXATTRIB4NUSVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4nusvARB");
00874 glVertexAttrib4bvARB = (PFNGLVERTEXATTRIB4BVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4bvARB");
00875 glVertexAttrib4dARB = (PFNGLVERTEXATTRIB4DARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4dARB");
00876 glVertexAttrib4dvARB = (PFNGLVERTEXATTRIB4DVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4dvARB");
00877 glVertexAttrib4fARB = (PFNGLVERTEXATTRIB4FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4fARB");
00878 glVertexAttrib4fvARB = (PFNGLVERTEXATTRIB4FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4fvARB");
00879 glVertexAttrib4ivARB = (PFNGLVERTEXATTRIB4IVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4ivARB");
00880 glVertexAttrib4sARB = (PFNGLVERTEXATTRIB4SARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4sARB");
00881 glVertexAttrib4svARB = (PFNGLVERTEXATTRIB4SVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4svARB");
00882 glVertexAttrib4ubvARB = (PFNGLVERTEXATTRIB4UBVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4ubvARB");
00883 glVertexAttrib4uivARB = (PFNGLVERTEXATTRIB4UIVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4uivARB");
00884 glVertexAttrib4usvARB = (PFNGLVERTEXATTRIB4USVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttrib4usvARB");
00885 glVertexAttribPointerARB = (PFNGLVERTEXATTRIBPOINTERARBPROC) GLH_EXT_GET_PROC_ADDRESS("glVertexAttribPointerARB");
00886 glEnableVertexAttribArrayARB = (PFNGLENABLEVERTEXATTRIBARRAYARBPROC) GLH_EXT_GET_PROC_ADDRESS("glEnableVertexAttribArrayARB");
00887 glDisableVertexAttribArrayARB = (PFNGLDISABLEVERTEXATTRIBARRAYARBPROC) GLH_EXT_GET_PROC_ADDRESS("glDisableVertexAttribArrayARB");
00888 glProgramStringARB = (PFNGLPROGRAMSTRINGARBPROC) GLH_EXT_GET_PROC_ADDRESS("glProgramStringARB");
00889 glBindProgramARB = (PFNGLBINDPROGRAMARBPROC) GLH_EXT_GET_PROC_ADDRESS("glBindProgramARB");
00890 glDeleteProgramsARB = (PFNGLDELETEPROGRAMSARBPROC) GLH_EXT_GET_PROC_ADDRESS("glDeleteProgramsARB");
00891 glGenProgramsARB = (PFNGLGENPROGRAMSARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGenProgramsARB");
00892 glProgramEnvParameter4dARB = (PFNGLPROGRAMENVPARAMETER4DARBPROC) GLH_EXT_GET_PROC_ADDRESS("glProgramEnvParameter4dARB");
00893 glProgramEnvParameter4dvARB = (PFNGLPROGRAMENVPARAMETER4DVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glProgramEnvParameter4dvARB");
00894 glProgramEnvParameter4fARB = (PFNGLPROGRAMENVPARAMETER4FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glProgramEnvParameter4fARB");
00895 glProgramEnvParameter4fvARB = (PFNGLPROGRAMENVPARAMETER4FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glProgramEnvParameter4fvARB");
00896 glProgramLocalParameter4dARB = (PFNGLPROGRAMLOCALPARAMETER4DARBPROC) GLH_EXT_GET_PROC_ADDRESS("glProgramLocalParameter4dARB");
00897 glProgramLocalParameter4dvARB = (PFNGLPROGRAMLOCALPARAMETER4DVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glProgramLocalParameter4dvARB");
00898 glProgramLocalParameter4fARB = (PFNGLPROGRAMLOCALPARAMETER4FARBPROC) GLH_EXT_GET_PROC_ADDRESS("glProgramLocalParameter4fARB");
00899 glProgramLocalParameter4fvARB = (PFNGLPROGRAMLOCALPARAMETER4FVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glProgramLocalParameter4fvARB");
00900 glGetProgramEnvParameterdvARB = (PFNGLGETPROGRAMENVPARAMETERDVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetProgramEnvParameterdvARB");
00901 glGetProgramEnvParameterfvARB = (PFNGLGETPROGRAMENVPARAMETERFVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetProgramEnvParameterfvARB");
00902 glGetProgramLocalParameterdvARB = (PFNGLGETPROGRAMLOCALPARAMETERDVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetProgramLocalParameterdvARB");
00903 glGetProgramLocalParameterfvARB = (PFNGLGETPROGRAMLOCALPARAMETERFVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetProgramLocalParameterfvARB");
00904 glGetProgramivARB = (PFNGLGETPROGRAMIVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetProgramivARB");
00905 glGetProgramStringARB = (PFNGLGETPROGRAMSTRINGARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetProgramStringARB");
00906 glGetVertexAttribdvARB = (PFNGLGETVERTEXATTRIBDVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetVertexAttribdvARB");
00907 glGetVertexAttribfvARB = (PFNGLGETVERTEXATTRIBFVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetVertexAttribfvARB");
00908 glGetVertexAttribivARB = (PFNGLGETVERTEXATTRIBIVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glGetVertexAttribivARB");
00909 glGetVertexAttribPointervARB = (PFNGLGETVERTEXATTRIBPOINTERVARBPROC) GLH_EXT_GET_PROC_ADDRESS("glgetVertexAttribPointervARB");
00910 glIsProgramARB = (PFNGLISPROGRAMARBPROC) GLH_EXT_GET_PROC_ADDRESS("glIsProgramARB");
00911 }
00912 LL_DEBUGS("RenderInit") << "GL Probe: Got symbols" << LL_ENDL;
00913 #endif
00914
00915 mInited = TRUE;
00916 }
00917
00918 void rotate_quat(LLQuaternion& rotation)
00919 {
00920 F32 angle_radians, x, y, z;
00921 rotation.getAngleAxis(&angle_radians, &x, &y, &z);
00922 glRotatef(angle_radians * RAD_TO_DEG, x, y, z);
00923 }
00924
00925 void flush_glerror()
00926 {
00927 glGetError();
00928 }
00929
00930 void assert_glerror()
00931 {
00932 if (gNoRender || !gDebugGL)
00933 {
00934 return;
00935 }
00936 if (!gGLManager.mInited)
00937 {
00938 LL_ERRS("RenderInit") << "GL not initialized" << LL_ENDL;
00939 }
00940
00941 GLenum error;
00942 error = glGetError();
00943 if (error)
00944 {
00945 #ifndef LL_LINUX // *FIX: ! This should be an error for linux as well.
00946 GLubyte const * gl_error_msg = gluErrorString(error);
00947 if (NULL != gl_error_msg)
00948 {
00949 LL_ERRS("RenderState") << "GL Error:" << gl_error_msg << LL_ENDL;
00950 }
00951 else
00952 {
00953
00954
00955 LL_ERRS("RenderState") << "GL Error: UNKNOWN 0x" << std::hex << error << LL_ENDL;
00956 }
00957 #endif
00958 }
00959 }
00960
00961 void clear_glerror()
00962 {
00963
00964 GLenum error;
00965 error = glGetError();
00966 }
00967
00969
00970
00971
00972
00973
00974 std::map<LLGLenum, LLGLboolean> LLGLState::sStateMap;
00975
00976 GLboolean LLGLDepthTest::sDepthEnabled = GL_FALSE;
00977 GLenum LLGLDepthTest::sDepthFunc = GL_LESS;
00978 GLboolean LLGLDepthTest::sWriteEnabled = GL_TRUE;
00979
00980
00981 void LLGLState::initClass()
00982 {
00983 sStateMap[GL_DITHER] = GL_TRUE;
00984 sStateMap[GL_TEXTURE_2D] = GL_TRUE;
00985 }
00986
00987
00988 void LLGLState::restoreGL()
00989 {
00990 sStateMap.clear();
00991 initClass();
00992 }
00993
00994
00995
00996 void LLGLState::resetTextureStates()
00997 {
00998 gGL.flush();
00999 GLint maxTextureUnits;
01000
01001 glGetIntegerv(GL_MAX_TEXTURE_UNITS_ARB, &maxTextureUnits);
01002 for (S32 j = maxTextureUnits-1; j >=0; j--)
01003 {
01004 glActiveTextureARB(GL_TEXTURE0_ARB+j);
01005 glClientActiveTextureARB(GL_TEXTURE0_ARB+j);
01006 j == 0 ? glEnable(GL_TEXTURE_2D) : glDisable(GL_TEXTURE_2D);
01007 }
01008 }
01009
01010 void LLGLState::dumpStates()
01011 {
01012 LL_INFOS("RenderState") << "GL States:" << LL_ENDL;
01013 for (std::map<LLGLenum, LLGLboolean>::iterator iter = sStateMap.begin();
01014 iter != sStateMap.end(); ++iter)
01015 {
01016 LL_INFOS("RenderState") << llformat(" 0x%04x : %s",(S32)iter->first,iter->second?"TRUE":"FALSE") << LL_ENDL;
01017 }
01018 }
01019
01020 void LLGLState::checkStates()
01021 {
01022 if (!gDebugGL)
01023 {
01024 return;
01025 }
01026
01027 stop_glerror();
01028
01029 GLint activeTexture;
01030 glGetIntegerv(GL_ACTIVE_TEXTURE_ARB, &activeTexture);
01031
01032 if (activeTexture != GL_TEXTURE0_ARB)
01033 {
01034 LL_GL_ERRS << "Texture channel corrupted. " << LL_ENDL;
01035 }
01036
01037 GLint src;
01038 GLint dst;
01039 glGetIntegerv(GL_BLEND_SRC, &src);
01040 glGetIntegerv(GL_BLEND_DST, &dst);
01041
01042 if (src != GL_SRC_ALPHA || dst != GL_ONE_MINUS_SRC_ALPHA)
01043 {
01044 LL_GL_ERRS << "Blend function corrupted: " << std::hex << src << " " << std::hex << dst << LL_ENDL;
01045 }
01046
01047 for (std::map<LLGLenum, LLGLboolean>::iterator iter = sStateMap.begin();
01048 iter != sStateMap.end(); ++iter)
01049 {
01050 LLGLenum state = iter->first;
01051 LLGLboolean cur_state = iter->second;
01052 LLGLboolean gl_state = glIsEnabled(state);
01053 if(cur_state != gl_state)
01054 {
01055 dumpStates();
01056 LL_GL_ERRS << llformat("LLGLState error. State: 0x%04x",state) << LL_ENDL;
01057 }
01058 }
01059
01060 stop_glerror();
01061 }
01062
01063 void LLGLState::checkTextureChannels()
01064 {
01065 if (!gDebugGL)
01066 {
01067 return;
01068 }
01069
01070 GLint activeTexture;
01071 glGetIntegerv(GL_ACTIVE_TEXTURE_ARB, &activeTexture);
01072
01073 BOOL error = FALSE;
01074
01075 if (activeTexture != GL_TEXTURE0_ARB)
01076 {
01077 error = TRUE;
01078 LL_WARNS("RenderState") << "Active texture channel corrupted. " << LL_ENDL;
01079 }
01080 else if (!glIsEnabled(GL_TEXTURE_2D))
01081 {
01082 error = TRUE;
01083 LL_WARNS("RenderState") << "GL_TEXTURE_2D not enabled on texture channel 0." << LL_ENDL;
01084 }
01085 else
01086 {
01087 GLint tex_env_mode = 0;
01088
01089 glGetTexEnviv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, &tex_env_mode);
01090 if (tex_env_mode != GL_MODULATE)
01091 {
01092 error = TRUE;
01093 LL_WARNS("RenderState") << "GL_TEXTURE_ENV_MODE invalid: " << std::hex << tex_env_mode << LL_ENDL;
01094 }
01095 }
01096
01097 GLint maxTextureUnits;
01098 glGetIntegerv(GL_MAX_TEXTURE_UNITS_ARB, &maxTextureUnits);
01099
01100 static const char* label[] =
01101 {
01102 "GL_TEXTURE_2D",
01103 "GL_TEXTURE_COORD_ARRAY",
01104 "GL_TEXTURE_1D",
01105 "GL_TEXTURE_CUBE_MAP_ARB",
01106 "GL_TEXTURE_GEN_S",
01107 "GL_TEXTURE_GEN_T",
01108 "GL_TEXTURE_GEN_Q",
01109 "GL_TEXTURE_GEN_R"
01110 };
01111
01112 static GLint value[] =
01113 {
01114 GL_TEXTURE_2D,
01115 GL_TEXTURE_COORD_ARRAY,
01116 GL_TEXTURE_1D,
01117 GL_TEXTURE_CUBE_MAP_ARB,
01118 GL_TEXTURE_GEN_S,
01119 GL_TEXTURE_GEN_T,
01120 GL_TEXTURE_GEN_Q,
01121 GL_TEXTURE_GEN_R
01122 };
01123
01124 GLint stackDepth = 0;
01125 LLMatrix4 identity;
01126 LLMatrix4 matrix;
01127
01128 for (GLint i = 0; i < maxTextureUnits; i++)
01129 {
01130 glActiveTextureARB(GL_TEXTURE0_ARB+i);
01131 glClientActiveTextureARB(GL_TEXTURE0_ARB+i);
01132
01133 glGetIntegerv(GL_TEXTURE_STACK_DEPTH, &stackDepth);
01134
01135 if (stackDepth != 1)
01136 {
01137 error = TRUE;
01138 LL_WARNS("RenderState") << "Texture matrix stack corrupted." << LL_ENDL;
01139 }
01140
01141 glGetFloatv(GL_TEXTURE_MATRIX, (GLfloat*) matrix.mMatrix);
01142
01143 if (matrix != identity)
01144 {
01145 error = TRUE;
01146 LL_WARNS("RenderState") << "Texture matrix in channel " << i << " corrupt." << LL_ENDL;
01147 }
01148
01149 for (S32 j = (i == 0 ? 1 : 0); j < 8; j++)
01150 {
01151 if (glIsEnabled(value[j]))
01152 {
01153 error = TRUE;
01154 LL_WARNS("RenderState") << "Texture channel " << i << " still has " << label[j] << " enabled." << LL_ENDL;
01155 }
01156 }
01157 }
01158
01159 glActiveTextureARB(GL_TEXTURE0_ARB);
01160 glClientActiveTextureARB(GL_TEXTURE0_ARB);
01161
01162 if (error)
01163 {
01164 LL_GL_ERRS << "GL texture state corruption detected." << LL_ENDL;
01165 }
01166 }
01167
01168 void LLGLState::checkClientArrays(U32 data_mask)
01169 {
01170 if (!gDebugGL)
01171 {
01172 return;
01173 }
01174
01175 stop_glerror();
01176 BOOL error = FALSE;
01177
01178 GLint active_texture;
01179 glGetIntegerv(GL_CLIENT_ACTIVE_TEXTURE_ARB, &active_texture);
01180
01181 if (active_texture != GL_TEXTURE0_ARB)
01182 {
01183 llwarns << "Client active texture corrupted: " << active_texture << llendl;
01184 error = TRUE;
01185 }
01186
01187 glGetIntegerv(GL_ACTIVE_TEXTURE_ARB, &active_texture);
01188 if (active_texture != GL_TEXTURE0_ARB)
01189 {
01190 llwarns << "Active texture corrupted: " << active_texture << llendl;
01191 error = TRUE;
01192 }
01193
01194 static const char* label[] =
01195 {
01196 "GL_VERTEX_ARRAY",
01197 "GL_NORMAL_ARRAY",
01198 "GL_COLOR_ARRAY",
01199 "GL_TEXTURE_COORD_ARRAY"
01200 };
01201
01202 static GLint value[] =
01203 {
01204 GL_VERTEX_ARRAY,
01205 GL_NORMAL_ARRAY,
01206 GL_COLOR_ARRAY,
01207 GL_TEXTURE_COORD_ARRAY
01208 };
01209
01210 U32 mask[] =
01211 {
01212 0x0001,
01213 0x0002,
01214 0x0010,
01215 0x0004,
01216 };
01217
01218
01219 for (S32 j = 0; j < 4; j++)
01220 {
01221 if (glIsEnabled(value[j]))
01222 {
01223 if (!(mask[j] & data_mask))
01224 {
01225 error = TRUE;
01226 LL_WARNS("RenderState") << "GL still has " << label[j] << " enabled." << LL_ENDL;
01227 }
01228 }
01229 else
01230 {
01231 if (mask[j] & data_mask)
01232 {
01233 error = TRUE;
01234 LL_WARNS("RenderState") << "GL does not have " << label[j] << " enabled." << LL_ENDL;
01235 }
01236 }
01237 }
01238
01239 glClientActiveTextureARB(GL_TEXTURE1_ARB);
01240 glActiveTextureARB(GL_TEXTURE1_ARB);
01241 if (glIsEnabled(GL_TEXTURE_COORD_ARRAY))
01242 {
01243 if (!(data_mask & 0x0008))
01244 {
01245 error = TRUE;
01246 LL_WARNS("RenderState") << "GL still has GL_TEXTURE_COORD_ARRAY enabled on channel 1." << LL_ENDL;
01247 }
01248 }
01249 else
01250 {
01251 if (data_mask & 0x0008)
01252 {
01253 error = TRUE;
01254 LL_WARNS("RenderState") << "GL does not have GL_TEXTURE_COORD_ARRAY enabled on channel 1." << LL_ENDL;
01255 }
01256 }
01257
01258 if (glIsEnabled(GL_TEXTURE_2D))
01259 {
01260 if (!(data_mask & 0x0008))
01261 {
01262 error = TRUE;
01263 LL_WARNS("RenderState") << "GL still has GL_TEXTURE_2D enabled on channel 1." << LL_ENDL;
01264 }
01265 }
01266 else
01267 {
01268 if (data_mask & 0x0008)
01269 {
01270 error = TRUE;
01271 LL_WARNS("RenderState") << "GL does not have GL_TEXTURE_2D enabled on channel 1." << LL_ENDL;
01272 }
01273 }
01274
01275 glClientActiveTextureARB(GL_TEXTURE0_ARB);
01276 glActiveTextureARB(GL_TEXTURE0_ARB);
01277
01278 if (error)
01279 {
01280 LL_GL_ERRS << "GL client array corruption detected." << LL_ENDL;
01281 }
01282 }
01283
01285
01286 LLGLState::LLGLState(LLGLenum state, S32 enabled) :
01287 mState(state), mWasEnabled(FALSE), mIsEnabled(FALSE)
01288 {
01289 stop_glerror();
01290 if (state)
01291 {
01292 mWasEnabled = sStateMap[state];
01293 llassert(mWasEnabled == glIsEnabled(state));
01294 setEnabled(enabled);
01295 stop_glerror();
01296 }
01297 }
01298
01299 void LLGLState::setEnabled(S32 enabled)
01300 {
01301 if (!mState)
01302 {
01303 return;
01304 }
01305 if (enabled == CURRENT_STATE)
01306 {
01307 enabled = sStateMap[mState] == GL_TRUE ? TRUE : FALSE;
01308 }
01309 else if (enabled == TRUE && sStateMap[mState] != GL_TRUE)
01310 {
01311 gGL.flush();
01312 glEnable(mState);
01313 sStateMap[mState] = GL_TRUE;
01314 }
01315 else if (enabled == FALSE && sStateMap[mState] != GL_FALSE)
01316 {
01317 gGL.flush();
01318 glDisable(mState);
01319 sStateMap[mState] = GL_FALSE;
01320 }
01321 mIsEnabled = enabled;
01322 }
01323
01324 LLGLState::~LLGLState()
01325 {
01326 stop_glerror();
01327 if (mState)
01328 {
01329 if (gDebugGL)
01330 {
01331 llassert_always(sStateMap[mState] == glIsEnabled(mState));
01332 }
01333
01334 if (mIsEnabled != mWasEnabled)
01335 {
01336 gGL.flush();
01337 if (mWasEnabled)
01338 {
01339 glEnable(mState);
01340 sStateMap[mState] = GL_TRUE;
01341 }
01342 else
01343 {
01344 glDisable(mState);
01345 sStateMap[mState] = GL_FALSE;
01346 }
01347 }
01348 }
01349 stop_glerror();
01350 }
01351
01353
01354 void LLGLManager::initGLStates()
01355 {
01356
01357 LLGLState::initClass();
01358 }
01359
01361
01362 void enable_vertex_weighting(const S32 index)
01363 {
01364 #if GL_ARB_vertex_program
01365 if (index > 0) glEnableVertexAttribArrayARB(index);
01366 #endif
01367 }
01368
01369 void disable_vertex_weighting(const S32 index)
01370 {
01371 #if GL_ARB_vertex_program
01372 if (index > 0) glDisableVertexAttribArrayARB(index);
01373 #endif
01374 }
01375
01376 void enable_binormals(const S32 index)
01377 {
01378 #if GL_ARB_vertex_program
01379 if (index > 0)
01380 {
01381 glEnableVertexAttribArrayARB(index);
01382 }
01383 #endif
01384 }
01385
01386 void disable_binormals(const S32 index)
01387 {
01388 #if GL_ARB_vertex_program
01389 if (index > 0)
01390 {
01391 glDisableVertexAttribArrayARB(index);
01392 }
01393 #endif
01394 }
01395
01396
01397 void enable_cloth_weights(const S32 index)
01398 {
01399 #if GL_ARB_vertex_program
01400 if (index > 0) glEnableVertexAttribArrayARB(index);
01401 #endif
01402 }
01403
01404 void disable_cloth_weights(const S32 index)
01405 {
01406 #if GL_ARB_vertex_program
01407 if (index > 0) glDisableVertexAttribArrayARB(index);
01408 #endif
01409 }
01410
01411 void set_vertex_weights(const S32 index, const U32 stride, const F32 *weights)
01412 {
01413 #if GL_ARB_vertex_program
01414 if (index > 0) glVertexAttribPointerARB(index, 1, GL_FLOAT, FALSE, stride, weights);
01415 stop_glerror();
01416 #endif
01417 }
01418
01419 void set_vertex_clothing_weights(const S32 index, const U32 stride, const LLVector4 *weights)
01420 {
01421 #if GL_ARB_vertex_program
01422 if (index > 0) glVertexAttribPointerARB(index, 4, GL_FLOAT, TRUE, stride, weights);
01423 stop_glerror();
01424 #endif
01425 }
01426
01427 void set_binormals(const S32 index, const U32 stride,const LLVector3 *binormals)
01428 {
01429 #if GL_ARB_vertex_program
01430 if (index > 0) glVertexAttribPointerARB(index, 3, GL_FLOAT, FALSE, stride, binormals);
01431 stop_glerror();
01432 #endif
01433 }
01434
01435
01436 void set_palette(U8 *palette_data)
01437 {
01438 if (gGLManager.mHasPalettedTextures)
01439 {
01440 glColorTableEXT(GL_TEXTURE_2D, GL_RGBA8, 256, GL_RGBA, GL_UNSIGNED_BYTE, palette_data);
01441 }
01442 }
01443
01444
01445 void parse_gl_version( S32* major, S32* minor, S32* release, LLString* vendor_specific )
01446 {
01447
01448
01449
01450 const char* version = (const char*) glGetString(GL_VERSION);
01451 *major = 0;
01452 *minor = 0;
01453 *release = 0;
01454 vendor_specific->assign("");
01455
01456 if( !version )
01457 {
01458 return;
01459 }
01460
01461 LLString ver_copy( version );
01462 S32 len = (S32)strlen( version );
01463 S32 i = 0;
01464 S32 start;
01465
01466 start = i;
01467 for( ; i < len; i++ )
01468 {
01469 if( '.' == version[i] )
01470 {
01471 break;
01472 }
01473 }
01474 LLString major_str = ver_copy.substr(start,i-start);
01475 LLString::convertToS32(major_str, *major);
01476
01477 if( '.' == version[i] )
01478 {
01479 i++;
01480 }
01481
01482
01483 start = i;
01484 for( ; i < len; i++ )
01485 {
01486 if( ('.' == version[i]) || isspace(version[i]) )
01487 {
01488 break;
01489 }
01490 }
01491 LLString minor_str = ver_copy.substr(start,i-start);
01492 LLString::convertToS32(minor_str, *minor);
01493
01494
01495 if( '.' == version[i] )
01496 {
01497 i++;
01498
01499 start = i;
01500 for( ; i < len; i++ )
01501 {
01502 if( isspace(version[i]) )
01503 {
01504 break;
01505 }
01506 }
01507
01508 LLString release_str = ver_copy.substr(start,i-start);
01509 LLString::convertToS32(release_str, *release);
01510 }
01511
01512
01513 while( version[i] && isspace( version[i] ) )
01514 {
01515 i++;
01516 }
01517
01518
01519 if( version[i] )
01520 {
01521 vendor_specific->assign( version + i );
01522 }
01523 }
01524
01525 LLGLUserClipPlane::LLGLUserClipPlane(const LLPlane& p, const glh::matrix4f& modelview, const glh::matrix4f& projection)
01526 {
01527 mModelview = modelview;
01528 mProjection = projection;
01529
01530 setPlane(p.mV[0], p.mV[1], p.mV[2], p.mV[3]);
01531 }
01532
01533 void LLGLUserClipPlane::setPlane(F32 a, F32 b, F32 c, F32 d)
01534 {
01535 glh::matrix4f& P = mProjection;
01536 glh::matrix4f& M = mModelview;
01537
01538 glh::matrix4f invtrans_MVP = (P * M).inverse().transpose();
01539 glh::vec4f oplane(a,b,c,d);
01540 glh::vec4f cplane;
01541 invtrans_MVP.mult_matrix_vec(oplane, cplane);
01542
01543 cplane /= fabs(cplane[2]);
01544 cplane[3] -= 1;
01545
01546 if(cplane[2] < 0)
01547 cplane *= -1;
01548
01549 glh::matrix4f suffix;
01550 suffix.set_row(2, cplane);
01551 glh::matrix4f newP = suffix * P;
01552 glMatrixMode(GL_PROJECTION);
01553 glPushMatrix();
01554 glLoadMatrixf(newP.m);
01555 gGLObliqueProjectionInverse = LLMatrix4(newP.inverse().transpose().m);
01556 glMatrixMode(GL_MODELVIEW);
01557 }
01558
01559 LLGLUserClipPlane::~LLGLUserClipPlane()
01560 {
01561 glMatrixMode(GL_PROJECTION);
01562 glPopMatrix();
01563 glMatrixMode(GL_MODELVIEW);
01564 }
01565
01566 LLGLNamePool::LLGLNamePool()
01567 {
01568 }
01569
01570 void LLGLNamePool::registerPool(LLGLNamePool* pool)
01571 {
01572 pool_list_t::iterator iter = std::find(sInstances.begin(), sInstances.end(), pool);
01573 if (iter == sInstances.end())
01574 {
01575 sInstances.push_back(pool);
01576 }
01577 }
01578
01579 LLGLNamePool::~LLGLNamePool()
01580 {
01581 pool_list_t::iterator iter = std::find(sInstances.begin(), sInstances.end(), this);
01582 if (iter != sInstances.end())
01583 {
01584 sInstances.erase(iter);
01585 }
01586 }
01587
01588 void LLGLNamePool::upkeep()
01589 {
01590 std::sort(mNameList.begin(), mNameList.end(), CompareUsed());
01591 }
01592
01593 void LLGLNamePool::cleanup()
01594 {
01595 for (name_list_t::iterator iter = mNameList.begin(); iter != mNameList.end(); ++iter)
01596 {
01597 releaseName(iter->name);
01598 }
01599
01600 mNameList.clear();
01601 }
01602
01603 GLuint LLGLNamePool::allocate()
01604 {
01605 for (name_list_t::iterator iter = mNameList.begin(); iter != mNameList.end(); ++iter)
01606 {
01607 if (!iter->used)
01608 {
01609 iter->used = TRUE;
01610 return iter->name;
01611 }
01612 }
01613
01614 NameEntry entry;
01615 entry.name = allocateName();
01616 entry.used = TRUE;
01617 mNameList.push_back(entry);
01618
01619 return entry.name;
01620 }
01621
01622 void LLGLNamePool::release(GLuint name)
01623 {
01624 for (name_list_t::iterator iter = mNameList.begin(); iter != mNameList.end(); ++iter)
01625 {
01626 if (iter->name == name)
01627 {
01628 iter->used = FALSE;
01629 return;
01630 }
01631 }
01632 }
01633
01634
01635 void LLGLNamePool::upkeepPools()
01636 {
01637 for (pool_list_t::iterator iter = sInstances.begin(); iter != sInstances.end(); ++iter)
01638 {
01639 LLGLNamePool* pool = *iter;
01640 pool->upkeep();
01641 }
01642 }
01643
01644
01645 void LLGLNamePool::cleanupPools()
01646 {
01647 for (pool_list_t::iterator iter = sInstances.begin(); iter != sInstances.end(); ++iter)
01648 {
01649 LLGLNamePool* pool = *iter;
01650 pool->cleanup();
01651 }
01652 }
01653
01654 LLGLDepthTest::LLGLDepthTest(GLboolean depth_enabled, GLboolean write_enabled, GLenum depth_func)
01655 : mPrevDepthEnabled(sDepthEnabled), mPrevDepthFunc(sDepthFunc), mPrevWriteEnabled(sWriteEnabled)
01656 {
01657 if (depth_enabled != sDepthEnabled)
01658 {
01659 gGL.flush();
01660 if (depth_enabled) glEnable(GL_DEPTH_TEST);
01661 else glDisable(GL_DEPTH_TEST);
01662 sDepthEnabled = depth_enabled;
01663 }
01664 if (depth_func != sDepthFunc)
01665 {
01666 gGL.flush();
01667 glDepthFunc(depth_func);
01668 sDepthFunc = depth_func;
01669 }
01670 if (write_enabled != sWriteEnabled)
01671 {
01672 gGL.flush();
01673 glDepthMask(write_enabled);
01674 sWriteEnabled = write_enabled;
01675 }
01676 }
01677
01678 LLGLDepthTest::~LLGLDepthTest()
01679 {
01680 if (sDepthEnabled != mPrevDepthEnabled )
01681 {
01682 gGL.flush();
01683 if (mPrevDepthEnabled) glEnable(GL_DEPTH_TEST);
01684 else glDisable(GL_DEPTH_TEST);
01685 sDepthEnabled = mPrevDepthEnabled;
01686 }
01687 if (sDepthFunc != mPrevDepthFunc)
01688 {
01689 gGL.flush();
01690 glDepthFunc(mPrevDepthFunc);
01691 sDepthFunc = mPrevDepthFunc;
01692 }
01693 if (sWriteEnabled != mPrevWriteEnabled )
01694 {
01695 gGL.flush();
01696 glDepthMask(mPrevWriteEnabled);
01697 sWriteEnabled = mPrevWriteEnabled;
01698 }
01699 }
01700
01701 LLGLClampToFarClip::LLGLClampToFarClip(glh::matrix4f P)
01702 {
01703 for (U32 i = 0; i < 4; i++)
01704 {
01705 P.element(2, i) = P.element(3, i) * 0.99999f;
01706 }
01707
01708 glMatrixMode(GL_PROJECTION);
01709 glPushMatrix();
01710 glLoadMatrixf(P.m);
01711 glMatrixMode(GL_MODELVIEW);
01712 }
01713
01714 LLGLClampToFarClip::~LLGLClampToFarClip()
01715 {
01716 glMatrixMode(GL_PROJECTION);
01717 glPopMatrix();
01718 glMatrixMode(GL_MODELVIEW);
01719 }
01720