[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

xserver-xorg-video-intel: Changes to 'debian-experimental'



 NEWS                               |   38 
 configure.ac                       |   16 
 debian/changelog                   |    2 
 src/compat-api.h                   |    4 
 src/intel_device.c                 |   99 
 src/intel_driver.h                 |   13 
 src/intel_module.c                 |   44 
 src/legacy/i810/i810_driver.c      |    2 
 src/sna/Makefile.am                |    5 
 src/sna/gen3_render.c              |   70 
 src/sna/gen4_render.c              |   28 
 src/sna/gen4_vertex.c              |   26 
 src/sna/gen4_vertex.h              |    1 
 src/sna/gen5_render.c              |   34 
 src/sna/gen6_render.c              |   48 
 src/sna/gen7_render.c              |   99 
 src/sna/kgem.c                     |   77 
 src/sna/kgem.h                     |    2 
 src/sna/sna.h                      |    1 
 src/sna/sna_accel.c                |   35 
 src/sna/sna_composite.c            |  187 
 src/sna/sna_display.c              |   75 
 src/sna/sna_dri.c                  |   13 
 src/sna/sna_driver.c               |   15 
 src/sna/sna_gradient.c             |    9 
 src/sna/sna_render.c               |    9 
 src/sna/sna_render.h               |    2 
 src/sna/sna_threads.c              |    2 
 src/sna/sna_trapezoids.c           | 7554 ++-----------------------------------
 src/sna/sna_trapezoids.h           |  342 +
 src/sna/sna_trapezoids_boxes.c     | 1461 +++++++
 src/sna/sna_trapezoids_imprecise.c | 3916 +++++++++++++++++++
 src/sna/sna_trapezoids_mono.c      | 1428 ++++++
 src/sna/sna_trapezoids_precise.c   | 3302 ++++++++++++++++
 src/sna/sna_video.c                |   11 
 src/sna/sna_video.h                |    1 
 src/sna/sna_video_hwmc.c           |   12 
 src/sna/sna_video_sprite.c         |    5 
 src/uxa/intel_driver.c             |    2 
 tools/virtual.c                    |    2 
 40 files changed, 11574 insertions(+), 7418 deletions(-)

New commits:
commit 3bfafcdfbdb0de1f041c1b9d358398750a341fe1
Author: Timo Aaltonen <tjaalton@ubuntu.com>
Date:   Wed Oct 9 19:28:49 2013 +0300

    update the changelog

diff --git a/debian/changelog b/debian/changelog
index 0a1167d..2cf0521 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,4 +1,4 @@
-xserver-xorg-video-intel (2:2.99.903-1) UNRELEASED; urgency=low
+xserver-xorg-video-intel (2:2.99.904-1) UNRELEASED; urgency=low
 
   * New upstream prerelease.
 

commit b9ad5b625e8935a3c115760bdd4738d4432542e3
Author: Chris Wilson <chris@chris-wilson.co.uk>
Date:   Wed Oct 9 17:18:43 2013 +0100

    2.99.904 snapshot

diff --git a/NEWS b/NEWS
index 159c67c..3fb057e 100644
--- a/NEWS
+++ b/NEWS
@@ -1,3 +1,41 @@
+Snapshot 2.99.904 (2013-10-09)
+==============================
+There is one more feature planned to be completed for 3.0, so time for a
+snapshot beforehand to push out the bug fixes from the last week.
+
+ * Fix video output using sprites when changing the image size
+
+ * Apply more restrictive tile constaints for 915g class devices
+   https://bugs.launchpad.net/ubuntu/+source/xserver-xorg-video-intel/+bug/1232546
+
+ * Ensure all overlapping rectangles are drawn for XRenderFillRectangles
+   https://bugs.freedesktop.org/show_bug.cgi?id=66313
+
+ * Fix trapezoid clipping against the left-edge
+   https://bugs.freedesktop.org/show_bug.cgi?id=69469
+
+ * Prevent discarding active upload buffers, causing glitches in chromium
+   https://bugs.freedesktop.org/show_bug.cgi?id=66990
+
+ * Prevent specifying a negative timeout to select if the BlockHandler
+   takes too long to update the display
+
+ * Promote the Ironlake pipecontrol to be a full pipeline flush to
+   prevent render cache corruption
+   https://bugs.freedesktop.org/show_bug.cgi?id=51422
+
+ * Never pass an invalid trapezoid to pixman
+   https://bugs.launchpad.net/ubuntu/+source/xorg-server/+bug/1197921
+
+ * Prevent out-of-bounds access by overassigning work amongst threads
+   https://bugs.freedesktop.org/show_bug.cgi?id=70204
+
+ * Make sure the current mode is always listed amongst the output modes
+   https://bugs.freedesktop.org/show_bug.cgi?id=70132
+
+ * Build fixes for 1.14.99.2
+
+
 Snapshot 2.99.903 (2013-09-28)
 ==============================
 Lots more stabilization work, not yet peaceful enough to christen 3.0. We
diff --git a/configure.ac b/configure.ac
index 6445373..b58bb79 100644
--- a/configure.ac
+++ b/configure.ac
@@ -23,7 +23,7 @@
 # Initialize Autoconf
 AC_PREREQ([2.60])
 AC_INIT([xf86-video-intel],
-        [2.99.903],
+        [2.99.904],
         [https://bugs.freedesktop.org/enter_bug.cgi?product=xorg],
         [xf86-video-intel])
 AC_CONFIG_SRCDIR([Makefile.am])

commit d1aa2ac5dddf6b8c8c1333aae415abda9ad72d85
Author: Chris Wilson <chris@chris-wilson.co.uk>
Date:   Wed Oct 9 16:22:59 2013 +0100

    sna: Steal the current mode name
    
    Rather than duplicating a string, we can simply transfer ownership from
    the temporary mode to the mode list.
    
    Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>

diff --git a/src/sna/sna_display.c b/src/sna/sna_display.c
index e893bcd..71c4c60 100644
--- a/src/sna/sna_display.c
+++ b/src/sna/sna_display.c
@@ -2112,7 +2112,8 @@ sna_output_get_modes(xf86OutputPtr output)
 		Mode = calloc(1, sizeof(DisplayModeRec));
 		if (Mode) {
 			*Mode = current;
-			Mode->name = strdup(Mode->name);
+			current.name = NULL;
+
 			output->probed_modes =
 				xf86ModesAdd(output->probed_modes, Mode);
 		}

commit 6fda305e2f2f991b39d09e67d0b17c8c3d50f9a4
Author: Chris Wilson <chris@chris-wilson.co.uk>
Date:   Wed Oct 9 15:59:42 2013 +0100

    sna: Append the current mode to the output list if not found
    
    If for some reason the current mode on the CRTC (inherited most likely
    from fastboot) doesn't match any of the modes reported by the output, we
    end up with a stray mode that the client cannot control.
    
    Reported-by: Jiri Slaby <jirislaby@gmail.com>
    Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=70132
    Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>

diff --git a/src/sna/sna_display.c b/src/sna/sna_display.c
index dddc6d7..e893bcd 100644
--- a/src/sna/sna_display.c
+++ b/src/sna/sna_display.c
@@ -2039,21 +2039,46 @@ sna_output_get_modes(xf86OutputPtr output)
 {
 	struct sna_output *sna_output = output->driver_private;
 	DisplayModePtr Modes = NULL;
+	DisplayModeRec current;
+	bool has_current = false;
 	int i;
 
-	DBG(("%s\n", __FUNCTION__));
+	DBG(("%s(%s)\n", __FUNCTION__, output->name));
 
 	sna_output_attach_edid(output);
 
+	memset(&current, 0, sizeof(current));
+	if (output->crtc) {
+		struct drm_mode_crtc mode;
+
+		VG_CLEAR(mode);
+		mode.crtc_id = to_sna_crtc(output->crtc)->id;
+
+		if (drmIoctl(to_sna(output->scrn)->kgem.fd, DRM_IOCTL_MODE_GETCRTC, &mode) == 0) {
+			DBG(("%s: CRTC:%d, pipe=%d: has mode?=%d\n", __FUNCTION__,
+			     to_sna_crtc(output->crtc)->id,
+			     to_sna_crtc(output->crtc)->pipe,
+			     mode.mode_valid && mode.mode.clock));
+
+			if (mode.mode_valid && mode.mode.clock)
+				mode_from_kmode(output->scrn, &mode.mode, &current);
+		}
+	}
+
 	for (i = 0; i < sna_output->num_modes; i++) {
 		DisplayModePtr Mode;
 
 		Mode = calloc(1, sizeof(DisplayModeRec));
-		if (Mode)
-			Modes = xf86ModesAdd(Modes,
-					     mode_from_kmode(output->scrn,
-							     &sna_output->modes[i],
-							     Mode));
+		if (Mode) {
+			Mode = mode_from_kmode(output->scrn,
+					       &sna_output->modes[i],
+					       Mode);
+
+			if (!has_current && xf86ModesEqual(Mode, &current))
+				has_current = true;
+
+			Modes = xf86ModesAdd(Modes, Mode);
+		}
 	}
 
 	/*
@@ -2081,6 +2106,19 @@ sna_output_get_modes(xf86OutputPtr output)
 		Modes = sna_output_panel_edid(output, Modes);
 	}
 
+	if (!has_current && current.Clock) {
+		DisplayModePtr Mode;
+
+		Mode = calloc(1, sizeof(DisplayModeRec));
+		if (Mode) {
+			*Mode = current;
+			Mode->name = strdup(Mode->name);
+			output->probed_modes =
+				xf86ModesAdd(output->probed_modes, Mode);
+		}
+	}
+	free(current.name);
+
 	return Modes;
 }
 

commit d1cb39d0a86390b7ef704422a5b91f9a012d24a5
Author: Chris Wilson <chris@chris-wilson.co.uk>
Date:   Wed Oct 9 10:32:02 2013 +0100

    sna/gen3+: Flush vertex buffer after computing resize
    
    Upon aligning the buffer, we may enlarge the vbo to accomodate the
    vertex alignment and push the current index past the end of the buffer.
    Move the space check from before the alignment computation to
    afterwards.
    
    Reported-by: Jiri Slaby <jirislaby@gmail.com>
    References: https://bugs.freedesktop.org/show_bug.cgi?id=47597
    Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>

diff --git a/src/sna/gen3_render.c b/src/sna/gen3_render.c
index ebe108d..2445b91 100644
--- a/src/sna/gen3_render.c
+++ b/src/sna/gen3_render.c
@@ -3123,20 +3123,29 @@ static void
 gen3_align_vertex(struct sna *sna,
 		  const struct sna_composite_op *op)
 {
-	if (op->floats_per_vertex != sna->render_state.gen3.last_floats_per_vertex) {
-		if (sna->render.vertex_size - sna->render.vertex_used < 2*op->floats_per_rect)
-			gen3_vertex_finish(sna);
-
-		DBG(("aligning vertex: was %d, now %d floats per vertex, %d->%d\n",
-		     sna->render_state.gen3.last_floats_per_vertex,
-		     op->floats_per_vertex,
-		     sna->render.vertex_index,
-		     (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex));
-		sna->render.vertex_index = (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex;
-		sna->render.vertex_used = sna->render.vertex_index * op->floats_per_vertex;
-		assert(sna->render.vertex_used < sna->render.vertex_size - op->floats_per_rect);
-		sna->render_state.gen3.last_floats_per_vertex = op->floats_per_vertex;
+	int vertex_index;
+
+	if (op->floats_per_vertex == sna->render_state.gen3.last_floats_per_vertex)
+		return;
+
+	DBG(("aligning vertex: was %d, now %d floats per vertex\n",
+	     sna->render_state.gen3.last_floats_per_vertex,
+	     op->floats_per_vertex));
+
+	assert(op->floats_per_rect == 3*op->floats_per_vertex);
+
+	vertex_index = (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex;
+	if ((int)sna->render.vertex_size - vertex_index * op->floats_per_vertex < 2*op->floats_per_rect) {
+		DBG(("%s: flushing vertex buffer: new index=%d, max=%d\n",
+		     __FUNCTION__, vertex_index, sna->render.vertex_size / op->floats_per_vertex));
+		if (gen3_vertex_finish(sna) < op->floats_per_vertex)
+			kgem_submit(&sna->kgem);
+
+		vertex_index = (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex;
 	}
+
+	sna->render.vertex_index = vertex_index;
+	sna->render.vertex_used = vertex_index * op->floats_per_vertex;
 }
 
 static bool
@@ -3806,8 +3815,8 @@ gen3_render_composite(struct sna *sna,
 			goto cleanup_mask;
 	}
 
-	gen3_emit_composite_state(sna, tmp);
 	gen3_align_vertex(sna, tmp);
+	gen3_emit_composite_state(sna, tmp);
 	return true;
 
 cleanup_mask:
@@ -5021,8 +5030,8 @@ gen3_render_composite_spans(struct sna *sna,
 			goto cleanup_src;
 	}
 
-	gen3_emit_composite_state(sna, &tmp->base);
 	gen3_align_vertex(sna, &tmp->base);
+	gen3_emit_composite_state(sna, &tmp->base);
 	return true;
 
 cleanup_src:
@@ -5665,8 +5674,8 @@ fallback_blt:
 	dst_dy += tmp.dst.y;
 	tmp.dst.x = tmp.dst.y = 0;
 
-	gen3_emit_composite_state(sna, &tmp);
 	gen3_align_vertex(sna, &tmp);
+	gen3_emit_composite_state(sna, &tmp);
 
 	do {
 		int n_this_time;
@@ -5803,8 +5812,8 @@ fallback:
 	tmp->blt  = gen3_render_copy_blt;
 	tmp->done = gen3_render_copy_done;
 
-	gen3_emit_composite_state(sna, &tmp->base);
 	gen3_align_vertex(sna, &tmp->base);
+	gen3_emit_composite_state(sna, &tmp->base);
 	return true;
 }
 
@@ -5943,8 +5952,8 @@ gen3_render_fill_boxes(struct sna *sna,
 		assert(kgem_check_bo(&sna->kgem, dst_bo, NULL));
 	}
 
-	gen3_emit_composite_state(sna, &tmp);
 	gen3_align_vertex(sna, &tmp);
+	gen3_emit_composite_state(sna, &tmp);
 
 	do {
 		int n_this_time;
@@ -6094,8 +6103,8 @@ gen3_render_fill(struct sna *sna, uint8_t alu,
 	tmp->boxes = gen3_render_fill_op_boxes;
 	tmp->done  = gen3_render_fill_op_done;
 
-	gen3_emit_composite_state(sna, &tmp->base);
 	gen3_align_vertex(sna, &tmp->base);
+	gen3_emit_composite_state(sna, &tmp->base);
 	return true;
 }
 
@@ -6172,8 +6181,8 @@ gen3_render_fill_one(struct sna *sna, PixmapPtr dst, struct kgem_bo *bo,
 			return true;
 	}
 
-	gen3_emit_composite_state(sna, &tmp);
 	gen3_align_vertex(sna, &tmp);
+	gen3_emit_composite_state(sna, &tmp);
 	gen3_get_rectangles(sna, &tmp, 1);
 	DBG(("	(%d, %d), (%d, %d): %x\n", x1, y1, x2, y2, color));
 	OUT_VERTEX(x2);
diff --git a/src/sna/gen4_render.c b/src/sna/gen4_render.c
index 416452b..48a8852 100644
--- a/src/sna/gen4_render.c
+++ b/src/sna/gen4_render.c
@@ -827,16 +827,10 @@ gen4_align_vertex(struct sna *sna, const struct sna_composite_op *op)
 {
 	assert(op->floats_per_rect == 3*op->floats_per_vertex);
 	if (op->floats_per_vertex != sna->render_state.gen4.floats_per_vertex) {
-		if (sna->render.vertex_size - sna->render.vertex_used < 2*op->floats_per_rect)
-			gen4_vertex_finish(sna);
-
-		DBG(("aligning vertex: was %d, now %d floats per vertex, %d->%d\n",
+		DBG(("aligning vertex: was %d, now %d floats per vertex\n",
 		     sna->render_state.gen4.floats_per_vertex,
-		     op->floats_per_vertex,
-		     sna->render.vertex_index,
-		     (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex));
-		sna->render.vertex_index = (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex;
-		sna->render.vertex_used = sna->render.vertex_index * op->floats_per_vertex;
+		     op->floats_per_vertex));
+		gen4_vertex_align(sna, op);
 		sna->render_state.gen4.floats_per_vertex = op->floats_per_vertex;
 	}
 }
@@ -1396,8 +1390,8 @@ gen4_render_video(struct sna *sna,
 		assert(kgem_check_bo(&sna->kgem, tmp.dst.bo, frame->bo, NULL));
 	}
 
-	gen4_video_bind_surfaces(sna, &tmp);
 	gen4_align_vertex(sna, &tmp);
+	gen4_video_bind_surfaces(sna, &tmp);
 
 	/* Set up the offset for translating from the given region (in screen
 	 * coordinates) to the backing pixmap.
@@ -1987,8 +1981,8 @@ gen4_render_composite(struct sna *sna,
 			goto cleanup_mask;
 	}
 
-	gen4_bind_surfaces(sna, tmp);
 	gen4_align_vertex(sna, tmp);
+	gen4_bind_surfaces(sna, tmp);
 	return true;
 
 cleanup_mask:
@@ -2226,8 +2220,8 @@ gen4_render_composite_spans(struct sna *sna,
 			goto cleanup_src;
 	}
 
-	gen4_bind_surfaces(sna, &tmp->base);
 	gen4_align_vertex(sna, &tmp->base);
+	gen4_bind_surfaces(sna, &tmp->base);
 	return true;
 
 cleanup_src:
@@ -2428,8 +2422,8 @@ fallback_blt:
 	src_dx += tmp.src.offset[0];
 	src_dy += tmp.src.offset[1];
 
-	gen4_copy_bind_surfaces(sna, &tmp);
 	gen4_align_vertex(sna, &tmp);
+	gen4_copy_bind_surfaces(sna, &tmp);
 
 	do {
 		gen4_render_copy_one(sna, &tmp,
@@ -2558,8 +2552,8 @@ fallback:
 			return true;
 	}
 
-	gen4_copy_bind_surfaces(sna, &op->base);
 	gen4_align_vertex(sna, &op->base);
+	gen4_copy_bind_surfaces(sna, &op->base);
 
 	op->blt  = gen4_render_copy_blt;
 	op->done = gen4_render_copy_done;
@@ -2664,8 +2658,8 @@ gen4_render_fill_boxes(struct sna *sna,
 		assert(kgem_check_bo(&sna->kgem, dst_bo, NULL));
 	}
 
-	gen4_bind_surfaces(sna, &tmp);
 	gen4_align_vertex(sna, &tmp);
+	gen4_bind_surfaces(sna, &tmp);
 
 	do {
 		gen4_render_fill_rectangle(sna, &tmp,
@@ -2769,8 +2763,8 @@ gen4_render_fill(struct sna *sna, uint8_t alu,
 		assert(kgem_check_bo(&sna->kgem, dst_bo, NULL));
 	}
 
-	gen4_bind_surfaces(sna, &op->base);
 	gen4_align_vertex(sna, &op->base);
+	gen4_bind_surfaces(sna, &op->base);
 
 	op->blt   = gen4_render_fill_op_blt;
 	op->box   = gen4_render_fill_op_box;
@@ -2853,8 +2847,8 @@ gen4_render_fill_one(struct sna *sna, PixmapPtr dst, struct kgem_bo *bo,
 		}
 	}
 
-	gen4_bind_surfaces(sna, &tmp);
 	gen4_align_vertex(sna, &tmp);
+	gen4_bind_surfaces(sna, &tmp);
 
 	gen4_render_fill_rectangle(sna, &tmp, x1, y1, x2 - x1, y2 - y1);
 
diff --git a/src/sna/gen4_vertex.c b/src/sna/gen4_vertex.c
index e2a4808..0585c4c 100644
--- a/src/sna/gen4_vertex.c
+++ b/src/sna/gen4_vertex.c
@@ -38,6 +38,29 @@
 #define sse2
 #endif
 
+void gen4_vertex_align(struct sna *sna, const struct sna_composite_op *op)
+{
+	int vertex_index;
+
+	assert(op->floats_per_rect == 3*op->floats_per_vertex);
+
+	vertex_index = (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex;
+	if ((int)sna->render.vertex_size - vertex_index * op->floats_per_vertex < 2*op->floats_per_rect) {
+		DBG(("%s: flushing vertex buffer: new index=%d, max=%d\n",
+		     __FUNCTION__, vertex_index, sna->render.vertex_size / op->floats_per_vertex));
+		if (gen4_vertex_finish(sna) < op->floats_per_rect) {
+			kgem_submit(&sna->kgem);
+			_kgem_set_mode(&sna->kgem, KGEM_RENDER);
+		}
+
+		vertex_index = (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex;
+		assert(vertex_index * op->floats_per_vertex <= sna->render.vertex_size);
+	}
+
+	sna->render.vertex_index = vertex_index;
+	sna->render.vertex_used = vertex_index * op->floats_per_vertex;
+}
+
 void gen4_vertex_flush(struct sna *sna)
 {
 	DBG(("%s[%x] = %d\n", __FUNCTION__,
diff --git a/src/sna/gen4_vertex.h b/src/sna/gen4_vertex.h
index 1494ba1..03ba2f8 100644
--- a/src/sna/gen4_vertex.h
+++ b/src/sna/gen4_vertex.h
@@ -6,6 +6,7 @@
 #include "sna.h"
 #include "sna_render.h"
 
+void gen4_vertex_align(struct sna *sna, const struct sna_composite_op *op);
 void gen4_vertex_flush(struct sna *sna);
 int gen4_vertex_finish(struct sna *sna);
 void gen4_vertex_close(struct sna *sna);
diff --git a/src/sna/gen5_render.c b/src/sna/gen5_render.c
index 2bd818a..ca41a9a 100644
--- a/src/sna/gen5_render.c
+++ b/src/sna/gen5_render.c
@@ -796,16 +796,10 @@ gen5_align_vertex(struct sna *sna, const struct sna_composite_op *op)
 {
 	assert(op->floats_per_rect == 3*op->floats_per_vertex);
 	if (op->floats_per_vertex != sna->render_state.gen5.floats_per_vertex) {
-		if (sna->render.vertex_size - sna->render.vertex_used < 2*op->floats_per_rect)
-			gen4_vertex_finish(sna);
-
-		DBG(("aligning vertex: was %d, now %d floats per vertex, %d->%d\n",
+		DBG(("aligning vertex: was %d, now %d floats per vertex\n",
 		     sna->render_state.gen5.floats_per_vertex,
-		     op->floats_per_vertex,
-		     sna->render.vertex_index,
-		     (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex));
-		sna->render.vertex_index = (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex;
-		sna->render.vertex_used = sna->render.vertex_index * op->floats_per_vertex;
+		     op->floats_per_vertex));
+		gen4_vertex_align(sna, op);
 		sna->render_state.gen5.floats_per_vertex = op->floats_per_vertex;
 	}
 }
@@ -1394,8 +1388,8 @@ gen5_render_video(struct sna *sna,
 		assert(kgem_check_bo(&sna->kgem, tmp.dst.bo, frame->bo, NULL));
 	}
 
-	gen5_video_bind_surfaces(sna, &tmp);
 	gen5_align_vertex(sna, &tmp);
+	gen5_video_bind_surfaces(sna, &tmp);
 
 	/* Set up the offset for translating from the given region (in screen
 	 * coordinates) to the backing pixmap.
@@ -1969,8 +1963,8 @@ gen5_render_composite(struct sna *sna,
 			goto cleanup_mask;
 	}
 
-	gen5_bind_surfaces(sna, tmp);
 	gen5_align_vertex(sna, tmp);
+	gen5_bind_surfaces(sna, tmp);
 	return true;
 
 cleanup_mask:
@@ -2198,8 +2192,8 @@ gen5_render_composite_spans(struct sna *sna,
 			goto cleanup_src;
 	}
 
-	gen5_bind_surfaces(sna, &tmp->base);
 	gen5_align_vertex(sna, &tmp->base);
+	gen5_bind_surfaces(sna, &tmp->base);
 	return true;
 
 cleanup_src:
@@ -2388,8 +2382,8 @@ fallback_blt:
 	src_dx += tmp.src.offset[0];
 	src_dy += tmp.src.offset[1];
 
-	gen5_copy_bind_surfaces(sna, &tmp);
 	gen5_align_vertex(sna, &tmp);
+	gen5_copy_bind_surfaces(sna, &tmp);
 
 	do {
 		int n_this_time;
@@ -2553,8 +2547,8 @@ fallback:
 			return true;
 	}
 
-	gen5_copy_bind_surfaces(sna, &op->base);
 	gen5_align_vertex(sna, &op->base);
+	gen5_copy_bind_surfaces(sna, &op->base);
 
 	op->blt  = gen5_render_copy_blt;
 	op->done = gen5_render_copy_done;
@@ -2694,8 +2688,8 @@ gen5_render_fill_boxes(struct sna *sna,
 		assert(kgem_check_bo(&sna->kgem, dst_bo, NULL));
 	}
 
-	gen5_fill_bind_surfaces(sna, &tmp);
 	gen5_align_vertex(sna, &tmp);
+	gen5_fill_bind_surfaces(sna, &tmp);
 
 	do {
 		int n_this_time;
@@ -2864,8 +2858,8 @@ gen5_render_fill(struct sna *sna, uint8_t alu,
 		assert(kgem_check_bo(&sna->kgem, dst_bo, NULL));
 	}
 
-	gen5_fill_bind_surfaces(sna, &op->base);
 	gen5_align_vertex(sna, &op->base);
+	gen5_fill_bind_surfaces(sna, &op->base);
 
 	op->blt   = gen5_render_fill_op_blt;
 	op->box   = gen5_render_fill_op_box;
@@ -2959,8 +2953,8 @@ gen5_render_fill_one(struct sna *sna, PixmapPtr dst, struct kgem_bo *bo,
 		assert(kgem_check_bo(&sna->kgem, bo, NULL));
 	}
 
-	gen5_fill_bind_surfaces(sna, &tmp);
 	gen5_align_vertex(sna, &tmp);
+	gen5_fill_bind_surfaces(sna, &tmp);
 
 	gen5_get_rectangles(sna, &tmp, 1, gen5_fill_bind_surfaces);
 
diff --git a/src/sna/gen6_render.c b/src/sna/gen6_render.c
index e5e07ce..ee1686f 100644
--- a/src/sna/gen6_render.c
+++ b/src/sna/gen6_render.c
@@ -1312,16 +1312,10 @@ gen6_align_vertex(struct sna *sna, const struct sna_composite_op *op)
 {
 	assert (sna->render.vertex_offset == 0);
 	if (op->floats_per_vertex != sna->render_state.gen6.floats_per_vertex) {
-		if (sna->render.vertex_size - sna->render.vertex_used < 2*op->floats_per_rect)
-			gen4_vertex_finish(sna);
-
-		DBG(("aligning vertex: was %d, now %d floats per vertex, %d->%d\n",
+		DBG(("aligning vertex: was %d, now %d floats per vertex\n",
 		     sna->render_state.gen6.floats_per_vertex,
-		     op->floats_per_vertex,
-		     sna->render.vertex_index,
-		     (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex));
-		sna->render.vertex_index = (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex;
-		sna->render.vertex_used = sna->render.vertex_index * op->floats_per_vertex;
+		     op->floats_per_vertex));
+		gen4_vertex_align(sna, op);
 		sna->render_state.gen6.floats_per_vertex = op->floats_per_vertex;
 	}
 	assert((sna->render.vertex_used % op->floats_per_vertex) == 0);
@@ -1649,8 +1643,8 @@ gen6_render_video(struct sna *sna,
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen6_emit_video_state(sna, &tmp);
 	gen6_align_vertex(sna, &tmp);
+	gen6_emit_video_state(sna, &tmp);
 
 	/* Set up the offset for translating from the given region (in screen
 	 * coordinates) to the backing pixmap.
@@ -2399,8 +2393,8 @@ gen6_render_composite(struct sna *sna,
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen6_emit_composite_state(sna, tmp);
 	gen6_align_vertex(sna, tmp);
+	gen6_emit_composite_state(sna, tmp);
 	return true;
 
 cleanup_mask:
@@ -2632,8 +2626,8 @@ gen6_render_composite_spans(struct sna *sna,
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen6_emit_composite_state(sna, &tmp->base);
 	gen6_align_vertex(sna, &tmp->base);
+	gen6_emit_composite_state(sna, &tmp->base);
 	return true;
 
 cleanup_src:
@@ -2916,8 +2910,8 @@ fallback_blt:
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen6_emit_copy_state(sna, &tmp);
 	gen6_align_vertex(sna, &tmp);
+	gen6_emit_copy_state(sna, &tmp);
 
 	do {
 		int16_t *v;
@@ -3075,8 +3069,8 @@ fallback:
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen6_emit_copy_state(sna, &op->base);
 	gen6_align_vertex(sna, &op->base);
+	gen6_emit_copy_state(sna, &op->base);
 
 	op->blt  = gen6_render_copy_blt;
 	op->done = gen6_render_copy_done;
@@ -3241,8 +3235,8 @@ gen6_render_fill_boxes(struct sna *sna,
 		assert(kgem_check_bo(&sna->kgem, dst_bo, NULL));
 	}
 
-	gen6_emit_fill_state(sna, &tmp);
 	gen6_align_vertex(sna, &tmp);
+	gen6_emit_fill_state(sna, &tmp);
 
 	do {
 		int n_this_time;
@@ -3421,8 +3415,8 @@ gen6_render_fill(struct sna *sna, uint8_t alu,
 		assert(kgem_check_bo(&sna->kgem, dst_bo, NULL));
 	}
 
-	gen6_emit_fill_state(sna, &op->base);
 	gen6_align_vertex(sna, &op->base);
+	gen6_emit_fill_state(sna, &op->base);
 
 	op->blt  = gen6_render_op_fill_blt;
 	op->box  = gen6_render_op_fill_box;
@@ -3505,8 +3499,8 @@ gen6_render_fill_one(struct sna *sna, PixmapPtr dst, struct kgem_bo *bo,
 		}
 	}
 
-	gen6_emit_fill_state(sna, &tmp);
 	gen6_align_vertex(sna, &tmp);
+	gen6_emit_fill_state(sna, &tmp);
 
 	gen6_get_rectangles(sna, &tmp, 1, gen6_emit_fill_state);
 
@@ -3592,8 +3586,8 @@ gen6_render_clear(struct sna *sna, PixmapPtr dst, struct kgem_bo *bo)
 		}
 	}
 
-	gen6_emit_fill_state(sna, &tmp);
 	gen6_align_vertex(sna, &tmp);
+	gen6_emit_fill_state(sna, &tmp);
 
 	gen6_get_rectangles(sna, &tmp, 1, gen6_emit_fill_state);
 
diff --git a/src/sna/gen7_render.c b/src/sna/gen7_render.c
index 4b60f53..30e1cc1 100644
--- a/src/sna/gen7_render.c
+++ b/src/sna/gen7_render.c
@@ -1097,36 +1097,48 @@ gen7_emit_state(struct sna *sna,
 		const struct sna_composite_op *op,
 		uint16_t wm_binding_table)
 {
+	bool need_invalidate;
+	bool need_flush;
 	bool need_stall;
 
 	assert(op->dst.bo->exec);
 
-	gen7_emit_cc(sna, GEN7_BLEND(op->u.gen7.flags));
-	gen7_emit_sampler(sna, GEN7_SAMPLER(op->u.gen7.flags));
-	gen7_emit_sf(sna, GEN7_VERTEX(op->u.gen7.flags) >> 2);
-	gen7_emit_wm(sna, GEN7_KERNEL(op->u.gen7.flags));
-	gen7_emit_vertex_elements(sna, op);
+	need_invalidate = kgem_bo_is_dirty(op->src.bo) || kgem_bo_is_dirty(op->mask.bo);
+	if (ALWAYS_INVALIDATE)
+		need_invalidate = true;
 
-	need_stall = gen7_emit_binding_table(sna, wm_binding_table);
+	need_flush = sna->render_state.gen7.emit_flush;
+	if (ALWAYS_FLUSH)
+		need_flush = true;
+
+	need_stall = sna->render_state.gen7.surface_table != wm_binding_table;
 	need_stall &= gen7_emit_drawing_rectangle(sna, op);
 	if (ALWAYS_STALL)
 		need_stall = true;
 
-	if (ALWAYS_INVALIDATE || kgem_bo_is_dirty(op->src.bo) || kgem_bo_is_dirty(op->mask.bo)) {
+	if (need_invalidate) {
 		gen7_emit_pipe_invalidate(sna);
 		kgem_clear_dirty(&sna->kgem);
 		assert(op->dst.bo->exec);
 		kgem_bo_mark_dirty(op->dst.bo);
-		sna->render_state.gen7.emit_flush = false;
+
+		need_flush = false;
 		need_stall = false;
 	}
-	if (ALWAYS_FLUSH || (sna->render_state.gen7.emit_flush && GEN7_READS_DST(op->u.gen7.flags))) {
+	if (need_flush) {
 		gen7_emit_pipe_flush(sna, need_stall);
 		need_stall = false;
 	}
 	if (need_stall)
 		gen7_emit_pipe_stall(sna);
 
+	gen7_emit_cc(sna, GEN7_BLEND(op->u.gen7.flags));
+	gen7_emit_sampler(sna, GEN7_SAMPLER(op->u.gen7.flags));
+	gen7_emit_sf(sna, GEN7_VERTEX(op->u.gen7.flags) >> 2);
+	gen7_emit_wm(sna, GEN7_KERNEL(op->u.gen7.flags));
+	gen7_emit_vertex_elements(sna, op);
+	gen7_emit_binding_table(sna, wm_binding_table);
+
 	sna->render_state.gen7.emit_flush = GEN7_READS_DST(op->u.gen7.flags);
 }
 
@@ -1522,16 +1534,9 @@ static void
 gen7_align_vertex(struct sna *sna, const struct sna_composite_op *op)
 {
 	if (op->floats_per_vertex != sna->render_state.gen7.floats_per_vertex) {
-		if (sna->render.vertex_size - sna->render.vertex_used < 2*op->floats_per_rect)
-			gen4_vertex_finish(sna);
-
-		DBG(("aligning vertex: was %d, now %d floats per vertex, %d->%d\n",
-		     sna->render_state.gen7.floats_per_vertex,
-		     op->floats_per_vertex,
-		     sna->render.vertex_index,
-		     (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex));
-		sna->render.vertex_index = (sna->render.vertex_used + op->floats_per_vertex - 1) / op->floats_per_vertex;
-		sna->render.vertex_used = sna->render.vertex_index * op->floats_per_vertex;
+		DBG(("aligning vertex: was %d, now %d floats per vertex\n",
+		     sna->render_state.gen7.floats_per_vertex, op->floats_per_vertex));
+		gen4_vertex_align(sna, op);
 		sna->render_state.gen7.floats_per_vertex = op->floats_per_vertex;
 	}
 }
@@ -1865,8 +1870,8 @@ gen7_render_video(struct sna *sna,
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen7_emit_video_state(sna, &tmp);
 	gen7_align_vertex(sna, &tmp);
+	gen7_emit_video_state(sna, &tmp);
 
 	/* Set up the offset for translating from the given region (in screen
 	 * coordinates) to the backing pixmap.
@@ -2654,8 +2659,8 @@ gen7_render_composite(struct sna *sna,
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen7_emit_composite_state(sna, tmp);
 	gen7_align_vertex(sna, tmp);
+	gen7_emit_composite_state(sna, tmp);
 	return true;
 
 cleanup_mask:
@@ -2867,8 +2872,8 @@ gen7_render_composite_spans(struct sna *sna,
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen7_emit_composite_state(sna, &tmp->base);
 	gen7_align_vertex(sna, &tmp->base);
+	gen7_emit_composite_state(sna, &tmp->base);
 	return true;
 
 cleanup_src:
@@ -3141,8 +3146,8 @@ fallback_blt:
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen7_emit_copy_state(sna, &tmp);
 	gen7_align_vertex(sna, &tmp);
+	gen7_emit_copy_state(sna, &tmp);
 
 	do {
 		int16_t *v;
@@ -3295,8 +3300,8 @@ fallback:
 		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen7_emit_copy_state(sna, &op->base);
 	gen7_align_vertex(sna, &op->base);
+	gen7_emit_copy_state(sna, &op->base);
 
 	op->blt  = gen7_render_copy_blt;
 	op->done = gen7_render_copy_done;
@@ -3458,10 +3463,11 @@ gen7_render_fill_boxes(struct sna *sna,
 	if (!kgem_check_bo(&sna->kgem, dst_bo, NULL)) {
 		kgem_submit(&sna->kgem);
 		assert(kgem_check_bo(&sna->kgem, dst_bo, NULL));
+		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen7_emit_fill_state(sna, &tmp);
 	gen7_align_vertex(sna, &tmp);
+	gen7_emit_fill_state(sna, &tmp);
 
 	do {
 		int n_this_time;
@@ -3632,10 +3638,11 @@ gen7_render_fill(struct sna *sna, uint8_t alu,
 	if (!kgem_check_bo(&sna->kgem, dst_bo, NULL)) {
 		kgem_submit(&sna->kgem);
 		assert(kgem_check_bo(&sna->kgem, dst_bo, NULL));
+		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen7_emit_fill_state(sna, &op->base);
 	gen7_align_vertex(sna, &op->base);
+	gen7_emit_fill_state(sna, &op->base);
 
 	op->blt   = gen7_render_fill_op_blt;
 	op->box   = gen7_render_fill_op_box;
@@ -3713,10 +3720,11 @@ gen7_render_fill_one(struct sna *sna, PixmapPtr dst, struct kgem_bo *bo,
 			kgem_bo_destroy(&sna->kgem, tmp.src.bo);
 			return false;
 		}
+		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen7_emit_fill_state(sna, &tmp);
 	gen7_align_vertex(sna, &tmp);
+	gen7_emit_fill_state(sna, &tmp);
 
 	gen7_get_rectangles(sna, &tmp, 1, gen7_emit_fill_state);
 
@@ -3797,10 +3805,11 @@ gen7_render_clear(struct sna *sna, PixmapPtr dst, struct kgem_bo *bo)
 			kgem_bo_destroy(&sna->kgem, tmp.src.bo);
 			return false;
 		}
+		_kgem_set_mode(&sna->kgem, KGEM_RENDER);
 	}
 
-	gen7_emit_fill_state(sna, &tmp);
 	gen7_align_vertex(sna, &tmp);
+	gen7_emit_fill_state(sna, &tmp);
 
 	gen7_get_rectangles(sna, &tmp, 1, gen7_emit_fill_state);
 

commit 38333443b804b9ac6517a7998551b229dc4d5c6c
Author: Chris Wilson <chris@chris-wilson.co.uk>
Date:   Tue Oct 8 16:12:06 2013 +0100

    sna: Emit DBG for when we fallback to xf86InitialConfig detection
    
    Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>

diff --git a/src/sna/sna_display.c b/src/sna/sna_display.c
index 95ce1b0..dddc6d7 100644
--- a/src/sna/sna_display.c
+++ b/src/sna/sna_display.c
@@ -3127,8 +3127,10 @@ static bool sna_probe_initial_configuration(struct sna *sna)
 
 	assert((sna->flags & SNA_IS_HOSTED) == 0);
 
-	if (xf86ReturnOptValBool(sna->Options, OPTION_REPROBE, FALSE))
+	if (xf86ReturnOptValBool(sna->Options, OPTION_REPROBE, FALSE)) {
+		DBG(("%s: user requests reprobing\n", __FUNCTION__));
 		return false;
+	}
 
 	/* First scan through all outputs and look for user overrides */
 	for (i = 0; i < config->num_output; i++) {
@@ -3239,6 +3241,8 @@ static bool sna_probe_initial_configuration(struct sna *sna)
 
 		if (j == config->num_crtc) {
 			/* Can not find the earlier associated CRTC, bail */
+			DBG(("%s: existing setup conflicts with output assignment (Zaphod), reprobing\n",
+			     __FUNCTION__));
 			return false;
 		}
 	}
@@ -3273,6 +3277,7 @@ static bool sna_probe_initial_configuration(struct sna *sna)
 	scrn->virtualY = height;
 
 	xf86SetScrnInfoModes(sna->scrn);
+	DBG(("%s: SetScrnInfoModes = %p\n", __FUNCTION__, scrn->modes));
 	return scrn->modes != NULL;
 }
 

commit 082c08789cf9a8c0cc2bf44d0fee579b96c0798f
Author: Chris Wilson <chris@chris-wilson.co.uk>
Date:   Tue Oct 8 09:40:34 2013 +0100

    sna: Rework the num_threads refinement to avoid the division
    
    We can replace the division by a multiplication.
    
    Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>

diff --git a/src/sna/sna_threads.c b/src/sna/sna_threads.c
index 3e10e5a..333b7eb 100644
--- a/src/sna/sna_threads.c
+++ b/src/sna/sna_threads.c
@@ -274,7 +274,7 @@ void sna_image_composite(pixman_op_t        op,
 
 		y = dst_y;
 		dy = (height + num_threads - 1) / num_threads;
-		num_threads = (height + dy - 1) / dy;
+		num_threads -= (num_threads-1) * dy >= height;
 
 		data[0].op = op;
 		data[0].src = src;
diff --git a/src/sna/sna_trapezoids.c b/src/sna/sna_trapezoids.c
index 8827b9c..f14a67c 100644
--- a/src/sna/sna_trapezoids.c
+++ b/src/sna/sna_trapezoids.c
@@ -390,7 +390,7 @@ trapezoids_fallback(struct sna *sna,
 


Reply to: