📄 context.c
字号:
* \param stencilBits requested minimum bits per stencil buffer value * \param accumRedBits, accumGreenBits, accumBlueBits, accumAlphaBits number of bits per color component in accum buffer. * \param indexBits number of bits per pixel if \p rgbFlag is GL_FALSE * \param redBits number of bits per color component in frame buffer for RGB(A) * mode. We always use 8 in core Mesa though. * \param greenBits same as above. * \param blueBits same as above. * \param alphaBits same as above. * \param numSamples not really used. * * \return pointer to new GLvisual or NULL if requested parameters can't be * met. * * \note Need to add params for level and numAuxBuffers (at least) */GLvisual *_mesa_create_visual( GLboolean rgbFlag, GLboolean dbFlag, GLboolean stereoFlag, GLint redBits, GLint greenBits, GLint blueBits, GLint alphaBits, GLint indexBits, GLint depthBits, GLint stencilBits, GLint accumRedBits, GLint accumGreenBits, GLint accumBlueBits, GLint accumAlphaBits, GLint numSamples ){ GLvisual *vis = (GLvisual *) CALLOC( sizeof(GLvisual) ); if (vis) { if (!_mesa_initialize_visual(vis, rgbFlag, dbFlag, stereoFlag, redBits, greenBits, blueBits, alphaBits, indexBits, depthBits, stencilBits, accumRedBits, accumGreenBits, accumBlueBits, accumAlphaBits, numSamples)) { FREE(vis); return NULL; } } return vis;}/** * Makes some sanity checks and fills in the fields of the * GLvisual object with the given parameters. If the caller needs * to set additional fields, he should just probably init the whole GLvisual * object himself. * \return GL_TRUE on success, or GL_FALSE on failure. * * \sa _mesa_create_visual() above for the parameter description. */GLboolean_mesa_initialize_visual( GLvisual *vis, GLboolean rgbFlag, GLboolean dbFlag, GLboolean stereoFlag, GLint redBits, GLint greenBits, GLint blueBits, GLint alphaBits, GLint indexBits, GLint depthBits, GLint stencilBits, GLint accumRedBits, GLint accumGreenBits, GLint accumBlueBits, GLint accumAlphaBits, GLint numSamples ){ assert(vis); if (depthBits < 0 || depthBits > 32) { return GL_FALSE; } if (stencilBits < 0 || stencilBits > STENCIL_BITS) { return GL_FALSE; } assert(accumRedBits >= 0); assert(accumGreenBits >= 0); assert(accumBlueBits >= 0); assert(accumAlphaBits >= 0); vis->rgbMode = rgbFlag; vis->doubleBufferMode = dbFlag; vis->stereoMode = stereoFlag; vis->redBits = redBits; vis->greenBits = greenBits; vis->blueBits = blueBits; vis->alphaBits = alphaBits; vis->rgbBits = redBits + greenBits + blueBits; vis->indexBits = indexBits; vis->depthBits = depthBits; vis->stencilBits = stencilBits; vis->accumRedBits = accumRedBits; vis->accumGreenBits = accumGreenBits; vis->accumBlueBits = accumBlueBits; vis->accumAlphaBits = accumAlphaBits; vis->haveAccumBuffer = accumRedBits > 0; vis->haveDepthBuffer = depthBits > 0; vis->haveStencilBuffer = stencilBits > 0; vis->numAuxBuffers = 0; vis->level = 0; vis->pixmapMode = 0; vis->sampleBuffers = numSamples > 0 ? 1 : 0; vis->samples = numSamples; return GL_TRUE;}/** * Destroy a visual and free its memory. * * \param vis visual. * * Frees the visual structure. */void_mesa_destroy_visual( GLvisual *vis ){ FREE(vis);}/*@}*//**********************************************************************//** \name Context allocation, initialization, destroying * * The purpose of the most initialization functions here is to provide the * default state values according to the OpenGL specification. *//**********************************************************************//*@{*//** * One-time initialization mutex lock. * * \sa Used by one_time_init(). */_glthread_DECLARE_STATIC_MUTEX(OneTimeLock);/** * Calls all the various one-time-init functions in Mesa. * * While holding a global mutex lock, calls several initialization functions, * and sets the glapi callbacks if the \c MESA_DEBUG environment variable is * defined. * * \sa _math_init(). */static voidone_time_init( GLcontext *ctx ){ static GLboolean alreadyCalled = GL_FALSE; (void) ctx; _glthread_LOCK_MUTEX(OneTimeLock); if (!alreadyCalled) { GLuint i; /* do some implementation tests */ assert( sizeof(GLbyte) == 1 ); assert( sizeof(GLubyte) == 1 ); assert( sizeof(GLshort) == 2 ); assert( sizeof(GLushort) == 2 ); assert( sizeof(GLint) == 4 ); assert( sizeof(GLuint) == 4 );#if _HAVE_FULL_GL _math_init(); for (i = 0; i < 256; i++) { _mesa_ubyte_to_float_color_tab[i] = (float) i / 255.0F; }#endif#ifdef USE_SPARC_ASM _mesa_init_sparc_glapi_relocs();#endif if (_mesa_getenv("MESA_DEBUG")) { _glapi_noop_enable_warnings(GL_TRUE); _glapi_set_warning_func( (_glapi_warning_func) _mesa_warning ); } else { _glapi_noop_enable_warnings(GL_FALSE); }#if defined(DEBUG) && defined(__DATE__) && defined(__TIME__) _mesa_debug(ctx, "Mesa %s DEBUG build %s %s\n", MESA_VERSION_STRING, __DATE__, __TIME__);#endif alreadyCalled = GL_TRUE; } _glthread_UNLOCK_MUTEX(OneTimeLock);}/** * Allocate and initialize a shared context state structure. * Initializes the display list, texture objects and vertex programs hash * tables, allocates the texture objects. If it runs out of memory, frees * everything already allocated before returning NULL. * * \return pointer to a gl_shared_state structure on success, or NULL on * failure. */static GLbooleanalloc_shared_state( GLcontext *ctx ){ struct gl_shared_state *ss = CALLOC_STRUCT(gl_shared_state); if (!ss) return GL_FALSE; ctx->Shared = ss; _glthread_INIT_MUTEX(ss->Mutex); ss->DisplayList = _mesa_NewHashTable(); ss->TexObjects = _mesa_NewHashTable();#if FEATURE_NV_vertex_program || FEATURE_NV_fragment_program ss->Programs = _mesa_NewHashTable();#endif#if FEATURE_ARB_vertex_program ss->DefaultVertexProgram = ctx->Driver.NewProgram(ctx, GL_VERTEX_PROGRAM_ARB, 0); if (!ss->DefaultVertexProgram) goto cleanup;#endif#if FEATURE_ARB_fragment_program ss->DefaultFragmentProgram = ctx->Driver.NewProgram(ctx, GL_FRAGMENT_PROGRAM_ARB, 0); if (!ss->DefaultFragmentProgram) goto cleanup;#endif#if FEATURE_ATI_fragment_shader ss->ATIShaders = _mesa_NewHashTable(); ss->DefaultFragmentShader = _mesa_new_ati_fragment_shader(ctx, 0); if (!ss->DefaultFragmentShader) goto cleanup;#endif ss->BufferObjects = _mesa_NewHashTable(); ss->GL2Objects = _mesa_NewHashTable (); ss->Default1D = (*ctx->Driver.NewTextureObject)(ctx, 0, GL_TEXTURE_1D); if (!ss->Default1D) goto cleanup; ss->Default2D = (*ctx->Driver.NewTextureObject)(ctx, 0, GL_TEXTURE_2D); if (!ss->Default2D) goto cleanup; ss->Default3D = (*ctx->Driver.NewTextureObject)(ctx, 0, GL_TEXTURE_3D); if (!ss->Default3D) goto cleanup; ss->DefaultCubeMap = (*ctx->Driver.NewTextureObject)(ctx, 0, GL_TEXTURE_CUBE_MAP_ARB); if (!ss->DefaultCubeMap) goto cleanup; ss->DefaultRect = (*ctx->Driver.NewTextureObject)(ctx, 0, GL_TEXTURE_RECTANGLE_NV); if (!ss->DefaultRect) goto cleanup; /* Effectively bind the default textures to all texture units */ ss->Default1D->RefCount += MAX_TEXTURE_IMAGE_UNITS; ss->Default2D->RefCount += MAX_TEXTURE_IMAGE_UNITS; ss->Default3D->RefCount += MAX_TEXTURE_IMAGE_UNITS; ss->DefaultCubeMap->RefCount += MAX_TEXTURE_IMAGE_UNITS; ss->DefaultRect->RefCount += MAX_TEXTURE_IMAGE_UNITS;#if FEATURE_EXT_framebuffer_object ss->FrameBuffers = _mesa_NewHashTable(); if (!ss->FrameBuffers) goto cleanup; ss->RenderBuffers = _mesa_NewHashTable(); if (!ss->RenderBuffers) goto cleanup;#endif return GL_TRUE; cleanup: /* Ran out of memory at some point. Free everything and return NULL */ if (ss->DisplayList) _mesa_DeleteHashTable(ss->DisplayList); if (ss->TexObjects) _mesa_DeleteHashTable(ss->TexObjects);#if FEATURE_NV_vertex_program if (ss->Programs) _mesa_DeleteHashTable(ss->Programs);#endif#if FEATURE_ARB_vertex_program if (ss->DefaultVertexProgram) ctx->Driver.DeleteProgram(ctx, ss->DefaultVertexProgram);#endif#if FEATURE_ARB_fragment_program if (ss->DefaultFragmentProgram) ctx->Driver.DeleteProgram(ctx, ss->DefaultFragmentProgram);#endif#if FEATURE_ATI_fragment_shader if (ss->DefaultFragmentShader) _mesa_delete_ati_fragment_shader(ctx, ss->DefaultFragmentShader);#endif#if FEATURE_ARB_vertex_buffer_object if (ss->BufferObjects) _mesa_DeleteHashTable(ss->BufferObjects);#endif if (ss->GL2Objects) _mesa_DeleteHashTable (ss->GL2Objects);#if FEATURE_EXT_framebuffer_object if (ss->FrameBuffers) _mesa_DeleteHashTable(ss->FrameBuffers); if (ss->RenderBuffers) _mesa_DeleteHashTable(ss->RenderBuffers);#endif if (ss->Default1D) (*ctx->Driver.DeleteTexture)(ctx, ss->Default1D); if (ss->Default2D) (*ctx->Driver.DeleteTexture)(ctx, ss->Default2D); if (ss->Default3D) (*ctx->Driver.DeleteTexture)(ctx, ss->Default3D); if (ss->DefaultCubeMap) (*ctx->Driver.DeleteTexture)(ctx, ss->DefaultCubeMap); if (ss->DefaultRect) (*ctx->Driver.DeleteTexture)(ctx, ss->DefaultRect); if (ss) _mesa_free(ss); return GL_FALSE;}/** * Deallocate a shared state context and all children structures. * * \param ctx GL context. * \param ss shared state pointer. * * Frees the display lists, the texture objects (calling the driver texture * deletion callback to free its private data) and the vertex programs, as well * as their hash tables. * * \sa alloc_shared_state(). */static voidfree_shared_state( GLcontext *ctx, struct gl_shared_state *ss ){ /* Free display lists */ while (1) { GLuint list = _mesa_HashFirstEntry(ss->DisplayList); if (list) { _mesa_destroy_list(ctx, list); } else { break; } } _mesa_DeleteHashTable(ss->DisplayList); /* Free texture objects */ ASSERT(ctx->Driver.DeleteTexture); /* the default textures */ (*ctx->Driver.DeleteTexture)(ctx, ss->Default1D); (*ctx->Driver.DeleteTexture)(ctx, ss->Default2D); (*ctx->Driver.DeleteTexture)(ctx, ss->Default3D); (*ctx->Driver.DeleteTexture)(ctx, ss->DefaultCubeMap); (*ctx->Driver.DeleteTexture)(ctx, ss->DefaultRect); /* all other textures */ while (1) { GLuint texName = _mesa_HashFirstEntry(ss->TexObjects); if (texName) { struct gl_texture_object *texObj = (struct gl_texture_object *) _mesa_HashLookup(ss->TexObjects, texName); ASSERT(texObj); (*ctx->Driver.DeleteTexture)(ctx, texObj); _mesa_HashRemove(ss->TexObjects, texName); } else { break; } } _mesa_DeleteHashTable(ss->TexObjects);#if defined(FEATURE_NV_vertex_program) || defined(FEATURE_NV_fragment_program) /* Free vertex/fragment programs */ while (1) { GLuint prog = _mesa_HashFirstEntry(ss->Programs); if (prog) { struct program *p = (struct program *) _mesa_HashLookup(ss->Programs, prog); ASSERT(p); ctx->Driver.DeleteProgram(ctx, p); _mesa_HashRemove(ss->Programs, prog); } else { break; } } _mesa_DeleteHashTable(ss->Programs);#endif#if FEATURE_ARB_vertex_program _mesa_delete_program(ctx, ss->DefaultVertexProgram);#endif#if FEATURE_ARB_fragment_program _mesa_delete_program(ctx, ss->DefaultFragmentProgram);#endif#if FEATURE_ATI_fragment_shader /* Free ATI fragment shaders */ while (1) { GLuint prog = _mesa_HashFirstEntry(ss->ATIShaders); if (prog) { struct ati_fragment_shader *s = (struct ati_fragment_shader *) _mesa_HashLookup(ss->ATIShaders, prog); ASSERT(s); _mesa_delete_ati_fragment_shader(ctx, s); _mesa_HashRemove(ss->ATIShaders, prog); } else { break; } } _mesa_DeleteHashTable(ss->ATIShaders); _mesa_delete_ati_fragment_shader(ctx, ss->DefaultFragmentShader);#endif#if FEATURE_ARB_vertex_buffer_object _mesa_DeleteHashTable(ss->BufferObjects);#endif#if FEATURE_ARB_shader_objects _mesa_DeleteHashTable (ss->GL2Objects);#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -