broadcom/vc5: Port the draw-time state emission to V3D 4.1.
authorEric Anholt <eric@anholt.net>
Fri, 12 Jan 2018 20:31:14 +0000 (12:31 -0800)
committerEric Anholt <eric@anholt.net>
Sat, 13 Jan 2018 05:57:52 +0000 (21:57 -0800)
src/gallium/drivers/vc5/Makefile.sources
src/gallium/drivers/vc5/meson.build
src/gallium/drivers/vc5/v3dx_context.h
src/gallium/drivers/vc5/vc5_context.h
src/gallium/drivers/vc5/vc5_draw.c
src/gallium/drivers/vc5/vc5_emit.c
src/gallium/drivers/vc5/vc5_screen.c

index 252431b54b5ed70a89507572ad505227be508c50..f5cd8d79f85d5b46b95ef6b7eb6aa82f23e36820 100644 (file)
@@ -7,7 +7,6 @@ C_SOURCES := \
        vc5_context.c \
        vc5_context.h \
        vc5_drm.h \
-       vc5_emit.c \
        vc5_fence.c \
        vc5_formats.c \
        vc5_job.c \
@@ -27,6 +26,7 @@ VC5_PER_VERSION_SOURCES = \
        v3dx_format_table.c \
        v3dx_simulator.c \
        vc5_draw.c \
+       vc5_emit.c \
        vc5_rcl.c \
        vc5_state.c \
        $()
