⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 context.c

📁 winNT技术操作系统,国外开放的原代码和LIUX一样
💻 C
📖 第 1 页 / 共 4 页
字号:
 * Allocates a GLvisual structure and initializes it via
 * _mesa_initialize_visual().
 * 
 * \param rgbFlag GL_TRUE for RGB(A) mode, GL_FALSE for Color Index mode.
 * \param dbFlag double buffering
 * \param stereoFlag stereo buffer
 * \param depthBits requested bits per depth buffer value. Any value in [0, 32]
 * is acceptable but the actual depth type will be GLushort or GLuint as
 * needed.
 * \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;
   }
   if (accumRedBits < 0 || accumRedBits > ACCUM_BITS) {
      return GL_FALSE;
   }
   if (accumGreenBits < 0 || accumGreenBits > ACCUM_BITS) {
      return GL_FALSE;
   }
   if (accumBlueBits < 0 || accumBlueBits > ACCUM_BITS) {
      return GL_FALSE;
   }
   if (accumAlphaBits < 0 || accumAlphaBits > ACCUM_BITS) {
      return GL_FALSE;
   }

   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 _mesa_init_lists(), _math_init().
 */
static void
one_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 );

      _mesa_init_lists();

#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 GLboolean
alloc_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->DefaultFragmentShader = ctx->Driver.NewProgram(ctx, GL_FRAGMENT_SHADER_ATI, 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)
      ctx->Driver.DeleteProgram(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 void
free_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 FEATURE_NV_vertex_program
   /* Free vertex 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

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -