Exemplo n.º 1
0
/**
 * For GL_EXT_separate_shader_objects
 */
void GLAPIENTRY
_mesa_UseShaderProgramEXT(GLenum type, GLuint program)
{
   GET_CURRENT_CONTEXT(ctx);
   struct gl_shader_program *shProg = NULL;

   ASSERT_OUTSIDE_BEGIN_END(ctx);

   if (!validate_shader_target(ctx, type)) {
      _mesa_error(ctx, GL_INVALID_ENUM, "glUseShaderProgramEXT(type)");
      return;
   }

   if (ctx->TransformFeedback.CurrentObject->Active &&
       !ctx->TransformFeedback.CurrentObject->Paused) {
      _mesa_error(ctx, GL_INVALID_OPERATION,
                  "glUseShaderProgramEXT(transform feedback is active)");
      return;
   }

   if (program) {
      shProg = _mesa_lookup_shader_program_err(ctx, program,
					       "glUseShaderProgramEXT");
      if (shProg == NULL)
	 return;

      if (!shProg->LinkStatus) {
	 _mesa_error(ctx, GL_INVALID_OPERATION,
		     "glUseShaderProgramEXT(program not linked)");
	 return;
      }
   }

   _mesa_use_shader_program(ctx, type, shProg);
}
Exemplo n.º 2
0
/**
 * For GL_EXT_separate_shader_objects
 */
void GLAPIENTRY
_mesa_UseShaderProgramEXT(GLenum type, GLuint program)
{
   GET_CURRENT_CONTEXT(ctx);
   struct gl_shader_program *shProg = NULL;

   if (!validate_shader_target(ctx, type)) {
      _mesa_error(ctx, GL_INVALID_ENUM, "glUseShaderProgramEXT(type)");
      return;
   }

   if (_mesa_is_xfb_active_and_unpaused(ctx)) {
      _mesa_error(ctx, GL_INVALID_OPERATION,
                  "glUseShaderProgramEXT(transform feedback is active)");
      return;
   }

   if (program) {
      shProg = _mesa_lookup_shader_program_err(ctx, program,
					       "glUseShaderProgramEXT");
      if (shProg == NULL)
	 return;

      if (!shProg->LinkStatus) {
	 _mesa_error(ctx, GL_INVALID_OPERATION,
		     "glUseShaderProgramEXT(program not linked)");
	 return;
      }
   }

   _mesa_use_shader_program(ctx, type, shProg);
}
Exemplo n.º 3
0
/**
 * Bound program to severals stages of the pipeline
 */
void GLAPIENTRY
_mesa_UseProgramStages(GLuint pipeline, GLbitfield stages, GLuint program)
{
   GET_CURRENT_CONTEXT(ctx);

   struct gl_pipeline_object *pipe = lookup_pipeline_object(ctx, pipeline);
   struct gl_shader_program *shProg = NULL;
   GLbitfield any_valid_stages;

   if (!pipe) {
      _mesa_error(ctx, GL_INVALID_OPERATION, "glUseProgramStages(pipeline)");
      return;
   }

   /* Object is created by any Pipeline call but glGenProgramPipelines,
    * glIsProgramPipeline and GetProgramPipelineInfoLog
    */
   pipe->EverBound = GL_TRUE;

   /* Section 2.11.4 (Program Pipeline Objects) of the OpenGL 4.1 spec says:
    *
    *     "If stages is not the special value ALL_SHADER_BITS, and has a bit
    *     set that is not recognized, the error INVALID_VALUE is generated."
    *
    * NOT YET SUPPORTED:
    * GL_TESS_CONTROL_SHADER_BIT
    * GL_TESS_EVALUATION_SHADER_BIT
    */
   any_valid_stages = GL_VERTEX_SHADER_BIT | GL_FRAGMENT_SHADER_BIT;
   if (_mesa_has_geometry_shaders(ctx))
      any_valid_stages |= GL_GEOMETRY_SHADER_BIT;

   if (stages != GL_ALL_SHADER_BITS && (stages & ~any_valid_stages) != 0) {
      _mesa_error(ctx, GL_INVALID_VALUE, "glUseProgramStages(Stages)");
      return;
   }

   /* Section 2.17.2 (Transform Feedback Primitive Capture) of the OpenGL 4.1
    * spec says:
    *
    *     "The error INVALID_OPERATION is generated:
    *
    *      ...
    *
    *         - by UseProgramStages if the program pipeline object it refers
    *           to is current and the current transform feedback object is
    *           active and not paused;
    */
   if (ctx->_Shader == pipe) {
      if (_mesa_is_xfb_active_and_unpaused(ctx)) {
         _mesa_error(ctx, GL_INVALID_OPERATION,
               "glUseProgramStages(transform feedback active)");
         return;
      }
   }

   if (program) {
      shProg = _mesa_lookup_shader_program_err(ctx, program,
                                               "glUseProgramStages");
      if (shProg == NULL)
         return;

      /* Section 2.11.4 (Program Pipeline Objects) of the OpenGL 4.1 spec
       * says:
       *
       *     "If the program object named by program was linked without the
       *     PROGRAM_SEPARABLE parameter set, or was not linked successfully,
       *     the error INVALID_OPERATION is generated and the corresponding
       *     shader stages in the pipeline program pipeline object are not
       *     modified."
       */
      if (!shProg->LinkStatus) {
         _mesa_error(ctx, GL_INVALID_OPERATION,
                     "glUseProgramStages(program not linked)");
         return;
      }

      if (!shProg->SeparateShader) {
         _mesa_error(ctx, GL_INVALID_OPERATION,
                     "glUseProgramStages(program wasn't linked with the "
                     "PROGRAM_SEPARABLE flag)");
         return;
      }
   }

   /* Enable individual stages from the program as requested by the
    * application.  If there is no shader for a requested stage in the
    * program, _mesa_use_shader_program will enable fixed-function processing
    * as dictated by the spec.
    *
    * Section 2.11.4 (Program Pipeline Objects) of the OpenGL 4.1 spec
    * says:
    *
    *     "If UseProgramStages is called with program set to zero or with a
    *     program object that contains no executable code for the given
    *     stages, it is as if the pipeline object has no programmable stage
    *     configured for the indicated shader stages."
    */
   if ((stages & GL_VERTEX_SHADER_BIT) != 0)
      _mesa_use_shader_program(ctx, GL_VERTEX_SHADER, shProg, pipe);

   if ((stages & GL_FRAGMENT_SHADER_BIT) != 0)
      _mesa_use_shader_program(ctx, GL_FRAGMENT_SHADER, shProg, pipe);

   if ((stages & GL_GEOMETRY_SHADER_BIT) != 0)
      _mesa_use_shader_program(ctx, GL_GEOMETRY_SHADER, shProg, pipe);
}