From: Dave Airlie <airl...@redhat.com>

If we have no tess control shader, then we have to use a fallback
one that just writes the tessellation factors.

Signed-off-by: Dave Airlie <airl...@redhat.com>
---
 src/gallium/drivers/r600/r600_pipe.c         |  3 ++
 src/gallium/drivers/r600/r600_pipe.h         |  2 ++
 src/gallium/drivers/r600/r600_state_common.c | 42 +++++++++++++++++++++++++++-
 3 files changed, 46 insertions(+), 1 deletion(-)

diff --git a/src/gallium/drivers/r600/r600_pipe.c 
b/src/gallium/drivers/r600/r600_pipe.c
index bd00dcb..64f5fc6 100644
--- a/src/gallium/drivers/r600/r600_pipe.c
+++ b/src/gallium/drivers/r600/r600_pipe.c
@@ -76,6 +76,9 @@ static void r600_destroy_context(struct pipe_context *context)
        pipe_resource_reference((struct pipe_resource**)&rctx->dummy_cmask, 
NULL);
        pipe_resource_reference((struct pipe_resource**)&rctx->dummy_fmask, 
NULL);
 
+       if (rctx->fixed_func_tcs_shader)
+               rctx->b.b.delete_tcs_state(&rctx->b.b, 
rctx->fixed_func_tcs_shader);
+
        if (rctx->dummy_pixel_shader) {
                rctx->b.b.delete_fs_state(&rctx->b.b, rctx->dummy_pixel_shader);
        }
diff --git a/src/gallium/drivers/r600/r600_pipe.h 
b/src/gallium/drivers/r600/r600_pipe.h
index dfb5f46..78f3a59 100644
--- a/src/gallium/drivers/r600/r600_pipe.h
+++ b/src/gallium/drivers/r600/r600_pipe.h
@@ -512,6 +512,8 @@ struct r600_context {
        struct r600_pipe_shader_selector *tcs_shader;
        struct r600_pipe_shader_selector *tes_shader;
 
+       struct r600_pipe_shader_selector *fixed_func_tcs_shader;
+
        struct r600_rasterizer_state    *rasterizer;
        bool                            alpha_to_one;
        bool                            force_blend_disable;
diff --git a/src/gallium/drivers/r600/r600_state_common.c 
b/src/gallium/drivers/r600/r600_state_common.c
index d9152d7..84d85fb 100644
--- a/src/gallium/drivers/r600/r600_state_common.c
+++ b/src/gallium/drivers/r600/r600_state_common.c
@@ -35,6 +35,7 @@
 #include "util/u_math.h"
 #include "tgsi/tgsi_parse.h"
 #include "tgsi/tgsi_scan.h"
+#include "tgsi/tgsi_ureg.h"
 
 void r600_init_command_buffer(struct r600_command_buffer *cb, unsigned num_dw)
 {
@@ -1376,6 +1377,35 @@ static void r600_update_clip_state(struct r600_context 
*rctx,
                                r600_mark_atom_dirty(rctx, 
&rctx->clip_misc_state.atom);
        }
 }
+
+static void r600_generate_fixed_func_tcs(struct r600_context *rctx)
+{
+       struct ureg_src const0, const1;
+       struct ureg_dst tessouter, tessinner;
+       struct ureg_program *ureg = ureg_create(TGSI_PROCESSOR_TESS_CTRL);
+
+       if (!ureg)
+               return; /* if we get here, we're screwed */
+
+       assert(!rctx->fixed_func_tcs_shader);
+
+       ureg_DECL_constant2D(ureg, 0, 3, R600_LDS_INFO_CONST_BUFFER);
+       const0 = ureg_src_dimension(ureg_src_register(TGSI_FILE_CONSTANT, 2),
+                                   R600_LDS_INFO_CONST_BUFFER);
+       const1 = ureg_src_dimension(ureg_src_register(TGSI_FILE_CONSTANT, 3),
+                                   R600_LDS_INFO_CONST_BUFFER);
+
+       tessouter = ureg_DECL_output(ureg, TGSI_SEMANTIC_TESSOUTER, 0);
+       tessinner = ureg_DECL_output(ureg, TGSI_SEMANTIC_TESSINNER, 0);
+
+       ureg_MOV(ureg, tessouter, const0);
+       ureg_MOV(ureg, tessinner, const1);
+       ureg_END(ureg);
+
+       rctx->fixed_func_tcs_shader =
+               ureg_create_shader_and_destroy(ureg, &rctx->b.b);
+}
+
 #define SELECT_SHADER_OR_FAIL(x) do {                                  \
                r600_shader_select(ctx, rctx->x##_shader, &x##_dirty);  \
                if (unlikely(!rctx->x##_shader))                        \
@@ -1411,7 +1441,7 @@ static bool r600_update_derived_state(struct r600_context 
*rctx)
 {
        struct pipe_context * ctx = (struct pipe_context*)rctx;
        bool ps_dirty = false, vs_dirty = false, gs_dirty = false;
-       bool tcs_dirty = false, tes_dirty = false;
+       bool tcs_dirty = false, tes_dirty = false, fixed_func_tcs_dirty = false;
        bool blend_disable;
        bool need_buf_const;
        struct r600_pipe_shader *clip_so_current = NULL;
@@ -1445,6 +1475,16 @@ static bool r600_update_derived_state(struct 
r600_context *rctx)
                SELECT_SHADER_OR_FAIL(tcs);
 
                UPDATE_SHADER(EG_HW_STAGE_HS, tcs);
+       } else if (rctx->tes_shader) {
+               if (!rctx->fixed_func_tcs_shader) {
+                       r600_generate_fixed_func_tcs(rctx);
+                       if (!rctx->fixed_func_tcs_shader)
+                               return false;
+
+               }
+               SELECT_SHADER_OR_FAIL(fixed_func_tcs);
+
+               UPDATE_SHADER(EG_HW_STAGE_HS, fixed_func_tcs);
        } else
                SET_NULL_SHADER(EG_HW_STAGE_HS);
 
-- 
2.5.0

_______________________________________________
mesa-dev mailing list
mesa-dev@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/mesa-dev

Reply via email to