index aa74e624bdbd8e86a878b0cd7812b464a7abc120..005bf2f9b8ec4183abb287bc485fd7295d7a48da 100644 (file)
@@ -26,7 +26,6 @@ files_libvc5 = files(
   'vc5_cl.h',
   'vc5_context.c',
   'vc5_context.h',
-  'vc5_emit.c',
   'vc5_fence.c',
   'vc5_formats.c',
   'vc5_job.c',
@@ -47,6 +46,7 @@ files_per_version = files(
   'v3dx_format_table.c',
   'v3dx_simulator.c',
   'vc5_draw.c',
+  'vc5_emit.c',
   'vc5_rcl.c',
   'vc5_state.c',
 )
index f92712dcf791d9e89e9919bd3395c769f3a7e208..addc7433b37dcfb3d520e3389648cf2e9a0ec1f2 100644 (file)
@@ -29,6 +29,7 @@
 struct v3d_hw;
 struct vc5_format;
 
+void v3dX(emit_state)(struct pipe_context *pctx);
 void v3dX(emit_rcl)(struct vc5_job *job);
 void v3dX(draw_init)(struct pipe_context *pctx);
 void v3dX(state_init)(struct pipe_context *pctx);
index e4c2eb551bd5569efaf887aeb13f7b626d6f735d..18fc27c5147f0fc0427fec9ced1d0807168acfaa 100644 (file)
@@ -492,7 +492,6 @@ void vc5_flush_jobs_writing_resource(struct vc5_context *vc5,
                                      struct pipe_resource *prsc);
 void vc5_flush_jobs_reading_resource(struct vc5_context *vc5,
                                      struct pipe_resource *prsc);
-void vc5_emit_state(struct pipe_context *pctx);
 void vc5_update_compiled_shaders(struct vc5_context *vc5, uint8_t prim_mode);
 
 bool vc5_rt_format_supported(const struct v3d_device_info *devinfo,
index 39378280823eb023a1fe02bb646eb0ef88a440a3..7a409c14d4c349b6e0ed10213120db2418443066 100644 (file)
@@ -385,7 +385,11 @@ vc5_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
         vc5_start_draw(vc5);
         vc5_update_compiled_shaders(vc5, info->mode);
 
-        vc5_emit_state(pctx);
+#if V3D_VERSION >= 41
+        v3d41_emit_state(pctx);
+#else
+        v3d33_emit_state(pctx);
+#endif
 
         if (vc5->dirty & (VC5_DIRTY_VTXBUF |
                           VC5_DIRTY_VTXSTATE |
index 53fa01b3f42473d1a96c1355f4d84f308b8cc1f1..ae47fda81ffc85c2390c255d5f31b98460414d0c 100644 (file)
@@ -24,7 +24,6 @@
 #include "util/u_format.h"
 #include "util/u_half.h"
 #include "vc5_context.h"
-#define V3D_VERSION 33
 #include "broadcom/common/v3d_macros.h"
 #include "broadcom/cle/v3dx_pack.h"
 #include "broadcom/compiler/v3d_compiler.h"
@@ -108,6 +107,7 @@ swizzled_border_color(const struct v3d_device_info *devinfo,
         }
 }
 
+#if V3D_VERSION < 40
 static uint32_t
 translate_swizzle(unsigned char pipe_swizzle)
 {
@@ -258,6 +258,7 @@ emit_textures(struct vc5_context *vc5, struct vc5_texture_stateobj *stage_tex)
                         emit_one_texture(vc5, stage_tex, i);
         }
 }
+#endif /* V3D_VERSION < 40 */
 
 static uint32_t
 translate_colormask(struct vc5_context *vc5, uint32_t colormask, int rt)
@@ -271,8 +272,39 @@ translate_colormask(struct vc5_context *vc5, uint32_t colormask, int rt)
         return (~colormask) & 0xf;
 }
 
+static void
+emit_rt_blend(struct vc5_context *vc5, struct vc5_job *job,
+              struct pipe_blend_state *blend, int rt)
+{
+        cl_emit(&job->bcl, BLEND_CONFIG, config) {
+                struct pipe_rt_blend_state *rtblend = &blend->rt[rt];
+
+#if V3D_VERSION >= 40
+                config.render_target_mask = 1 << rt;
+#else
+                assert(rt == 0);
+#endif
+
+                config.colour_blend_mode = rtblend->rgb_func;
+                config.colour_blend_dst_factor =
+                        vc5_factor(rtblend->rgb_dst_factor,
+                                   vc5->blend_dst_alpha_one);
+                config.colour_blend_src_factor =
+                        vc5_factor(rtblend->rgb_src_factor,
+                                   vc5->blend_dst_alpha_one);
+
+                config.alpha_blend_mode = rtblend->alpha_func;
+                config.alpha_blend_dst_factor =
+                        vc5_factor(rtblend->alpha_dst_factor,
+                                   vc5->blend_dst_alpha_one);
+                config.alpha_blend_src_factor =
+                        vc5_factor(rtblend->alpha_src_factor,
+                                   vc5->blend_dst_alpha_one);
+        }
+}
+
 void
-vc5_emit_state(struct pipe_context *pctx)
+v3dX(emit_state)(struct pipe_context *pctx)
 {
         struct vc5_context *vc5 = vc5_context(pctx);
         struct vc5_job *job = vc5->job;
@@ -421,24 +453,11 @@ vc5_emit_state(struct pipe_context *pctx)
         if (vc5->dirty & VC5_DIRTY_BLEND && vc5->blend->rt[0].blend_enable) {
                 struct pipe_blend_state *blend = vc5->blend;
 
-                cl_emit(&job->bcl, BLEND_CONFIG, config) {
-                        struct pipe_rt_blend_state *rtblend = &blend->rt[0];
-
-                        config.colour_blend_mode = rtblend->rgb_func;
-                        config.colour_blend_dst_factor =
-                                vc5_factor(rtblend->rgb_dst_factor,
-                                           vc5->blend_dst_alpha_one);
-                        config.colour_blend_src_factor =
-                                vc5_factor(rtblend->rgb_src_factor,
-                                           vc5->blend_dst_alpha_one);
-
-                        config.alpha_blend_mode = rtblend->alpha_func;
-                        config.alpha_blend_dst_factor =
-                                vc5_factor(rtblend->alpha_dst_factor,
-                                           vc5->blend_dst_alpha_one);
-                        config.alpha_blend_src_factor =
-                                vc5_factor(rtblend->alpha_src_factor,
-                                           vc5->blend_dst_alpha_one);
+                if (blend->independent_blend_enable) {
+                        for (int i = 0; i < VC5_MAX_DRAW_BUFFERS; i++)
+                                emit_rt_blend(vc5, job, blend, i);
+                } else {
+                        emit_rt_blend(vc5, job, blend, 0);
                 }
         }
 
@@ -502,11 +521,16 @@ vc5_emit_state(struct pipe_context *pctx)
                 }
         }
 
+#if V3D_VERSION < 40
+        /* Pre-4.x, we have texture state that depends on both the sampler and
+         * the view, so we merge them together at draw time.
+         */
         if (vc5->dirty & VC5_DIRTY_FRAGTEX)
                 emit_textures(vc5, &vc5->fragtex);
 
         if (vc5->dirty & VC5_DIRTY_VERTTEX)
                 emit_textures(vc5, &vc5->verttex);
+#endif
 
         if (vc5->dirty & VC5_DIRTY_FLAT_SHADE_FLAGS) {
                 bool emitted_any = false;
@@ -549,13 +573,22 @@ vc5_emit_state(struct pipe_context *pctx)
                 struct vc5_streamout_stateobj *so = &vc5->streamout;
 
                 if (so->num_targets) {
+#if V3D_VERSION >= 40
+                        cl_emit(&job->bcl, TRANSFORM_FEEDBACK_SPECS, tfe) {
+                                tfe.number_of_16_bit_output_data_specs_following =
+                                        vc5->prog.bind_vs->num_tf_specs;
+                                tfe.enable =
+                                        (vc5->prog.bind_vs->num_tf_specs != 0 &&
+                                         vc5->active_queries);
+                        };
+#else /* V3D_VERSION < 40 */
                         cl_emit(&job->bcl, TRANSFORM_FEEDBACK_ENABLE, tfe) {
                                 tfe.number_of_32_bit_output_buffer_address_following =
                                         so->num_targets;
                                 tfe.number_of_16_bit_output_data_specs_following =
                                         vc5->prog.bind_vs->num_tf_specs;
                         };
-
+#endif /* V3D_VERSION < 40 */
                         for (int i = 0; i < vc5->prog.bind_vs->num_tf_specs; i++) {
                                 cl_emit_prepacked(&job->bcl,
                                                   &vc5->prog.bind_vs->tf_specs[i]);
@@ -567,12 +600,22 @@ vc5_emit_state(struct pipe_context *pctx)
                                 struct vc5_resource *rsc =
                                         vc5_resource(target->buffer);
 
+#if V3D_VERSION >= 40
+                                cl_emit(&job->bcl, TRANSFORM_FEEDBACK_BUFFER, output) {
+                                        output.buffer_address =
+                                                cl_address(rsc->bo,
+                                                           target->buffer_offset);
+                                        output.buffer_size_in_32_bit_words =
+                                                target->buffer_size >> 2;
+                                        output.buffer_number = i;
+                                }
+#else /* V3D_VERSION < 40 */
                                 cl_emit(&job->bcl, TRANSFORM_FEEDBACK_OUTPUT_ADDRESS, output) {
                                         output.address =
                                                 cl_address(rsc->bo,
                                                            target->buffer_offset);
                                 };
-
+#endif /* V3D_VERSION < 40 */
                                 vc5_job_add_write_resource(vc5->job,
                                                            target->buffer);
                                 /* XXX: buffer_size? */
index 1e794bc223f50f115b45322dae3b518dcda7b3e0..b55272edac7d0925088f4e9a4c3e108612ffb2a8 100644 (file)
@@ -102,7 +102,6 @@ vc5_screen_get_param(struct pipe_screen *pscreen, enum pipe_cap param)
         case PIPE_CAP_START_INSTANCE:
         case PIPE_CAP_TGSI_INSTANCEID:
         case PIPE_CAP_SM3:
-        case PIPE_CAP_INDEP_BLEND_ENABLE: /* XXX */
         case PIPE_CAP_TEXTURE_QUERY_LOD:
         case PIPE_CAP_PRIMITIVE_RESTART:
         case PIPE_CAP_GLSL_OPTIMIZE_CONSERVATIVELY:
@@ -116,6 +115,9 @@ vc5_screen_get_param(struct pipe_screen *pscreen, enum pipe_cap param)
         case PIPE_CAP_SIGNED_VERTEX_BUFFER_OFFSET:
                 return 1;
 
+        case PIPE_CAP_INDEP_BLEND_ENABLE:
+                return screen->devinfo.ver >= 40;
+
         case PIPE_CAP_CONSTANT_BUFFER_OFFSET_ALIGNMENT:
                 return 256;