summaryrefslogtreecommitdiff
path: root/src/mesa/drivers/dri/i965/brw_state_upload.c
diff options
context:
space:
mode:
authorKenneth Graunke <kenneth@whitecape.org>2015-12-07 20:18:42 -0800
committerKenneth Graunke <kenneth@whitecape.org>2015-12-22 17:22:11 -0800
commit794eb9d7270456ab3d2cadbaf302192eca7f4dbc (patch)
tree6c2d552a6b09f29b8a07ed2ffba290d67350e56f /src/mesa/drivers/dri/i965/brw_state_upload.c
parent01b1b44d31adde3954d1f1404ca66f90d87d4ae5 (diff)
i965: Handle mix-and-match TCS/TES with separate shader objects.
GL_ARB_separate_shader_objects allows the application to mix-and-match TCS and TES programs separately. This means that the interface between the two stages isn't known until the final SSO pipeline is in place. This isn't a great match for our hardware: the TCS and TES have to agree on the Patch URB entry layout. Since we store data as per-patch slots followed by per-vertex slots, changing the number of per-patch slots can significantly alter the layout. This can easily happen with SSO. To handle this, we store the [Patch]OutputsWritten and [Patch]InputsRead bitfields in the TCS/TES program keys, introducing program recompiles. brw_upload_programs() decides the layout for both TCS and TES, and passes it to brw_upload_tcs/tes(), which store it in the key. When creating the NIR for a shader specialization, we override nir->info.inputs_read (and friends) to the program key's values. Since everything uses those, no further compiler changes are needed. This also replaces the hack in brw_create_nir(). To avoid recompiles, brw_precompile_tes() looks to see if there's a TCS in the linked shader. If so, it accounts for the TCS outputs, just as brw_upload_programs() would. This eliminates all recompiles in the non-SSO case. In the SSO case, there should only be recompiles when using a TCS and TES that have different input/output interfaces. Fixes Piglit's mix-and-match-tcs-tes test. v2: Pull the brw_upload_programs code into a brw_upload_tess_programs() helper function (requested by Jordan Justen). Signed-off-by: Kenneth Graunke <kenneth@whitecape.org> Reviewed-by: Jordan Justen <jordan.l.justen@intel.com>
Diffstat (limited to 'src/mesa/drivers/dri/i965/brw_state_upload.c')
-rw-r--r--src/mesa/drivers/dri/i965/brw_state_upload.c38
1 files changed, 29 insertions, 9 deletions
diff --git a/src/mesa/drivers/dri/i965/brw_state_upload.c b/src/mesa/drivers/dri/i965/brw_state_upload.c
index eb0357b755..81a67d284e 100644
--- a/src/mesa/drivers/dri/i965/brw_state_upload.c
+++ b/src/mesa/drivers/dri/i965/brw_state_upload.c
@@ -674,20 +674,40 @@ brw_print_dirty_count(struct dirty_bit_map *bit_map)
}
static inline void
+brw_upload_tess_programs(struct brw_context *brw)
+{
+ if (brw->tess_eval_program) {
+ uint64_t per_vertex_slots = brw->tess_eval_program->Base.InputsRead;
+ uint32_t per_patch_slots =
+ brw->tess_eval_program->Base.PatchInputsRead;
+
+ /* The TCS may have additional outputs which aren't read by the
+ * TES (possibly for cross-thread communication). These need to
+ * be stored in the Patch URB Entry as well.
+ */
+ if (brw->tess_ctrl_program) {
+ per_vertex_slots |= brw->tess_ctrl_program->Base.OutputsWritten;
+ per_patch_slots |=
+ brw->tess_ctrl_program->Base.PatchOutputsWritten;
+ }
+
+ brw_upload_tcs_prog(brw, per_vertex_slots, per_patch_slots);
+ brw_upload_tes_prog(brw, per_vertex_slots, per_patch_slots);
+ } else {
+ brw->tcs.prog_data = NULL;
+ brw->tcs.base.prog_data = NULL;
+ brw->tes.prog_data = NULL;
+ brw->tes.base.prog_data = NULL;
+ }
+}
+
+static inline void
brw_upload_programs(struct brw_context *brw,
enum brw_pipeline pipeline)
{
if (pipeline == BRW_RENDER_PIPELINE) {
brw_upload_vs_prog(brw);
- if (brw->tess_eval_program) {
- brw_upload_tcs_prog(brw);
- brw_upload_tes_prog(brw);
- } else {
- brw->tcs.prog_data = NULL;
- brw->tcs.base.prog_data = NULL;
- brw->tes.prog_data = NULL;
- brw->tes.base.prog_data = NULL;
- }
+ brw_upload_tess_programs(brw);
if (brw->gen < 6)
brw_upload_ff_gs_prog(brw);