Пример #1
0
static enum pipe_error
emit_hw_fs(struct svga_context *svga, unsigned dirty)
{
   struct svga_shader_variant *variant = NULL;
   enum pipe_error ret = PIPE_OK;
   struct svga_fragment_shader *fs = svga->curr.fs;
   struct svga_compile_key key;

   /* SVGA_NEW_BLEND
    * SVGA_NEW_TEXTURE_BINDING
    * SVGA_NEW_RAST
    * SVGA_NEW_NEED_SWTNL
    * SVGA_NEW_SAMPLER
    * SVGA_NEW_FRAME_BUFFER
    * SVGA_NEW_DEPTH_STENCIL_ALPHA
    * SVGA_NEW_VS
    */
   ret = make_fs_key(svga, fs, &key);
   if (ret != PIPE_OK)
      return ret;

   variant = svga_search_shader_key(&fs->base, &key);
   if (!variant) {
      ret = compile_fs(svga, fs, &key, &variant);
      if (ret != PIPE_OK)
         return ret;
   }

   assert(variant);

   if (variant != svga->state.hw_draw.fs) {
      ret = svga_set_shader(svga, SVGA3D_SHADERTYPE_PS, variant);
      if (ret != PIPE_OK)
         return ret;

      svga->rebind.flags.fs = FALSE;

      svga->dirty |= SVGA_NEW_FS_VARIANT;
      svga->state.hw_draw.fs = variant;
   }

   return PIPE_OK;
}
Пример #2
0
static enum pipe_error
emit_hw_gs(struct svga_context *svga, unsigned dirty)
{
   struct svga_shader_variant *variant;
   struct svga_geometry_shader *gs = svga->curr.gs;
   enum pipe_error ret = PIPE_OK;
   struct svga_compile_key key;

   /* If there's a user-defined GS, we should have a pointer to a derived
    * GS.  This should have been resolved in update_tgsi_transform().
    */
   if (svga->curr.user_gs)
      assert(svga->curr.gs);

   if (!gs) {
      if (svga->state.hw_draw.gs != NULL) {

         /** The previous geometry shader is made inactive.
          *  Needs to unbind the geometry shader.
          */
         ret = svga_set_shader(svga, SVGA3D_SHADERTYPE_GS, NULL);
         svga->state.hw_draw.gs = NULL;
      }
      return ret;
   }

   /* If there is stream output info for this geometry shader, then use
    * it instead of the one from the vertex shader.
    */
   if (svga_have_gs_streamout(svga)) {
      svga_set_stream_output(svga, gs->base.stream_output);
   }
   else if (!svga_have_vs_streamout(svga)) {
      /* turn off stream out */
      svga_set_stream_output(svga, NULL);
   }

   /* SVGA_NEW_NEED_SWTNL */
   if (svga->state.sw.need_swtnl && !svga_have_vgpu10(svga)) {
      /* No geometry shader is needed */
      variant = NULL;
   }
   else {
      make_gs_key(svga, &key);

      /* See if we already have a GS variant that matches the key */
      variant = svga_search_shader_key(&gs->base, &key);

      if (!variant) {
         ret = compile_gs(svga, gs, &key, &variant);
         if (ret != PIPE_OK)
            return ret;

         /* insert the new variant at head of linked list */
         assert(variant);
         variant->next = gs->base.variants;
         gs->base.variants = variant;
      }
   }

   if (variant != svga->state.hw_draw.gs) {
      /* Bind the new variant */
      ret = svga_set_shader(svga, SVGA3D_SHADERTYPE_GS, variant);
      if (ret != PIPE_OK)
         return ret;

      svga->rebind.flags.gs = FALSE;
      svga->dirty |= SVGA_NEW_GS_VARIANT;
      svga->state.hw_draw.gs = variant;
   }

   return PIPE_OK;
}
Пример #3
0
static enum pipe_error
emit_hw_vs(struct svga_context *svga, unsigned dirty)
{
   struct svga_shader_variant *variant;
   struct svga_vertex_shader *vs = svga->curr.vs;
   struct svga_fragment_shader *fs = svga->curr.fs;
   enum pipe_error ret = PIPE_OK;
   struct svga_compile_key key;

   /* If there is an active geometry shader, and it has stream output
    * defined, then we will skip the stream output from the vertex shader
    */
   if (!svga_have_gs_streamout(svga)) {
      /* No GS stream out */
      if (svga_have_vs_streamout(svga)) {
         /* Set VS stream out */
         svga_set_stream_output(svga, vs->base.stream_output);
      }
      else {
         /* turn off stream out */
         svga_set_stream_output(svga, NULL);
      }
   }

   /* SVGA_NEW_NEED_SWTNL */
   if (svga->state.sw.need_swtnl && !svga_have_vgpu10(svga)) {
      /* No vertex shader is needed */
      variant = NULL;
   }
   else {
      make_vs_key(svga, &key);

      /* See if we already have a VS variant that matches the key */
      variant = svga_search_shader_key(&vs->base, &key);

      if (!variant) {
         /* Create VS variant now */
         if (key.vs.passthrough) {
            ret = compile_passthrough_vs(svga, vs, fs, &variant);
         }
         else {
            ret = compile_vs(svga, vs, &key, &variant);
         }
         if (ret != PIPE_OK)
            return ret;

         /* insert the new variant at head of linked list */
         assert(variant);
         variant->next = vs->base.variants;
         vs->base.variants = variant;
      }
   }

   if (variant != svga->state.hw_draw.vs) {
      /* Bind the new variant */
      if (variant) {
         ret = svga_set_shader(svga, SVGA3D_SHADERTYPE_VS, variant);
         if (ret != PIPE_OK)
            return ret;
         svga->rebind.flags.vs = FALSE;
      }

      svga->dirty |= SVGA_NEW_VS_VARIANT;
      svga->state.hw_draw.vs = variant;
   }

   return PIPE_OK;
}