summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/mesa/drivers/dri/i965/brw_defines.h1
-rw-r--r--src/mesa/drivers/dri/i965/gen7_gs_state.c28
2 files changed, 29 insertions, 0 deletions
diff --git a/src/mesa/drivers/dri/i965/brw_defines.h b/src/mesa/drivers/dri/i965/brw_defines.h
index c1e7f31fe8b..5ba9d45c9e8 100644
--- a/src/mesa/drivers/dri/i965/brw_defines.h
+++ b/src/mesa/drivers/dri/i965/brw_defines.h
@@ -1381,6 +1381,7 @@ enum brw_message_target {
# define GEN6_GS_SO_STATISTICS_ENABLE (1 << 9)
# define GEN6_GS_RENDERING_ENABLE (1 << 8)
# define GEN7_GS_INCLUDE_PRIMITIVE_ID (1 << 4)
+# define GEN7_GS_REORDER_TRAILING (1 << 2)
# define GEN7_GS_ENABLE (1 << 0)
/* DW6 */
# define HSW_GS_CONTROL_DATA_FORMAT_SHIFT 31
diff --git a/src/mesa/drivers/dri/i965/gen7_gs_state.c b/src/mesa/drivers/dri/i965/gen7_gs_state.c
index 3dd5896eee8..c272b7d8b57 100644
--- a/src/mesa/drivers/dri/i965/gen7_gs_state.c
+++ b/src/mesa/drivers/dri/i965/gen7_gs_state.c
@@ -105,6 +105,33 @@ upload_gs_state(struct brw_context *brw)
(0 << GEN6_GS_URB_ENTRY_READ_OFFSET_SHIFT) |
(prog_data->dispatch_grf_start_reg <<
GEN6_GS_DISPATCH_START_GRF_SHIFT);
+
+ /* Note: the meaning of the GEN7_GS_REORDER_TRAILING bit changes between
+ * Ivy Bridge and Haswell.
+ *
+ * On Ivy Bridge, setting this bit causes the vertices of a triangle
+ * strip to be delivered to the geometry shader in an order that does
+ * not strictly follow the OpenGL spec, but preserves triangle
+ * orientation. For example, if the vertices are (1, 2, 3, 4, 5), then
+ * the geometry shader sees triangles:
+ *
+ * (1, 2, 3), (2, 4, 3), (3, 4, 5)
+ *
+ * (Clearing the bit is even worse, because it fails to preserve
+ * orientation).
+ *
+ * Triangle strips with adjacency always ordered in a way that preserves
+ * triangle orientation but does not strictly follow the OpenGL spec,
+ * regardless of the setting of this bit.
+ *
+ * On Haswell, both triangle strips and triangle strips with adjacency
+ * are always ordered in a way that preserves triangle orientation.
+ * Setting this bit causes the ordering to strictly follow the OpenGL
+ * spec.
+ *
+ * So in either case we want to set the bit. Unfortunately on Ivy
+ * Bridge this will get the order close to correct but not perfect.
+ */
uint32_t dw5 =
((brw->max_gs_threads - 1) << max_threads_shift) |
(brw->gs.prog_data->control_data_header_size_hwords <<
@@ -113,6 +140,7 @@ upload_gs_state(struct brw_context *brw)
GEN6_GS_STATISTICS_ENABLE |
(brw->gs.prog_data->include_primitive_id ?
GEN7_GS_INCLUDE_PRIMITIVE_ID : 0) |
+ GEN7_GS_REORDER_TRAILING |
GEN7_GS_ENABLE;
uint32_t dw6 = 0;