xf86-video-intel: Branch 'projective-965' - 21 commits - configure.ac man/intel.man src/exa_sf.g4a src/exa_sf_prog.h src/exa_wm_nomask.g4a src/exa_wm_nomask_prog.h src/i810_reg.h src/i830_bios.c src/i830_crt.c src/i830_display.c src/i830_dri.c src/i830_driver.c src/i830_dvo.c src/i830_lvds.c src/i830_memory.c src/i830_sdvo.c src/i830_tv.c src/i830_video.c src/i830_xaa.c src/i915_hwmc.c src/i965_render.c src/reg_dumper/idle.c src/xvmc/i915_xvmc.c src/xvmc/intel_batchbuffer.c src/xvmc/intel_xvmc.c src/xvmc/intel_xvmc.h src/xvmc/xf86dri.c src/xvmc/xf86dri.h

Keith Packard keithp at kemper.freedesktop.org
Sun Mar 30 18:07:14 PDT 2008


Rebased ref, commits from common ancestor:
commit 6304b38423f99190a5e54f1a7dcaa75adfad4f2a
Author: Keith Packard <keithp at keithp.com>
Date:   Sun Mar 30 00:54:51 2008 -0700

    Reimplement wm program for nomask case to handle affine transforms
    
    This involves correctly computing u/v locations based on x/y vectors and
    line constants computed in new sf program.
    
    Also, use fewer instructions to make this go a bit faster (2X for 500x500
    composite).

diff --git a/src/exa_wm_nomask.g4a b/src/exa_wm_nomask.g4a
index f92dc1a..97426ec 100644
--- a/src/exa_wm_nomask.g4a
+++ b/src/exa_wm_nomask.g4a
@@ -40,75 +40,49 @@
  * Y1_R is g7
  */
 
-    /* Set up ss0.x coordinates*/
-mov (1) g4<1>F g1.8<0,1,0>UW { align1 };
-add (1) g4.4<1>F g1.8<0,1,0>UW 1UB { align1 };
-mov (1) g4.8<1>F g1.8<0,1,0>UW { align1 };
-add (1) g4.12<1>F g1.8<0,1,0>UW 1UB { align1 };
-    /* Set up ss0.y coordinates */
-mov (1) g6<1>F g1.10<0,1,0>UW { align1 };
-mov (1) g6.4<1>F g1.10<0,1,0>UW { align1 };
-add (1) g6.8<1>F g1.10<0,1,0>UW 1UB { align1 };
-add (1) g6.12<1>F g1.10<0,1,0>UW 1UB { align1 };
-    /* set up ss1.x coordinates */
-mov (1) g4.16<1>F g1.12<0,1,0>UW { align1 };
-add (1) g4.20<1>F g1.12<0,1,0>UW 1UB { align1 };
-mov (1) g4.24<1>F g1.12<0,1,0>UW { align1 };
-add (1) g4.28<1>F g1.12<0,1,0>UW 1UB { align1 };
-    /* set up ss1.y coordinates */
-mov (1) g6.16<1>F g1.14<0,1,0>UW { align1 };
-mov (1) g6.20<1>F g1.14<0,1,0>UW { align1 };
-add (1) g6.24<1>F g1.14<0,1,0>UW 1UB { align1 };
-add (1) g6.28<1>F g1.14<0,1,0>UW 1UB { align1 };
-    /* Set up ss2.x coordinates */
-mov (1) g5<1>F g1.16<0,1,0>UW { align1 };
-add (1) g5.4<1>F g1.16<0,1,0>UW 1UB { align1 };
-mov (1) g5.8<1>F g1.16<0,1,0>UW { align1 };
-add (1) g5.12<1>F g1.16<0,1,0>UW 1UB { align1 };
-    /* Set up ss2.y coordinates */
-mov (1) g7<1>F g1.18<0,1,0>UW { align1 };
-mov (1) g7.4<1>F g1.18<0,1,0>UW { align1 };
-add (1) g7.8<1>F g1.18<0,1,0>UW 1UB { align1 };
-add (1) g7.12<1>F g1.18<0,1,0>UW 1UB { align1 };
-    /* Set up ss3.x coordinates */
-mov (1) g5.16<1>F g1.20<0,1,0>UW { align1 };
-add (1) g5.20<1>F g1.20<0,1,0>UW 1UB { align1 };
-mov (1) g5.24<1>F g1.20<0,1,0>UW { align1 };
-add (1) g5.28<1>F g1.20<0,1,0>UW 1UB { align1 };
-    /* Set up ss3.y coordinates */
-mov (1) g7.16<1>F g1.22<0,1,0>UW { align1 };
-mov (1) g7.20<1>F g1.22<0,1,0>UW { align1 };
-add (1) g7.24<1>F g1.22<0,1,0>UW 1UB { align1 };
-add (1) g7.28<1>F g1.22<0,1,0>UW 1UB { align1 };
+
+/* Load X and Y coordinates and compute per-pixel coordinates */
+add (16)	g4<1>UW		g1.8<2,4,0>UW	0x10101010V	{ align1 };
+add (16)	g6<1>UW		g1.10<2,4,0>UW	0x11001100V	{ align1 };
 
     /* Now, map these screen space coordinates into texture coordinates. */
+    
     /* subtract screen-space X origin of vertex 0. */
-add (8) g4<1>F g4<8,8,1>F -g1<0,1,0>F { align1 };
-add (8) g5<1>F g5<8,8,1>F -g1<0,1,0>F { align1 };
-    /* scale by texture X increment */
-mul (8) g4<1>F g4<8,8,1>F g3<0,1,0>F { align1 };
-mul (8) g5<1>F g5<8,8,1>F g3<0,1,0>F { align1 };
-    /* add in texture X offset */
-add (8) g4<1>F g4<8,8,1>F g3.12<0,1,0>F { align1 };
-add (8) g5<1>F g5<8,8,1>F g3.12<0,1,0>F { align1 };
+add (16)	g12<1>F		g4<8,8,1>UW	-g1.0<0,1,0>F { compr align1 };
+
     /* subtract screen-space Y origin of vertex 0. */
-add (8) g6<1>F g6<8,8,1>F -g1.4<0,1,0>F { align1 };
-add (8) g7<1>F g7<8,8,1>F -g1.4<0,1,0>F { align1 };
-    /* scale by texture Y increment */
-mul (8) g6<1>F g6<8,8,1>F g3.20<0,1,0>F { align1 };
-mul (8) g7<1>F g7<8,8,1>F g3.20<0,1,0>F { align1 };
-    /* add in texture Y offset */
-add (8) g6<1>F g6<8,8,1>F g3.28<0,1,0>F { align1 };
-add (8) g7<1>F g7<8,8,1>F g3.28<0,1,0>F { align1 };
+add (16)	g16<1>F		g6<8,8,1>UW	-g1.4<0,1,0>F { compr align1 };
+
+	/* g8/g9 = X * du/dx */
+mul (16)	g8<1>F		g12<8,8,1>F	g3.0<0,1,0>F { compr align1 };
+
+	/* g10/g11 = Y * du/dy */
+mul (16)	g10<1>F		g16<8,8,1>F	g3.4<0,1,0>F { compr align1 };
+
+	/* g8/g9 = X du/dx + Y du/dy */
+add (16)	g8<1>F		g8<8,8,1>F	g10<8,8,1>F { compr align1 };
+
+	/* m1/m2 = g8/g9 + uo */
+add (16)	m1<1>F		g8<8,8,1>F	g3.12<0,1,0>F { compr align1 };
+
+
+	/* g8/g9 = X * dv/dx */
+mul (16)	g8<1>F		g12<8,8,1>F	g3.16<0,1,0>F { compr align1 };
+
+	/* g10/g11 = Y * du/dy */
+mul (16)	g10<1>F		g16<8,8,1>F	g3.20<0,1,0>F { compr align1 };
+
+	/* g8/g9 = X du/dx + Y du/dy */
+add (16)	g8<1>F		g8<8,8,1>F	g10<8,8,1>F { compr align1 };
+
+	/* m3/m4 = g8/g9 + vo */
+add (16)	m3<1>F		g8<8,8,1>F	g3.28<0,1,0>F { compr align1 };
+
 
 /* prepare sampler read back gX register, which would be written back to output */
 
 /* use simd16 sampler, param 0 is u, param 1 is v. */
 /* 'payload' loading, assuming tex coord start from g4 */
-mov (8) m1<1>F g4<8,8,1>F { align1 };
-mov (8) m2<1>F g5<8,8,1>F { align1 };  /* param 0 u in m1, m2 */
-mov (8) m3<1>F g6<8,8,1>F { align1 };
-mov (8) m4<1>F g7<8,8,1>F { align1 };  /* param 1 v in m3, m4 */
 
 /* m0 will be copied with g0, as it contains send desc */
 /* emit sampler 'send' cmd */
diff --git a/src/exa_wm_nomask_prog.h b/src/exa_wm_nomask_prog.h
index 7870b3b..c73bdbc 100644
--- a/src/exa_wm_nomask_prog.h
+++ b/src/exa_wm_nomask_prog.h
@@ -1,51 +1,15 @@
-   { 0x00000001, 0x2080013d, 0x00000028, 0x00000000 },
-   { 0x00000040, 0x20840d3d, 0x00000028, 0x00000001 },
-   { 0x00000001, 0x2088013d, 0x00000028, 0x00000000 },
-   { 0x00000040, 0x208c0d3d, 0x00000028, 0x00000001 },
-   { 0x00000001, 0x20c0013d, 0x0000002a, 0x00000000 },
-   { 0x00000001, 0x20c4013d, 0x0000002a, 0x00000000 },
-   { 0x00000040, 0x20c80d3d, 0x0000002a, 0x00000001 },
-   { 0x00000040, 0x20cc0d3d, 0x0000002a, 0x00000001 },
-   { 0x00000001, 0x2090013d, 0x0000002c, 0x00000000 },
-   { 0x00000040, 0x20940d3d, 0x0000002c, 0x00000001 },
-   { 0x00000001, 0x2098013d, 0x0000002c, 0x00000000 },
-   { 0x00000040, 0x209c0d3d, 0x0000002c, 0x00000001 },
-   { 0x00000001, 0x20d0013d, 0x0000002e, 0x00000000 },
-   { 0x00000001, 0x20d4013d, 0x0000002e, 0x00000000 },
-   { 0x00000040, 0x20d80d3d, 0x0000002e, 0x00000001 },
-   { 0x00000040, 0x20dc0d3d, 0x0000002e, 0x00000001 },
-   { 0x00000001, 0x20a0013d, 0x00000030, 0x00000000 },
-   { 0x00000040, 0x20a40d3d, 0x00000030, 0x00000001 },
-   { 0x00000001, 0x20a8013d, 0x00000030, 0x00000000 },
-   { 0x00000040, 0x20ac0d3d, 0x00000030, 0x00000001 },
-   { 0x00000001, 0x20e0013d, 0x00000032, 0x00000000 },
-   { 0x00000001, 0x20e4013d, 0x00000032, 0x00000000 },
-   { 0x00000040, 0x20e80d3d, 0x00000032, 0x00000001 },
-   { 0x00000040, 0x20ec0d3d, 0x00000032, 0x00000001 },
-   { 0x00000001, 0x20b0013d, 0x00000034, 0x00000000 },
-   { 0x00000040, 0x20b40d3d, 0x00000034, 0x00000001 },
-   { 0x00000001, 0x20b8013d, 0x00000034, 0x00000000 },
-   { 0x00000040, 0x20bc0d3d, 0x00000034, 0x00000001 },
-   { 0x00000001, 0x20f0013d, 0x00000036, 0x00000000 },
-   { 0x00000001, 0x20f4013d, 0x00000036, 0x00000000 },
-   { 0x00000040, 0x20f80d3d, 0x00000036, 0x00000001 },
-   { 0x00000040, 0x20fc0d3d, 0x00000036, 0x00000001 },
-   { 0x00600040, 0x208077bd, 0x008d0080, 0x00004020 },
-   { 0x00600040, 0x20a077bd, 0x008d00a0, 0x00004020 },
-   { 0x00600041, 0x208077bd, 0x008d0080, 0x00000060 },
-   { 0x00600041, 0x20a077bd, 0x008d00a0, 0x00000060 },
-   { 0x00600040, 0x208077bd, 0x008d0080, 0x0000006c },
-   { 0x00600040, 0x20a077bd, 0x008d00a0, 0x0000006c },
-   { 0x00600040, 0x20c077bd, 0x008d00c0, 0x00004024 },
-   { 0x00600040, 0x20e077bd, 0x008d00e0, 0x00004024 },
-   { 0x00600041, 0x20c077bd, 0x008d00c0, 0x00000074 },
-   { 0x00600041, 0x20e077bd, 0x008d00e0, 0x00000074 },
-   { 0x00600040, 0x20c077bd, 0x008d00c0, 0x0000007c },
-   { 0x00600040, 0x20e077bd, 0x008d00e0, 0x0000007c },
-   { 0x00600001, 0x202003be, 0x008d0080, 0x00000000 },
-   { 0x00600001, 0x204003be, 0x008d00a0, 0x00000000 },
-   { 0x00600001, 0x206003be, 0x008d00c0, 0x00000000 },
-   { 0x00600001, 0x208003be, 0x008d00e0, 0x00000000 },
+   { 0x00800040, 0x20806d29, 0x00480028, 0x10101010 },
+   { 0x00800040, 0x20c06d29, 0x0048002a, 0x11001100 },
+   { 0x00802040, 0x2180753d, 0x008d0080, 0x00004020 },
+   { 0x00802040, 0x2200753d, 0x008d00c0, 0x00004024 },
+   { 0x00802041, 0x210077bd, 0x008d0180, 0x00000060 },
+   { 0x00802041, 0x214077bd, 0x008d0200, 0x00000064 },
+   { 0x00802040, 0x210077bd, 0x008d0100, 0x008d0140 },
+   { 0x00802040, 0x202077be, 0x008d0100, 0x0000006c },
+   { 0x00802041, 0x210077bd, 0x008d0180, 0x00000070 },
+   { 0x00802041, 0x214077bd, 0x008d0200, 0x00000074 },
+   { 0x00802040, 0x210077bd, 0x008d0100, 0x008d0140 },
+   { 0x00802040, 0x206077be, 0x008d0100, 0x0000007c },
    { 0x00800031, 0x21801d29, 0x008d0000, 0x02580001 },
    { 0x00600001, 0x22600021, 0x008d0260, 0x00000000 },
    { 0x00600001, 0x202003be, 0x008d0020, 0x00000000 },
diff --git a/src/i965_render.c b/src/i965_render.c
index 93583b0..26c06aa 100644
--- a/src/i965_render.c
+++ b/src/i965_render.c
@@ -318,7 +318,7 @@ static const uint32_t sip_kernel_static[][4] = {
  */
 
 #define SF_KERNEL_NUM_GRF  16
-#define SF_MAX_THREADS	   1
+#define SF_MAX_THREADS	   2
 
 static const uint32_t sf_kernel_static[][4] = {
 #include "exa_sf_prog.h"
@@ -328,10 +328,6 @@ static const uint32_t sf_kernel_static_mask[][4] = {
 #include "exa_sf_mask_prog.h"
 };
 
-static const uint32_t sf_kernel_static_rotation[][4] = {
-#include "exa_sf_rotation_prog.h"
-};
-
 /* ps kernels */
 #define PS_KERNEL_NUM_GRF   32
 #define PS_MAX_THREADS	   32
@@ -352,10 +348,6 @@ static const uint32_t ps_kernel_static_masknoca [][4] = {
 #include "exa_wm_masknoca_prog.h"
 };
 
-static const uint32_t ps_kernel_static_rotation [][4] = {
-#include "exa_wm_rotation_prog.h"
-};
-
 static uint32_t 
 i965_get_card_format(PicturePtr pPict)
 {
@@ -370,21 +362,6 @@ i965_get_card_format(PicturePtr pPict)
     return i965_tex_formats[i].card_fmt;
 }
 
-static Bool
-i965_check_rotation_transform(PictTransformPtr t)
-{
-    /* XXX this is arbitrary */
-    int a, b;
-    a = xFixedToInt(t->matrix[0][1]);
-    b = xFixedToInt(t->matrix[1][0]);
-    if (a == -1 && b == 1)
-	return TRUE;
-    else if (a == 1 && b == -1)
-	return TRUE;
-    else
-	return FALSE;
-}
-
 Bool
 i965_prepare_composite(int op, PicturePtr pSrcPicture,
 		       PicturePtr pMaskPicture, PicturePtr pDstPicture,
@@ -397,7 +374,6 @@ i965_prepare_composite(int op, PicturePtr pSrcPicture,
 	mask_tiled = 0;
     uint32_t dst_format, dst_offset, dst_pitch, dst_tile_format = 0,
 	dst_tiled = 0;
-    Bool rotation_program = FALSE;
 
     IntelEmitInvarientState(pScrn);
     *pI830->last_3d = LAST_3D_RENDER;
@@ -431,9 +407,6 @@ i965_prepare_composite(int op, PicturePtr pSrcPicture,
 	pI830->transform[1] = NULL;
 	pI830->scale_units[1][0] = -1;
 	pI830->scale_units[1][1] = -1;
-	if (pI830->transform[0] && 
-		i965_check_rotation_transform(pI830->transform[0]))
-	    rotation_program = TRUE;
     } else {
 	pI830->transform[1] = pMaskPicture->transform;
 	if (pI830->transform[1])
@@ -469,8 +442,6 @@ i965_prepare_composite(int op, PicturePtr pSrcPicture,
     sf_kernel_offset = ALIGN(next_offset, 64);
     if (pMask)
 	next_offset = sf_kernel_offset + sizeof (sf_kernel_static_mask);
-    else if (rotation_program)
-	next_offset = sf_kernel_offset + sizeof (sf_kernel_static_rotation);
     else 
 	next_offset = sf_kernel_offset + sizeof (sf_kernel_static);
 
@@ -488,8 +459,6 @@ i965_prepare_composite(int op, PicturePtr pSrcPicture,
         } else
 	    next_offset = ps_kernel_offset + 
                           sizeof(ps_kernel_static_masknoca);
-    } else if (rotation_program) {
-   	next_offset = ps_kernel_offset + sizeof (ps_kernel_static_rotation);
     } else {
    	next_offset = ps_kernel_offset + sizeof (ps_kernel_static_nomask);
     }
@@ -816,9 +785,6 @@ i965_prepare_composite(int op, PicturePtr pSrcPicture,
     if (pMask)
 	memcpy(sf_kernel, sf_kernel_static_mask,
 		sizeof (sf_kernel_static_mask));
-    else if (rotation_program)
-	memcpy(sf_kernel, sf_kernel_static_rotation, 
-		sizeof (sf_kernel_static_rotation));
     else
 	memcpy(sf_kernel, sf_kernel_static, sizeof (sf_kernel_static));
 
@@ -870,9 +836,6 @@ i965_prepare_composite(int op, PicturePtr pSrcPicture,
         } else
    	    memcpy(ps_kernel, ps_kernel_static_masknoca,
 		   sizeof (ps_kernel_static_masknoca));
-    } else if (rotation_program) {
-   	memcpy(ps_kernel, ps_kernel_static_rotation,
-	       sizeof (ps_kernel_static_rotation));
     } else {
    	memcpy(ps_kernel, ps_kernel_static_nomask,
 	       sizeof (ps_kernel_static_nomask));
@@ -883,7 +846,7 @@ i965_prepare_composite(int op, PicturePtr pSrcPicture,
     wm_state->thread0.kernel_start_pointer =
 	(state_base_offset + ps_kernel_offset) >> 6;
     wm_state->thread0.grf_reg_count = BRW_GRF_BLOCKS(PS_KERNEL_NUM_GRF);
-    wm_state->thread1.single_program_flow = 1;
+    wm_state->thread1.single_program_flow = 0;
     if (!pMask)
 	wm_state->thread1.binding_table_entry_count = 2; /* 1 tex and fb */
     else
commit 771a56b1ed0df69345c723cb62a73b6842cd8227
Author: Keith Packard <keithp at keithp.com>
Date:   Sun Mar 30 00:54:07 2008 -0700

    Clarify comment in exa_sf program

diff --git a/src/exa_sf.g4a b/src/exa_sf.g4a
index 4da5eba..3e660ac 100644
--- a/src/exa_sf.g4a
+++ b/src/exa_sf.g4a
@@ -80,7 +80,7 @@
 /* Compute inverses of the input deltas */
 send (4) 0 g6<1>F g1.12<4,4,1>F math inv mlen 1 rlen 1 { align1 };
 
-/* texture value at V0 */
+/* texture location at V0 */
 mov (4) m3<1>F g3<4,4,1>F { align1 };
 
 /* compute V1 - V2 (motion in X) for texture coordinates */
commit 4f469189fed541549e5d470b2529275a29cc2f20
Author: Keith Packard <keithp at keithp.com>
Date:   Sat Mar 29 14:28:05 2008 -0700

    Compute du/dv/dw in no-mask SF prog

diff --git a/src/exa_sf.g4a b/src/exa_sf.g4a
index 5a02399..4da5eba 100644
--- a/src/exa_sf.g4a
+++ b/src/exa_sf.g4a
@@ -26,14 +26,76 @@
  *
  */
 
-send (1) 0 g6<1>F g1.12<0,1,0>F math inv scalar mlen 1 rlen 1 { align1 };
-send (1) 0 g6.4<1>F g1.20<0,1,0>F math inv scalar mlen 1 rlen 1 { align1 };
-add (8) g7<1>F g4<8,8,1>F -g3<8,8,1>F { align1 };
-mul (1) g7<1>F g7<0,1,0>F g6<0,1,0>F { align1 };
-mul (1) g7.4<1>F g7.4<0,1,0>F g6.4<0,1,0>F { align1 };
-mov (8) m1<1>F g7<0,1,0>F { align1 };
-mov (8) m2<1>F g7.4<0,1,0>F { align1 };
-mov (8) m3<1>F g3<8,8,1>F { align1 };
+/*
+ * Inputs (note all sub-register addresses are bytes, not float indices)
+ *
+ * Note that the vertices will have been reordered:
+ *
+ * V0 is topmost (leftmost among topmost) (upper left)
+ * V1 is next clockwise (lower right)
+ * V2 is remaining (lower left)
+ *
+ *  V0 ...................... XX
+ *  |                          .
+ *  |                          .
+ *  |                          .
+ *  V2------------------------V1
+ *
+ *  G0	    thread state -- just pass along
+ *
+ *  G1 and G2 are fixed by SF spec
+ *
+ *  G1.0    reserved
+ *  G1.4    Provoking vertex
+ *  G1.8    Determinant
+ *  G1.12   X1 - X0
+ *  G1.16   X2 - X0
+ *  G1.20   Y1 - Y0
+ *  G1.24   Y2 - Y0
+ *  G1.30   reserved
+ *
+ *  G2.0    Z0
+ *  G2.4    1/W0
+ *  G2.8    Z1
+ *  G2.12   1/W1
+ *  G2.16   Z2
+ *  G2.20   1/W2
+ *  G2.24   reserved
+ *  G2.30   reserved
+ *
+ *  G3 is V0 Vertex Attribute Data from URB (upper left)
+ *
+ *  G3.0    u0
+ *  G3.4    v0
+ *
+ *  G4 is V1 Vertex Attribute Data from URB (lower right)
+ *
+ *  G4.0    u1
+ *  G4.4    v1
+ *
+ *  G5 is V2 Vertex Attribute Data from URB (lower left)
+ *
+ */
+
+/* Compute inverses of the input deltas */
+send (4) 0 g6<1>F g1.12<4,4,1>F math inv mlen 1 rlen 1 { align1 };
+
+/* texture value at V0 */
+mov (4) m3<1>F g3<4,4,1>F { align1 };
+
+/* compute V1 - V2 (motion in X) for texture coordinates */
+add (4) g7<1>F g4<4,4,1>F -g5<4,4,1>F { align1 };
+
+/* multiply by 1/dx */
+mul (4) m1<1>F g7<4,4,1>F g6.0<0,1,0>F { align1 };
+
+/* Compute V2 - V0 (motion in Y) for texture coordinates */
+add (4) g7<1>F g5<4,4,1>F -g3<4,4,1>F { align1 };
+
+/* multiply by 1/dy */
+mul (4) m2<1>F g7<4,4,1>F g6.8<0,1,0>F {align1 };
+
+/* and we're done */
 send (8) 0 null g0<8,8,1>F urb 0 transpose used complete mlen 4 rlen 0 { align1 EOT };
 nop;
 nop;
diff --git a/src/exa_sf_prog.h b/src/exa_sf_prog.h
index 830d176..223c9c9 100644
--- a/src/exa_sf_prog.h
+++ b/src/exa_sf_prog.h
@@ -1,11 +1,9 @@
-   { 0x00000031, 0x20c01fbd, 0x0000002c, 0x01110081 },
-   { 0x00000031, 0x20c41fbd, 0x00000034, 0x01110081 },
-   { 0x00600040, 0x20e077bd, 0x008d0080, 0x008d4060 },
-   { 0x00000041, 0x20e077bd, 0x000000e0, 0x000000c0 },
-   { 0x00000041, 0x20e477bd, 0x000000e4, 0x000000c4 },
-   { 0x00600001, 0x202003be, 0x000000e0, 0x00000000 },
-   { 0x00600001, 0x204003be, 0x000000e4, 0x00000000 },
-   { 0x00600001, 0x206003be, 0x008d0060, 0x00000000 },
+   { 0x00400031, 0x20c01fbd, 0x0069002c, 0x01110001 },
+   { 0x00400001, 0x206003be, 0x00690060, 0x00000000 },
+   { 0x00400040, 0x20e077bd, 0x00690080, 0x006940a0 },
+   { 0x00400041, 0x202077be, 0x006900e0, 0x000000c0 },
+   { 0x00400040, 0x20e077bd, 0x006900a0, 0x00694060 },
+   { 0x00400041, 0x204077be, 0x006900e0, 0x000000c8 },
    { 0x00600031, 0x20001fbc, 0x008d0000, 0x8640c800 },
    { 0x0000007e, 0x00000000, 0x00000000, 0x00000000 },
    { 0x0000007e, 0x00000000, 0x00000000, 0x00000000 },
commit 7dcb6e627449c80cea9812462ce6a3e125bd1240
Author: Keith Packard <keithp at keithp.com>
Date:   Sat Mar 29 14:27:35 2008 -0700

    Disable cursors while switching modes

diff --git a/src/i830_display.c b/src/i830_display.c
index 5e52aac..6a2d1d7 100644
--- a/src/i830_display.c
+++ b/src/i830_display.c
@@ -901,9 +901,12 @@ i830_crtc_unlock (xf86CrtcPtr crtc)
 static void
 i830_crtc_prepare (xf86CrtcPtr crtc)
 {
+    I830CrtcPrivatePtr	intel_crtc = crtc->driver_private;
     /* Temporarily turn off FB compression during modeset */
     if (i830_use_fb_compression(crtc))
         i830_disable_fb_compression(crtc);
+    if (intel_crtc->enabled)
+	crtc->funcs->hide_cursor (crtc);
     crtc->funcs->dpms (crtc, DPMSModeOff);
 }
 
commit d50264fc7c4e0f80d9cc68dfdf322f68520a0f1e
Author: Eric Anholt <eric at anholt.net>
Date:   Fri Mar 28 15:15:26 2008 -0700

    Add a "total" field to intel_idle output (set when any unit is busy).

diff --git a/src/reg_dumper/idle.c b/src/reg_dumper/idle.c
index 0077bf4..bc9dbb7 100644
--- a/src/reg_dumper/idle.c
+++ b/src/reg_dumper/idle.c
@@ -54,22 +54,24 @@ struct idle_flags i965_idle_flags[] = {
     {I965_MAP_FILTER_DONE, "map filter"},
     {I965_MAP_L2_IDLE, "map L2"},
     {I965_CP_DONE, "CP"},
+    {0, "total"},
     {0, "other"},
 };
 
-/* Fills in the "other" field's idle flags */
+/* Fills in the "other" and "total" fields' idle flags */
 static void
 setup_other_flags(struct idle_flags *idle_flags, int idle_flag_count)
 {
-    uint32_t other_idle_flags;
+    uint32_t other_idle_flags, total_idle_flags = 0;
     int i;
 
     other_idle_flags = ~(I965_RING_0_ENABLE);
-    for (i = 0; i < idle_flag_count - 1; i++) {
+    for (i = 0; i < idle_flag_count - 2; i++) {
 	other_idle_flags &= ~idle_flags[i].instdone_flag;
+	total_idle_flags |= idle_flags[i].instdone_flag;
     }
+    idle_flags[i - 1].instdone_flag = total_idle_flags;
     idle_flags[i].instdone_flag = other_idle_flags;
-
 }
 
 int main(int argc, char **argv)
@@ -138,7 +140,8 @@ int main(int argc, char **argv)
 	    uint32_t instdone = INREG(INST_DONE_I965);
 
 	    for (j = 0; j < idle_flag_count; j++) {
-		if ((instdone & idle_flags[j].instdone_flag) == 0)
+		if ((instdone & idle_flags[j].instdone_flag) !=
+		    idle_flags[j].instdone_flag)
 		    idle_flags[j].count++;
 	    }
 
commit 1450acd046d47e1739a3ffbd146c73ad2974a935
Author: Jesse Barnes <jbarnes at hobbes.virtuousgeek.org>
Date:   Fri Mar 28 13:23:02 2008 -0700

    Use combo backlight control rather than pure legacy
    
    If the legacy bit is set, use both the BLC_PWM_CTL and LBB regs to control the
    backlight, rather than just LBB.  Looks like more platforms want that than what
    the current code does.  Note that kernel provided interfaces will always be
    used if available, so this shouldn't affect users with /sys/class/backlight
    interfaces at all.
    
    Fixes #14721.

diff --git a/src/i830_lvds.c b/src/i830_lvds.c
index 28a51d9..33b4f26 100644
--- a/src/i830_lvds.c
+++ b/src/i830_lvds.c
@@ -133,11 +133,11 @@ i830_set_lvds_backlight_method(xf86OutputPtr output)
     } else if (IS_I965GM(pI830) || IS_IGD_GM(pI830)) {
 	blc_pwm_ctl2 = INREG(BLC_PWM_CTL2);
 	if (blc_pwm_ctl2 & BLM_LEGACY_MODE2)
-	    method = BCM_LEGACY;
+	    method = BCM_COMBO;
     } else {
 	blc_pwm_ctl = INREG(BLC_PWM_CTL);
 	if (blc_pwm_ctl & BLM_LEGACY_MODE)
-	    method = BCM_LEGACY;
+	    method = BCM_COMBO;
     }
 
     pI830->backlight_control_method = method;
commit 49f409fef5e8b04a8595309ba8959ca36b2e41b1
Author: Matthias Hopf <mhopf at suse.de>
Date:   Wed Jan 9 16:31:41 2008 +0100

    Include missing stdlib.h for free()

diff --git a/src/i830_bios.c b/src/i830_bios.c
index 0a28fb4..57ee278 100644
--- a/src/i830_bios.c
+++ b/src/i830_bios.c
@@ -31,6 +31,7 @@
 
 #include <stdio.h>
 #include <string.h>
+#include <stdlib.h>
 
 #define _PARSE_EDID_
 #include "xf86.h"
commit 3414313ac9d0faa95797ee18cc33afa231ec7581
Author: Matthias Hopf <mhopf at suse.de>
Date:   Wed Jan 9 16:08:57 2008 +0100

    Fix obviously wrong verification of DRI_SUPPORTS_CLIP_NOTIFY.

diff --git a/src/i830_dri.c b/src/i830_dri.c
index 3493eb9..4361ad0 100644
--- a/src/i830_dri.c
+++ b/src/i830_dri.c
@@ -135,7 +135,7 @@ static void I830DRITransitionSingleToMulti3d(ScreenPtr pScreen);
 #define DRI_DRIVER_FRAMEBUFFER_MAP 0
 #endif
 
-#ifdef DRI_SUPPORTS_CLIP_NOTIFY
+#if DRI_SUPPORTS_CLIP_NOTIFY
 static void I830DRIClipNotify(ScreenPtr pScreen, WindowPtr *ppWin, int num);
 #endif
 
commit c40f195f2dc3467259b4588e087aac9741003ebf
Author: Matthias Hopf <mhopf at suse.de>
Date:   Wed Jan 9 14:40:49 2008 +0100

    Fix obviously stray '(' in non-I830_USE_EXA case.

diff --git a/src/i830_xaa.c b/src/i830_xaa.c
index 0df7f98..c9c26b0 100644
--- a/src/i830_xaa.c
+++ b/src/i830_xaa.c
@@ -326,7 +326,7 @@ I830SetupForSolidFill(ScrnInfoPtr pScrn, int color, int rop,
      */
     pI830->BR[13] |= (I830PatternROP[rop] << 16);
 #else
-    pI830->BR[13] |= ((XAAGetPatternROP(rop) << 16);
+    pI830->BR[13] |= (XAAGetPatternROP(rop) << 16);
 #endif
 
     pI830->BR[16] = color;
commit 7bba2c13310ed5ac22a355a3cc0ec8b7afaa79cf
Author: Zhenyu Wang <zhenyu.z.wang at intel.com>
Date:   Fri Mar 28 11:41:24 2008 +0800

    Disable DRI earlier if fb width > 2048

diff --git a/src/i830_driver.c b/src/i830_driver.c
index 94f0712..a19c8eb 100644
--- a/src/i830_driver.c
+++ b/src/i830_driver.c
@@ -2685,6 +2685,12 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
       pScrn->videoRam &= ~3;
    }
 
+   if (!IS_I965G(pI830) && pScrn->displayWidth > 2048) {
+      xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+		 "Cannot support DRI with frame buffer width > 2048.\n");
+      pI830->directRenderingDisabled = TRUE;
+   }
+
 #ifdef XF86DRI
    /* If DRI hasn't been explicitly disabled, try to initialize it.
     * It will be used by the memory allocator.
@@ -2762,12 +2768,6 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
     pI830->XvEnabled = !pI830->XvDisabled;
 #endif
 
-   if (!IS_I965G(pI830) && pScrn->displayWidth > 2048) {
-      xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
-		 "Cannot support DRI with frame buffer width > 2048.\n");
-      pI830->tiling = FALSE;
-      pI830->directRenderingEnabled = FALSE;
-   }
 
    /* Need MMIO mapped to do GTT lookups during memory allocation. */
    I830MapMMIO(pScrn);
commit b1f358ba97473b792ec2b7ed5170152faebe7262
Author: Zhenyu Wang <zhenyu.z.wang at intel.com>
Date:   Fri Mar 28 11:29:40 2008 +0800

    Disable overlay on new mobile chipset
    
    It's gone, really.

diff --git a/src/i830_driver.c b/src/i830_driver.c
index b0bb9da..94f0712 100644
--- a/src/i830_driver.c
+++ b/src/i830_driver.c
@@ -2827,7 +2827,7 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
 		    "needs 2D acceleration.\n");
 	 pI830->XvEnabled = FALSE;
       }
-      if (!IS_I9XX(pI830) && pI830->overlay_regs == NULL) {
+      if (!IS_IGD_GM(pI830) && pI830->overlay_regs == NULL) {
 	  xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
 		     "Disabling Xv because the overlay register buffer "
 		      "allocation failed.\n");
diff --git a/src/i830_memory.c b/src/i830_memory.c
index a38ee78..6835a6f 100644
--- a/src/i830_memory.c
+++ b/src/i830_memory.c
@@ -445,7 +445,7 @@ i830_allocator_init(ScrnInfoPtr pScrn, unsigned long offset, unsigned long size)
 	/* Overlay and cursors, if physical, need to be allocated outside
 	 * of the kernel memory manager.
 	 */
-	if (!OVERLAY_NOPHYSICAL(pI830) && !IS_I965G(pI830)) {
+	if (!OVERLAY_NOPHYSICAL(pI830) && !IS_IGD_GM(pI830)) {
 	    mmsize -= ROUND_TO(OVERLAY_SIZE, GTT_PAGE_SIZE);
 	}
 	if (pI830->CursorNeedsPhysical) {
@@ -1025,6 +1025,9 @@ i830_allocate_overlay(ScrnInfoPtr pScrn)
     if (!pI830->XvEnabled)
 	return TRUE;
 
+    if (IS_IGD_GM(pI830))
+	return TRUE;
+
     if (!OVERLAY_NOPHYSICAL(pI830))
 	flags |= NEED_PHYSICAL_ADDR;
 
diff --git a/src/i830_video.c b/src/i830_video.c
index 04ce0d6..68bcc88 100644
--- a/src/i830_video.c
+++ b/src/i830_video.c
@@ -617,7 +617,8 @@ I830InitVideo(ScreenPtr pScreen)
     }
 
     /* Set up overlay video if we can do it at this depth. */
-    if (pScrn->bitsPerPixel != 8 && pI830->overlay_regs != NULL)
+    if (!IS_IGD_GM(pI830) && pScrn->bitsPerPixel != 8 &&
+	    pI830->overlay_regs != NULL)
     {
 	overlayAdaptor = I830SetupImageVideoOverlay(pScreen);
 	if (overlayAdaptor != NULL) {
@@ -2634,6 +2635,7 @@ I830VideoBlockHandler(int i, pointer blockData, pointer pTimeout,
     I830Ptr pI830 = I830PTR(pScrn);
     I830PortPrivPtr pPriv;
 
+    /* no overlay */
     if (pI830->adaptor == NULL)
         return;
 
@@ -2913,6 +2915,7 @@ i830_crtc_dpms_video(xf86CrtcPtr crtc, Bool on)
     I830Ptr pI830 = I830PTR(pScrn);
     I830PortPrivPtr pPriv;
 
+    /* no overlay */
     if (pI830->adaptor == NULL)
 	return;
 
commit 588371ba15afffa9343629f0ea7ce530586eef0b
Merge: 52d6ced... c13efdd...
Author: Jesse Barnes <jbarnes at hobbes.virtuousgeek.org>
Date:   Wed Mar 26 14:53:15 2008 -0700

    Merge branch 'master' into pfit

commit c13efdd3d6d3846078766814b57306a7519bce18
Author: Paulo Cesar Pereira de Andrade <pcpa at mandriva.com.br>
Date:   Wed Mar 26 10:11:36 2008 +0800

    More compile warning fixes.
    
    o Check for RANDR_GET_CRTC_INTERFACE before defining functions that
      are used only if it is defined.
    o Declare a variable before code, and rename it from ret to xvmc_status
      to better describe it.
    o if 0 some static functions not used.
    o Don't declare some unused variables.
    o Declare as static some functions that are used only in the file defining it.
    o Add a default/fallback return True to the Bool function
      src/xvmc/intel_batchbuffer.c:intelInitBatchBuffer().
    o Ansify src/xvmc/xf86dri.c.
    o Add missing prototype to src/xvmc/xf86dri.h and follow pattern of other
      headers by adding "extern" before function prototype.

diff --git a/src/i830_crt.c b/src/i830_crt.c
index d1ed3a8..2a99f9c 100644
--- a/src/i830_crt.c
+++ b/src/i830_crt.c
@@ -391,6 +391,7 @@ i830_crt_destroy (xf86OutputPtr output)
 	xfree (output->driver_private);
 }
 
+#ifdef RANDR_GET_CRTC_INTERFACE
 static xf86CrtcPtr
 i830_crt_get_crtc(xf86OutputPtr output)
 {
@@ -400,6 +401,7 @@ i830_crt_get_crtc(xf86OutputPtr output)
    
     return i830_pipe_to_crtc(pScrn, pipe);
 }
+#endif
 
 static const xf86OutputFuncsRec i830_crt_output_funcs = {
     .dpms = i830_crt_dpms,
diff --git a/src/i830_dvo.c b/src/i830_dvo.c
index 7561833..9e82171 100644
--- a/src/i830_dvo.c
+++ b/src/i830_dvo.c
@@ -330,6 +330,7 @@ i830_dvo_destroy (xf86OutputPtr output)
     }
 }
 
+#ifdef RANDR_GET_CRTC_INTERFACE
 static xf86CrtcPtr
 i830_dvo_get_crtc(xf86OutputPtr output)
 {
@@ -341,6 +342,7 @@ i830_dvo_get_crtc(xf86OutputPtr output)
    
     return i830_pipe_to_crtc(pScrn, pipe);
 }
+#endif
 
 static const xf86OutputFuncsRec i830_dvo_output_funcs = {
     .dpms = i830_dvo_dpms,
diff --git a/src/i830_lvds.c b/src/i830_lvds.c
index 0b331ef..772a8b8 100644
--- a/src/i830_lvds.c
+++ b/src/i830_lvds.c
@@ -879,6 +879,7 @@ i830_lvds_get_property(xf86OutputPtr output, Atom property)
 }
 #endif /* RANDR_13_INTERFACE */
 
+#ifdef RANDR_GET_CRTC_INTERFACE
 static xf86CrtcPtr
 i830_lvds_get_crtc(xf86OutputPtr output)
 {
@@ -888,6 +889,7 @@ i830_lvds_get_crtc(xf86OutputPtr output)
    
     return i830_pipe_to_crtc(pScrn, pipe);
 }
+#endif
 
 static const xf86OutputFuncsRec i830_lvds_output_funcs = {
     .create_resources = i830_lvds_create_resources,
diff --git a/src/i830_sdvo.c b/src/i830_sdvo.c
index d72b913..f60e38c 100644
--- a/src/i830_sdvo.c
+++ b/src/i830_sdvo.c
@@ -1146,6 +1146,7 @@ i830_sdvo_destroy (xf86OutputPtr output)
     }
 }
 
+#ifdef RANDR_GET_CRTC_INTERFACE
 static xf86CrtcPtr
 i830_sdvo_get_crtc(xf86OutputPtr output)
 {
@@ -1157,6 +1158,7 @@ i830_sdvo_get_crtc(xf86OutputPtr output)
    
     return i830_pipe_to_crtc(pScrn, pipe);
 }
+#endif
 
 static const xf86OutputFuncsRec i830_sdvo_output_funcs = {
     .dpms = i830_sdvo_dpms,
diff --git a/src/i830_tv.c b/src/i830_tv.c
index b478cc7..6adb9f2 100644
--- a/src/i830_tv.c
+++ b/src/i830_tv.c
@@ -1640,6 +1640,7 @@ i830_tv_set_property(xf86OutputPtr output, Atom property,
 }
 #endif /* RANDR_12_INTERFACE */
 
+#ifdef RANDR_GET_CRTC_INTERFACE
 static xf86CrtcPtr
 i830_tv_get_crtc(xf86OutputPtr output)
 {
@@ -1649,6 +1650,7 @@ i830_tv_get_crtc(xf86OutputPtr output)
    
     return i830_pipe_to_crtc(pScrn, pipe);
 }
+#endif
 
 static const xf86OutputFuncsRec i830_tv_output_funcs = {
     .create_resources = i830_tv_create_resources,
diff --git a/src/i830_video.c b/src/i830_video.c
index 5939634..04ce0d6 100644
--- a/src/i830_video.c
+++ b/src/i830_video.c
@@ -565,6 +565,9 @@ I830InitVideo(ScreenPtr pScreen)
     XF86VideoAdaptorPtr *adaptors, *newAdaptors = NULL;
     XF86VideoAdaptorPtr overlayAdaptor = NULL, texturedAdaptor = NULL;
     int num_adaptors;
+#ifdef INTEL_XVMC
+    Bool xvmc_status = FALSE;
+#endif
 
 #if 0
     {
@@ -627,10 +630,9 @@ I830InitVideo(ScreenPtr pScreen)
 	I830InitOffscreenImages(pScreen);
     }
 #ifdef INTEL_XVMC
-    Bool ret = FALSE;
     if (intel_xvmc_probe(pScrn)) {
 	if (texturedAdaptor)
-	    ret = intel_xvmc_driver_init(pScreen, texturedAdaptor);
+	    xvmc_status = intel_xvmc_driver_init(pScreen, texturedAdaptor);
     }
 #endif
 
@@ -638,7 +640,7 @@ I830InitVideo(ScreenPtr pScreen)
 	xf86XVScreenInit(pScreen, adaptors, num_adaptors);
 
 #ifdef INTEL_XVMC
-    if (ret)
+    if (xvmc_status)
 	intel_xvmc_screen_init(pScreen);
 #endif
     xfree(adaptors);
diff --git a/src/i915_hwmc.c b/src/i915_hwmc.c
index cdcef5a..c3d3c75 100644
--- a/src/i915_hwmc.c
+++ b/src/i915_hwmc.c
@@ -97,6 +97,7 @@ typedef struct _I915XvMC
 
 #define ARRARY_SIZE(a) (sizeof(a) / sizeof(a[0]))
 
+/*
 static int yv12_subpicture_index_list[2] =
 {
     FOURCC_IA44,
@@ -108,6 +109,7 @@ static XF86MCImageIDList yv12_subpicture_list =
     ARRARY_SIZE(yv12_subpicture_index_list),
     yv12_subpicture_index_list
 };
+ */
 
 static XF86MCSurfaceInfoRec i915_YV12_mpg2_surface =
 {
@@ -147,6 +149,7 @@ static XF86MCSurfaceInfoPtr ppSI[2] =
     (XF86MCSurfaceInfoPtr)&i915_YV12_mpg1_surface
 };
 
+#if 0
 /* List of subpicture types that we support */
 static XF86ImageRec ia44_subpicture = XVIMAGE_IA44;
 static XF86ImageRec ai44_subpicture = XVIMAGE_AI44;
@@ -156,7 +159,7 @@ static XF86ImagePtr i915_subpicture_list[2] =
     (XF86ImagePtr)&ia44_subpicture,
     (XF86ImagePtr)&ai44_subpicture
 };
-
+#endif
 
 /*
  * Init and clean up the screen private parts of XvMC.
diff --git a/src/xvmc/i915_xvmc.c b/src/xvmc/i915_xvmc.c
index b30facd..20b2e61 100644
--- a/src/xvmc/i915_xvmc.c
+++ b/src/xvmc/i915_xvmc.c
@@ -25,7 +25,6 @@
  *
  */
 
-#include <pthread.h>
 #include <sys/ioctl.h>
 
 #include "i915_xvmc.h"
@@ -56,6 +55,7 @@ typedef union {
     uint  u[2];
 } su_t;
 
+#if 0
 static int findOverlap(unsigned int width, unsigned int height,
                        short *dstX, short *dstY,
                        short *srcX, short *srcY,
@@ -91,6 +91,7 @@ static int findOverlap(unsigned int width, unsigned int height,
     *areaH = (h <= mHeight) ? h : mHeight;
     return 0;
 }
+#endif
 
 static void i915_flush(int map, int render)
 {
@@ -117,7 +118,7 @@ static void i915_mc_static_indirect_state_buffer(XvMCContext *context,
     struct i915_3dstate_dest_buffer_variables_mpeg *dest_buffer_variables_mpeg;
     i915XvMCSurface *pI915Surface = (i915XvMCSurface *)surface->privData;
     i915XvMCContext *pI915XvMC = (i915XvMCContext *)context->privData;
-    unsigned int w = surface->width, h = surface->height;
+    unsigned int w = surface->width;
 
     /* 3DSTATE_BUFFER_INFO */
     /* DEST Y */
@@ -459,7 +460,7 @@ static void i915_mc_mpeg_macroblock_ipicture(XvMCContext *context, XvMCMacroBloc
     intelBatchbufferData(&macroblock_ipicture, sizeof(macroblock_ipicture), 0);
 }
 
-
+#if 0
 static void i915_mc_mpeg_macroblock_0mv(XvMCContext *context, XvMCMacroBlock *mb)
 {
     struct i915_3dmpeg_macroblock_0mv macroblock_0mv;
@@ -487,6 +488,7 @@ static void i915_mc_mpeg_macroblock_0mv(XvMCContext *context, XvMCMacroBlock *mb
 
     intelBatchbufferData(&macroblock_0mv, sizeof(macroblock_0mv), 0);
 }
+#endif
 
 static void i915_mc_mpeg_macroblock_1fbmv(XvMCContext *context, XvMCMacroBlock *mb)
 {
@@ -529,7 +531,6 @@ static void i915_mc_mpeg_macroblock_1fbmv(XvMCContext *context, XvMCMacroBlock *
 static void i915_mc_mpeg_macroblock_2fbmv(XvMCContext *context, XvMCMacroBlock *mb, unsigned int ps)
 {
     struct i915_3dmpeg_macroblock_2fbmv macroblock_2fbmv;
-    i915XvMCContext *pI915XvMC = (i915XvMCContext *)context->privData;
 
     /* Motion Vectors */
     su_t fmv;
@@ -979,6 +980,7 @@ static void i915_mc_one_time_state_initialization(XvMCContext *context)
     free(base);
 }
 
+#if 0
 static void i915_mc_invalidate_subcontext_buffers(XvMCContext *context, unsigned int mask)
 {
     struct i915_3dstate_load_indirect *load_indirect = NULL;
@@ -1086,6 +1088,7 @@ static void i915_mc_invalidate_subcontext_buffers(XvMCContext *context, unsigned
     intelBatchbufferData(base, size, 0);
     free(base);
 }
+#endif
 
 static int i915_xvmc_map_buffers(i915XvMCContext *pI915XvMC)
 {
@@ -1167,6 +1170,7 @@ static void i915_xvmc_unmap_buffers(i915XvMCContext *pI915XvMC)
     }
 }
 
+#if 0
 /*
  * Video post processing
  */
@@ -1243,7 +1247,9 @@ static void i915_yuv2rgb_map_state_buffer(XvMCSurface *target_surface)
     tm->tm2.cube_face = 0;
     tm->tm2.pitch = (privTarget->uvStride >> 2) - 1;    /* in DWords - 1 */
 }
+#endif
 
+#if 0
 static void i915_yuv2rgb_sampler_state_buffer(XvMCSurface *surface)
 {
     struct i915_3dstate_sampler_state *sampler_state;
@@ -1340,7 +1346,9 @@ static void i915_yuv2rgb_sampler_state_buffer(XvMCSurface *surface)
     ts->ts1.east_deinterlacer = 0;
     ts->ts2.default_color = 0;
 }
+#endif
 
+#if 0
 static void i915_yuv2rgb_static_indirect_state_buffer(XvMCSurface *surface,
                                                       unsigned int dstaddr,
                                                       int dstpitch)
@@ -1374,7 +1382,9 @@ static void i915_yuv2rgb_static_indirect_state_buffer(XvMCSurface *surface,
     dest_buffer_variables->dw1.dest_h_bias = 8;
     dest_buffer_variables->dw1.color_fmt = COLORBUFFER_A8R8G8B8;  /* FIXME */
 }
+#endif
 
+#if 0
 static void i915_yuv2rgb_pixel_shader_program_buffer(XvMCSurface *surface)
 {
     struct i915_3dstate_pixel_shader_program *pixel_shader_program;
@@ -1424,7 +1434,9 @@ static void i915_yuv2rgb_pixel_shader_program_buffer(XvMCSurface *surface)
     src1 = UREG(REG_TYPE_S, 2); /* SAMPLER */
     i915_inst_texld(inst, T0_TEXLD, dest, src0, src1);
 }
+#endif
 
+#if 0
 static void i915_yuv2rgb_proc(XvMCSurface *surface)
 {
     i915XvMCSurface *privSurface = (i915XvMCSurface *)surface->privData;
@@ -1581,6 +1593,7 @@ static void i915_yuv2rgb_proc(XvMCSurface *surface)
     intelBatchbufferData(base, size, 0);
     free(base);
 }
+#endif
 
 /*
  * Function: i915_release_resource
@@ -1588,7 +1601,6 @@ static void i915_yuv2rgb_proc(XvMCSurface *surface)
 static void i915_release_resource(Display *display, XvMCContext *context)
 {
     i915XvMCContext *pI915XvMC;
-    int screen = DefaultScreen(display);
 
     if (!(pI915XvMC = context->privData))
         return;
@@ -1608,13 +1620,7 @@ static Status i915_xvmc_mc_create_context(Display *display, XvMCContext *context
 {
     i915XvMCContext *pI915XvMC = NULL;
     I915XvMCCreateContextRec *tmpComm = NULL;
-    Status ret;
     drm_sarea_t *pSAREA;
-    char *curBusID;
-    uint magic;
-    int major, minor;
-    int isCapable;
-    int screen = DefaultScreen(display);
 
     XVMC_DBG("%s\n", __FUNCTION__);
 
@@ -1718,7 +1724,6 @@ static Status i915_xvmc_mc_create_surface(Display *display,
 	XvMCContext *context, XvMCSurface *surface, int priv_count,
 	CARD32 *priv_data)
 {
-    Status ret;
     i915XvMCContext *pI915XvMC;
     i915XvMCSurface *pI915Surface;
     I915XvMCCreateSurfaceRec *tmpComm = NULL;
diff --git a/src/xvmc/intel_batchbuffer.c b/src/xvmc/intel_batchbuffer.c
index a3f82ff..224d0de 100644
--- a/src/xvmc/intel_batchbuffer.c
+++ b/src/xvmc/intel_batchbuffer.c
@@ -48,7 +48,7 @@
 
 #define MI_BATCH_BUFFER_END     (0xA << 23)
 
-int intelEmitIrqLocked(void)
+static int intelEmitIrqLocked(void)
 {
    drmI830IrqEmit ie;
    int ret, seq;
@@ -65,7 +65,7 @@ int intelEmitIrqLocked(void)
    return seq;
 }
 
-void intelWaitIrq(int seq)
+static void intelWaitIrq(int seq)
 {
    int ret;
    drmI830IrqWait iw;
@@ -118,6 +118,7 @@ Bool intelInitBatchBuffer(void)
 
     xvmc_driver->alloc.active_buf = 0;
     assert(xvmc_driver->alloc.ptr);
+    return True;
 }
 
 void intelFiniBatchBuffer(void)
@@ -129,7 +130,7 @@ void intelFiniBatchBuffer(void)
     intelDestroyBatchBuffer();
 }
 
-void intelBatchbufferRequireSpace(unsigned int sz)
+static void intelBatchbufferRequireSpace(unsigned int sz)
 {
    if (xvmc_driver->batch.space < sz)
       intelFlushBatch(TRUE);
@@ -152,7 +153,7 @@ void intelBatchbufferData(const void *data, unsigned bytes, unsigned flags)
 #define FLUSH_RENDER_CACHE      (0 << 2)
 #define FLUSH_WRITE_DIRTY_STATE (1 << 4)
 
-void intelRefillBatchLocked(Bool allow_unlock )
+static void intelRefillBatchLocked(Bool allow_unlock)
 {
    unsigned half = xvmc_driver->alloc.size >> 1;
    unsigned buf = (xvmc_driver->alloc.active_buf ^= 1);
@@ -175,9 +176,9 @@ void intelRefillBatchLocked(Bool allow_unlock )
 }
 
 
-void intelFlushBatchLocked(Bool ignore_cliprects,
-                           Bool refill,
-                           Bool allow_unlock)
+static void intelFlushBatchLocked(Bool ignore_cliprects,
+				  Bool refill,
+				  Bool allow_unlock)
 {
    drmI830BatchBuffer batch;
 
diff --git a/src/xvmc/intel_xvmc.c b/src/xvmc/intel_xvmc.c
index 489a2c2..1be8cc6 100644
--- a/src/xvmc/intel_xvmc.c
+++ b/src/xvmc/intel_xvmc.c
@@ -250,7 +250,7 @@ Status XvMCCreateContext(Display *display, XvPortID port,
         XVMC_ERR("Unable to create XvMC Context.");
         return ret;
     }
-    XVMC_DBG("new context %d created\n", context->context_id);
+    XVMC_DBG("new context %d created\n", (int)context->context_id);
 
     comm = (struct _intel_xvmc_common *)priv_data;
 
@@ -341,7 +341,7 @@ Status XvMCCreateContext(Display *display, XvPortID port,
 			     context->context_id,
                              &intel_ctx->hw_context)) {
         XVMC_ERR("Could not create DRI context for xvmc ctx %d.",
-			context->context_id);
+		 (int)context->context_id);
 	XFree(priv_data);
         context->privData = NULL;
         drmUnmap(xvmc_driver->sarea_address, xvmc_driver->sarea_size);
diff --git a/src/xvmc/intel_xvmc.h b/src/xvmc/intel_xvmc.h
index 3375ffc..5506683 100644
--- a/src/xvmc/intel_xvmc.h
+++ b/src/xvmc/intel_xvmc.h
@@ -27,6 +27,7 @@
 #ifndef INTEL_XVMC_H
 #define INTEL_XVMC_H
 
+#include <pthread.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <unistd.h>
diff --git a/src/xvmc/xf86dri.c b/src/xvmc/xf86dri.c
index 798c1a8..96987bf 100644
--- a/src/xvmc/xf86dri.c
+++ b/src/xvmc/xf86dri.c
@@ -88,9 +88,8 @@ XEXT_GENERATE_FIND_DISPLAY(find_display, xf86dri_info,
 #else
 #define TRACE(msg, arg...)
 #endif
-    Bool uniDRIQueryExtension(dpy, event_basep, error_basep)
-    Display *dpy;
-    int *event_basep, *error_basep;
+Bool
+uniDRIQueryExtension(Display *dpy, int *event_basep, int *error_basep)
 {
     XExtDisplayInfo *info = find_display(dpy);
 
@@ -107,11 +106,8 @@ XEXT_GENERATE_FIND_DISPLAY(find_display, xf86dri_info,
 }
 
 Bool
-uniDRIQueryVersion(dpy, majorVersion, minorVersion, patchVersion)
-    Display *dpy;
-    int *majorVersion;
-    int *minorVersion;
-    int *patchVersion;
+uniDRIQueryVersion(Display *dpy, int *majorVersion, int *minorVersion,
+		   int *patchVersion)
 {
     XExtDisplayInfo *info = find_display(dpy);
     xXF86DRIQueryVersionReply rep;
@@ -141,10 +137,7 @@ uniDRIQueryVersion(dpy, majorVersion, minorVersion, patchVersion)
 }
 
 Bool
-uniDRIQueryDirectRenderingCapable(dpy, screen, isCapable)
-    Display *dpy;
-    int screen;
-    Bool *isCapable;
+uniDRIQueryDirectRenderingCapable(Display *dpy, int screen, Bool *isCapable)
 {
     XExtDisplayInfo *info = find_display(dpy);
     xXF86DRIQueryDirectRenderingCapableReply rep;
@@ -173,11 +166,8 @@ uniDRIQueryDirectRenderingCapable(dpy, screen, isCapable)
 }
 
 Bool
-uniDRIOpenConnection(dpy, screen, hSAREA, busIdString)
-    Display *dpy;
-    int screen;
-    drm_handle_t *hSAREA;
-    char **busIdString;
+uniDRIOpenConnection(Display *dpy, int screen,
+		     drm_handle_t *hSAREA, char **busIdString)
 {
     XExtDisplayInfo *info = find_display(dpy);
     xXF86DRIOpenConnectionReply rep;
@@ -224,10 +214,7 @@ uniDRIOpenConnection(dpy, screen, hSAREA, busIdString)
 }
 
 Bool
-uniDRIAuthConnection(dpy, screen, magic)
-    Display *dpy;
-    int screen;
-    drm_magic_t magic;
+uniDRIAuthConnection(Display *dpy, int screen, drm_magic_t magic)
 {
     XExtDisplayInfo *info = find_display(dpy);
     xXF86DRIAuthConnectionReq *req;
@@ -256,9 +243,7 @@ uniDRIAuthConnection(dpy, screen, magic)
 }
 
 Bool
-uniDRICloseConnection(dpy, screen)
-    Display *dpy;
-    int screen;
+uniDRICloseConnection(Display *dpy, int screen)
 {
     XExtDisplayInfo *info = find_display(dpy);
     xXF86DRICloseConnectionReq *req;
@@ -279,14 +264,9 @@ uniDRICloseConnection(dpy, screen)
 }
 
 Bool
-uniDRIGetClientDriverName(dpy, screen, ddxDriverMajorVersion,
-    ddxDriverMinorVersion, ddxDriverPatchVersion, clientDriverName)
-    Display *dpy;
-    int screen;
-    int *ddxDriverMajorVersion;
-    int *ddxDriverMinorVersion;
-    int *ddxDriverPatchVersion;
-    char **clientDriverName;
+uniDRIGetClientDriverName(Display *dpy, int screen, int *ddxDriverMajorVersion,
+			  int *ddxDriverMinorVersion, int *ddxDriverPatchVersion,
+			  char **clientDriverName)
 {
     XExtDisplayInfo *info = find_display(dpy);
     xXF86DRIGetClientDriverNameReply rep;
@@ -331,12 +311,8 @@ uniDRIGetClientDriverName(dpy, screen, ddxDriverMajorVersion,
 }
 
 Bool
-uniDRICreateContextWithConfig(dpy, screen, configID, context, hHWContext)
-    Display *dpy;
-    int screen;
-    int configID;
-    XID context;
-    drm_context_t *hHWContext;
+uniDRICreateContextWithConfig(Display *dpy, int screen, int configID,
+			      XID context, drm_context_t *hHWContext)
 {
     XExtDisplayInfo *info = find_display(dpy);
     xXF86DRICreateContextReply rep;
@@ -366,12 +342,8 @@ uniDRICreateContextWithConfig(dpy, screen, configID, context, hHWContext)
 }
 
 Bool
-uniDRICreateContext(dpy, screen, visual, context, hHWContext)
-    Display *dpy;
-    int screen;
-    Visual *visual;
-    XID context;
-    drm_context_t *hHWContext;
+uniDRICreateContext(Display *dpy, int screen, Visual *visual,
+		    XID context, drm_context_t *hHWContext)
 {
     return uniDRICreateContextWithConfig(dpy, screen,
 	   visual->visualid, context, hHWContext);
@@ -539,16 +511,9 @@ uniDRIGetDrawableInfo(Display * dpy, int screen, Drawable drawable,
 }
 
 Bool
-uniDRIGetDeviceInfo(dpy, screen, hFrameBuffer,
-    fbOrigin, fbSize, fbStride, devPrivateSize, pDevPrivate)
-    Display *dpy;
-    int screen;
-    drm_handle_t *hFrameBuffer;
-    int *fbOrigin;
-    int *fbSize;
-    int *fbStride;
-    int *devPrivateSize;
-    void **pDevPrivate;
+uniDRIGetDeviceInfo(Display *dpy, int screen, drm_handle_t *hFrameBuffer,
+		    int *fbOrigin, int *fbSize, int *fbStride,
+		    int *devPrivateSize, void **pDevPrivate)
 {
     XExtDisplayInfo *info = find_display(dpy);
     xXF86DRIGetDeviceInfoReply rep;
diff --git a/src/xvmc/xf86dri.h b/src/xvmc/xf86dri.h
index 7598bc8..81cfdfd 100644
--- a/src/xvmc/xf86dri.h
+++ b/src/xvmc/xf86dri.h
@@ -66,33 +66,33 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 #ifndef _XF86DRI_SERVER_
 
 _XFUNCPROTOBEGIN
-    Bool uniDRIQueryExtension(Display * dpy, int *event_base,
+extern Bool uniDRIQueryExtension(Display * dpy, int *event_base,
     int *error_base);
 
-Bool uniDRIQueryVersion(Display * dpy, int *majorVersion, int *minorVersion,
-    int *patchVersion);
+extern Bool uniDRIQueryVersion(Display * dpy, int *majorVersion,
+    int *minorVersion, int *patchVersion);
 
-Bool uniDRIQueryDirectRenderingCapable(Display * dpy, int screen,
+extern Bool uniDRIQueryDirectRenderingCapable(Display * dpy, int screen,
     Bool * isCapable);
 
-Bool uniDRIOpenConnection(Display * dpy, int screen, drm_handle_t * hSAREA,
+extern Bool uniDRIOpenConnection(Display * dpy, int screen, drm_handle_t * hSAREA,
     char **busIDString);
 
-Bool uniDRIAuthConnection(Display * dpy, int screen, drm_magic_t magic);
+extern Bool uniDRIAuthConnection(Display * dpy, int screen, drm_magic_t magic);
 
-Bool uniDRICloseConnection(Display * dpy, int screen);
+extern Bool uniDRICloseConnection(Display * dpy, int screen);
 
-Bool uniDRIGetClientDriverName(Display * dpy, int screen,
+extern Bool uniDRIGetClientDriverName(Display * dpy, int screen,
     int *ddxDriverMajorVersion, int *ddxDriverMinorVersion,
     int *ddxDriverPatchVersion, char **clientDriverName);
 
 /* XvMC context XID is alloced in _xvmc_create_context, so
  * don't recreate here */
-Bool uniDRICreateContext(Display * dpy, int screen, Visual * visual,
+extern Bool uniDRICreateContext(Display * dpy, int screen, Visual * visual,
     XID context_id, drm_context_t * hHWContext);
 
-Bool uniDRICreateContextWithConfig(Display * dpy, int screen, int configID,
-    XID context_id, drm_context_t * hHWContext);
+extern Bool uniDRICreateContextWithConfig(Display * dpy, int screen,
+    int configID, XID context_id, drm_context_t * hHWContext);
 
 extern Bool uniDRIDestroyContext(Display * dpy, int screen, XID context_id);
 
@@ -102,10 +102,17 @@ extern Bool uniDRICreateDrawable(Display * dpy, int screen,
 extern Bool uniDRIDestroyDrawable(Display * dpy, int screen,
     Drawable drawable);
 
-Bool uniDRIGetDeviceInfo(Display * dpy, int screen,
+extern Bool uniDRIGetDeviceInfo(Display * dpy, int screen,
     drm_handle_t * hFrameBuffer, int *fbOrigin, int *fbSize,
     int *fbStride, int *devPrivateSize, void **pDevPrivate);
 
+extern Bool uniDRIGetDrawableInfo(Display * dpy, int screen,
+    Drawable drawable, unsigned int *index, unsigned int *stamp,
+    int *X, int *Y, int *W, int *H,
+    int *numClipRects, drm_clip_rect_t ** pClipRects,
+    int *backX, int *backY,
+    int *numBackClipRects, drm_clip_rect_t ** pBackClipRects);
+
 _XFUNCPROTOEND
 #endif /* _XF86DRI_SERVER_ */
 #endif /* _XF86DRI_H_ */
commit 8cdbd55f8075cd18b563badde35815665d7d053e
Author: Eric Anholt <eric at anholt.net>
Date:   Tue Mar 25 10:06:14 2008 -0700

    Fix 965+ rendering issues with DRI disabled.
    
    The new chips no longer automatically flush the rendering cache, so if we
    don't flush the RC at blockhandler, the last rendering done may not
    appear on the screen.  This was particularly noticable with a bare Xorg with
    some missing root weave, and terminals where the last character wouldn't
    appear until the cursor blinked.  A flush in the DRI blockhandler path had
    hidden this issue for most people.

diff --git a/src/i830_driver.c b/src/i830_driver.c
index 50d9808..b0bb9da 100644
--- a/src/i830_driver.c
+++ b/src/i830_driver.c
@@ -2387,6 +2387,15 @@ I830BlockHandler(int i,
     pI830->BlockHandler = pScreen->BlockHandler;
     pScreen->BlockHandler = I830BlockHandler;
 
+    /* Emit a flush of the rendering cache, or on the 965 and beyond
+     * rendering results may not hit the framebuffer until significantly
+     * later.  In the direct rendering case this is already done just
+     * after the page flipping updates, so there's no need to duplicate
+     * the effort here.
+     */
+    if (!pI830->noAccel && !pI830->directRenderingEnabled)
+	I830EmitFlush(pScrn);
+
     I830VideoBlockHandler(i, blockData, pTimeout, pReadmask);
 }
 
commit c02ab432dd7058c700c35eecf6215daf5f262c51
Author: Eric Anholt <eric at anholt.net>
Date:   Mon Mar 24 13:48:20 2008 -0700

    Revert "Use mprotect on unbound AGP memory to attempt to catch use while unbound."
    
    While I still like the idea, the mprotect calls themselves are failing on
    Linux and causing more trouble than they're worth.
    
    This reverts commit a1612b7728d4153499fe86b6713a13c8702cc7d9.
    
    Conflicts:
    
    	src/i830_driver.c
    	src/i830_memory.c

diff --git a/src/i830_driver.c b/src/i830_driver.c
index c2ddf45..50d9808 100644
--- a/src/i830_driver.c
+++ b/src/i830_driver.c
@@ -171,7 +171,6 @@ USE OR OTHER DEALINGS IN THE SOFTWARE.
 #include <unistd.h>
 #include <stdlib.h>
 #include <stdio.h>
-#include <sys/mman.h>
 #include <errno.h>
 
 #include "xf86.h"
@@ -697,15 +696,6 @@ I830MapMem(ScrnInfoPtr pScrn)
 	 pI830->FbBase + pI830->LpRing->mem->offset;
    }
 
-   /* Mark the pages we haven't yet bound into AGP as inaccessible. */
-   if (pI830->FbMapSize > pI830->stolen_size) {
-      if (mprotect(pI830->FbBase + pI830->stolen_size,
-		   pI830->FbMapSize - pI830->stolen_size, PROT_NONE) != 0) {
-	 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
-		    "Failed to mprotect unbound AGP: %s\n", strerror(errno));
-      }
-   }
-
    return TRUE;
 }
 
diff --git a/src/i830_memory.c b/src/i830_memory.c
index 9e23c3c..a38ee78 100644
--- a/src/i830_memory.c
+++ b/src/i830_memory.c
@@ -101,7 +101,6 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 #include <string.h>
 #include <errno.h>
 #include <sys/types.h>
-#include <sys/mman.h>
 
 #include "xf86.h"
 #include "xf86_OSproc.h"
@@ -204,31 +203,15 @@ i830_bind_memory(ScrnInfoPtr pScrn, i830_memory *mem)
 					mem->allocated_size, mem->tiling);
     }
 
-    /* Mark the pages accessible now that they're bound. */
-    if (mprotect(pI830->FbBase + mem->offset, ALIGN(mem->size, GTT_PAGE_SIZE),
-		 PROT_READ | PROT_WRITE) != 0) {
-	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
-		   "Failed to mprotect %s: %s\n", mem->name, strerror(errno));
-    }
-
     return TRUE;
 }
 
 static Bool
 i830_unbind_memory(ScrnInfoPtr pScrn, i830_memory *mem)
 {
-    I830Ptr pI830 = I830PTR(pScrn);
-
     if (mem == NULL || !mem->bound)
 	return TRUE;
 
-    /* Mark the pages accessible now that they're bound. */
-    if (mprotect(pI830->FbBase + mem->offset, ALIGN(mem->size, GTT_PAGE_SIZE),
-		 PROT_NONE) != 0) {
-	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
-		   "Failed to mprotect %s: %s\n", mem->name, strerror(errno));
-    }
-
     if (mem->tiling != TILE_NONE)
 	i830_clear_tiling(pScrn, mem->fence_nr);
 
commit 552a1b824db31a234d7c5cb71057ed0e0ce64477
Author: Eric Anholt <eric at anholt.net>
Date:   Mon Mar 24 13:25:37 2008 -0700

    Disable a bunch of clock gating disables on IGD_GM, which doesn't need them.
    
    Besides our driver having fallen through to the GM965 path for
    RENCLK_GATE_D1, the BIOS was turning some of these on.  It may be relevant
    for previous platforms as well to zero out the fields that should be zero
    in the other registers.

diff --git a/src/i830_driver.c b/src/i830_driver.c
index 98f4261..c2ddf45 100644
--- a/src/i830_driver.c
+++ b/src/i830_driver.c
@@ -1887,7 +1887,11 @@ SetHWOperatingState(ScrnInfoPtr pScrn)
 
    /* Disable clock gating reported to work incorrectly according to the specs.
     */
-   if (IS_I965GM(pI830)) {
+   if (IS_IGD_GM(pI830)) {
+      OUTREG(RENCLK_GATE_D1, 0);
+      OUTREG(RENCLK_GATE_D2, 0);
+      OUTREG(DSPCLK_GATE_D, VRHUNIT_CLOCK_GATE_DISABLE);
+   } else if (IS_I965GM(pI830)) {
       OUTREG(RENCLK_GATE_D1, I965_RCC_CLOCK_GATE_DISABLE);
    } else if (IS_I965G(pI830)) {
       OUTREG(RENCLK_GATE_D1,
commit c1a2bc357fc122d3718eca771530367ba2915815
Author: Julien Cristau <jcristau at debian.org>
Date:   Mon Mar 24 13:29:24 2008 +0800

    Don't try to build XvMC if DRI is disabled
    
    Instead of failing the build, don't even try unless --enable-xvmc was used.

diff --git a/configure.ac b/configure.ac
index 5b677f0..9965e0b 100644
--- a/configure.ac
+++ b/configure.ac
@@ -67,9 +67,9 @@ AC_ARG_WITH(xserver-source,AC_HELP_STRING([--with-xserver-source=XSERVER_SOURCE]
 			   [ XSERVER_SOURCE="" ])
 
 AC_ARG_ENABLE(xvmc, AC_HELP_STRING([--disable-xvmc],
-                                  [Disable XvMC support [[default=yes]]]),
+                                  [Disable XvMC support [[default=auto]]]),
               [XVMC="$enableval"],
-              [XVMC=yes])
+              [XVMC=auto])
 
 # Checks for extensions
 XORG_DRIVER_CHECK_EXT(XINERAMA, xineramaproto)
@@ -211,6 +211,12 @@ if test "$VIDEO_DEBUG" = yes; then
 fi
 
 AC_MSG_CHECKING([whether to include XvMC support])
+if test "$XVMC" = auto; then
+	XVMC="$DRI"
+fi
+if test "$XVMC" = yes && test "$DRI" = no; then
+	AC_MSG_ERROR([XvMC can't be enabled without DRI])
+fi
 AC_MSG_RESULT([$XVMC])
 AM_CONDITIONAL(XVMC, test x$XVMC = xyes)
 if test "$XVMC" = yes; then
commit 5fcc002f77ebb66c1dc0f901a377ccf9bbc1d0bd
Author: Maxim Levitsky <maximlevitsky at gmail.com>
Date:   Mon Mar 24 13:24:12 2008 +0800

    Fix crash triggered by dpms low power mode with hardware overlay running
    
    When overlay switch crtc, it ignores current crtc dpms mode which
    might lead to hang.

diff --git a/src/i830_video.c b/src/i830_video.c
index 0d0a9a0..5939634 100644
--- a/src/i830_video.c
+++ b/src/i830_video.c
@@ -385,11 +385,13 @@ i830_overlay_switch_to_crtc (ScrnInfoPtr pScrn, xf86CrtcPtr crtc)
     I830CrtcPrivatePtr  intel_crtc = crtc->driver_private;
     int			pipeconf_reg = intel_crtc->pipe == 0 ? PIPEACONF : PIPEBCONF;
 
-    if (!IS_I965G(pI830) && (INREG(pipeconf_reg) & PIPEACONF_DOUBLE_WIDE))
+    /* overlay can't be used on pipe with double wide, and pipe must be enabled. */
+    if ((!IS_I965G(pI830) && (INREG(pipeconf_reg) & PIPEACONF_DOUBLE_WIDE))
+	    || (intel_crtc->dpms_mode == DPMSModeOff))
 	pPriv->overlayOK = FALSE;
     else
 	pPriv->overlayOK = TRUE;
-    
+
     if (!pPriv->overlayOK)
 	return;
 
@@ -1829,10 +1831,11 @@ i830_display_video(ScrnInfoPtr pScrn, xf86CrtcPtr crtc,
     
     if (crtc != pPriv->current_crtc)
     {
-        pPriv->current_crtc = crtc;
 	i830_overlay_switch_to_crtc (pScrn, crtc);
-	if (pPriv->overlayOK)
+	if (pPriv->overlayOK) {
+	    pPriv->current_crtc = crtc;
 	    I830ResetVideo (pScrn);
+	}
     }
 
     if (!pPriv->overlayOK)
commit 52d6ced652059989e6d9780a149488ccd16e3a22
Author: Jesse Barnes <jbarnes at hobbes.virtuousgeek.org>
Date:   Wed Mar 19 11:59:15 2008 -0700

    Fixup backlight control and panel fitting property names
    
    They should be listed as lower case, since that's what you'd pass to xrandr.

diff --git a/man/intel.man b/man/intel.man
index 473897a..f59ffb4 100644
--- a/man/intel.man
+++ b/man/intel.man
@@ -209,19 +209,19 @@ By adjusting the BACKLIGHT property, the brightness on the LVDS output can be ad
 .TP 2
 The driver will attempt to automatically detect the backlight control method for your platform.  If this fails however, you can select another method which may allow you to control your backlight.  Available methods include:
 .PP
-.B NATIVE
+.B native
 .TP 4
 Intel chipsets include backlight control registers, which on some platforms may be wired to control the backlight directly.  This method uses those registers.
 .PP
-.B LEGACY
+.B legacy
 .TP 4
 The legacy backlight control registers exist in PCI configuration space, and have fewer available backlight levels than the native registers.  However, some platforms are wired this way and so need to use this method.
 .PP
-.B COMBO
+.B combo
 .TP 4
 This method attempts to use the native registers where possible, resorting to the legacy, configuration space registers only to enable the backlight if needed.  On platforms that have both wired this can be a good choice as it allows the fine grained backlight control of the native interface.
 .PP
-.B KERNEL
+.B kernel
 .TP 4
 On some system, the kernel may provide a backlight control driver.  In that case, using the kernel interfaces is preferable, as the same driver may respond to hotkey events or external APIs.
 
@@ -231,15 +231,15 @@ On some system, the kernel may provide a backlight control driver.  In that case
 .TP 2
 By default, the driver will attempt to upscale resolutions smaller than the LCD's native size while preserving the aspect ratio.  Other modes are available however:
 .PP
-.B CENTER
+.B center
 .TP 4
 Simply center the image on-screen, without scaling.
 .PP
-.B FULL_ASPECT
+.B full_aspect
 .TP 4
 The default mode.  Try to upscale the image to the screen size, while preserving aspect ratio.  May result in letterboxing or pillar-boxing with some resolutions.
 .PP
-.B FULL
+.B full
 .TP 4
 Upscale the image to the native screen size without regard to aspect ratio.  In this mode, the full screen image may appear distorted in some resolutions.
 
commit ffb5a115cc62ed63110f77815b7f04976f720065
Merge: 05cf070... 24e6eb2...
Author: Jesse Barnes <jbarnes at nietzche.virtuousgeek.org>
Date:   Mon Mar 17 15:19:05 2008 -0700

    Merge branch 'master' into pfit

commit 05cf07071e25f84dec3476a9bed7235ed50cd249
Author: Jesse Barnes <jbarnes at nietzche.virtuousgeek.org>
Date:   Thu Mar 13 18:12:00 2008 -0700

    Initial panel fitting changes
    
    Basic support for panel fitting.

diff --git a/man/intel.man b/man/intel.man
index e5736e5..473897a 100644
--- a/man/intel.man
+++ b/man/intel.man
@@ -225,6 +225,24 @@ This method attempts to use the native registers where possible, resorting to th
 .TP 4
 On some system, the kernel may provide a backlight control driver.  In that case, using the kernel interfaces is preferable, as the same driver may respond to hotkey events or external APIs.
 
+.PP
+.B PANEL_FITTING
+- control LCD panel fitting
+.TP 2
+By default, the driver will attempt to upscale resolutions smaller than the LCD's native size while preserving the aspect ratio.  Other modes are available however:
+.PP
+.B CENTER
+.TP 4
+Simply center the image on-screen, without scaling.
+.PP
+.B FULL_ASPECT
+.TP 4
+The default mode.  Try to upscale the image to the screen size, while preserving aspect ratio.  May result in letterboxing or pillar-boxing with some resolutions.
+.PP
+.B FULL
+.TP 4
+Upscale the image to the native screen size without regard to aspect ratio.  In this mode, the full screen image may appear distorted in some resolutions.
+
 .SS "TV"
 Integrated TV output.  Available properties include:
 
diff --git a/src/i810_reg.h b/src/i810_reg.h
index d5b6805..d799e77 100644
--- a/src/i810_reg.h
+++ b/src/i810_reg.h
@@ -871,8 +871,7 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 
 #define PFIT_CONTROL	0x61230
 # define PFIT_ENABLE				(1 << 31)
-# define PFIT_PIPE_MASK				(3 << 29)
-# define PFIT_PIPE_SHIFT			29
+/* Pre-965 */
 # define VERT_INTERP_DISABLE			(0 << 10)
 # define VERT_INTERP_BILINEAR			(1 << 10)
 # define VERT_INTERP_MASK			(3 << 10)
@@ -882,12 +881,30 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 # define HORIZ_INTERP_MASK			(3 << 6)
 # define HORIZ_AUTO_SCALE			(1 << 5)
 # define PANEL_8TO6_DITHER_ENABLE		(1 << 3)
+/* 965+ */
+# define PFIT_PIPE_MASK				(3 << 29)
+# define PFIT_PIPE_SHIFT			29
+# define PFIT_SCALING_MODE_MASK			(7 << 26)
+#  define PFIT_SCALING_AUTO			(0 << 26)
+#  define PFIT_SCALING_PROGRAMMED		(1 << 26)
+#  define PFIT_SCALING_PILLAR			(2 << 26)
+#  define PFIT_SCALING_LETTER			(3 << 26)
+# define PFIT_FILTER_SELECT_MASK		(3 << 24)
+#  define PFIT_FILTER_FUZZY			(0 << 24)
+#  define PFIT_FILTER_CRISP			(1 << 24)
+#  define PFIT_FILTER_MEDIAN			(2 << 24)
 
 #define PFIT_PGM_RATIOS	0x61234
+/* Pre-965 */
+# define PFIT_VERT_SCALE_SHIFT			20
 # define PFIT_VERT_SCALE_MASK			0xfff00000
+# define PFIT_HORIZ_SCALE_SHIFT			4
 # define PFIT_HORIZ_SCALE_MASK			0x0000fff0
-
-#define PFIT_AUTO_RATIOS	0x61238
+/* 965+ */
+# define PFIT_VERT_SCALE_SHIFT_965		16
+# define PFIT_VERT_SCALE_MASK_965		0x1fff0000
+# define PFIT_HORIZ_SCALE_SHIFT_965		0
+# define PFIT_HORIZ_SCALE_MASK_965		0x00001fff
 
 #define DPLL_A		0x06014
 #define DPLL_B		0x06018
diff --git a/src/i830_lvds.c b/src/i830_lvds.c
index a75d7e6..daf71da 100644
--- a/src/i830_lvds.c
+++ b/src/i830_lvds.c
@@ -44,12 +44,25 @@
 #include "i830_display.h"
 #include "X11/Xatom.h"
 
+/*
+ * Three panel fitting modes:
+ * CENTER - center image on screen, don't scale
+ * FULL_ASPECT - scale image to fit screen, but preserve aspect ratio
+ * FULL - scale image to fit screen without regard to aspect ratio
+ */
+enum pfit_mode {
+    CENTER = 0,
+    FULL_ASPECT,
+    FULL,
+};
+
 struct i830_lvds_priv {
     /* The BIOS's fixed timings for the LVDS */
     DisplayModePtr panel_fixed_mode;
     
     /* The panel needs dithering enabled */
     Bool	    panel_wants_dither;
+    Bool	    need_border;
 
     /* restore backlight to this value */
     int		    backlight_duty_cycle;
@@ -57,6 +70,9 @@ struct i830_lvds_priv {
     void (*set_backlight)(xf86OutputPtr output, int level);
     int (*get_backlight)(xf86OutputPtr output);
     int backlight_max;
+    enum pfit_mode fitting_mode;
+    uint32_t pfit_control;
+    uint32_t pfit_pgm_ratios;
 };
 
 #define BACKLIGHT_CLASS "/sys/class/backlight"
@@ -481,7 +497,13 @@ i830_lvds_mode_fixup(xf86OutputPtr output, DisplayModePtr mode,
     ScrnInfoPtr		    pScrn = output->scrn;
     xf86CrtcConfigPtr	    xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
     I830CrtcPrivatePtr	    intel_crtc = output->crtc->driver_private;
+    I830Ptr		    pI830 = I830PTR(pScrn);
+    uint32_t		    pfit_control = 0, pfit_pgm_ratios = 0;
+    float		    panel_ratio, desired_ratio, vert_scale, horiz_scale;
+    float		    horiz_ratio, vert_ratio;
+    int left_border = 0, right_border = 0, top_border = 0, bottom_border = 0;
     int i;
+    Bool border = 0;
 
     for (i = 0; i < xf86_config->num_output; i++) {
 	xf86OutputPtr other_output = xf86_config->output[i];
@@ -500,24 +522,207 @@ i830_lvds_mode_fixup(xf86OutputPtr output, DisplayModePtr mode,
 	return FALSE;
     }
 
+    /* If we don't have a panel mode there's not much we can do */
+    if (dev_priv->panel_fixed_mode == NULL)
+	return TRUE;
+
     /* If we have timings from the BIOS for the panel, put them in
      * to the adjusted mode.  The CRTC will be set up for this mode,
      * with the panel scaling set up to source from the H/VDisplay
      * of the original mode.
      */
-    if (dev_priv->panel_fixed_mode != NULL) {
-	adjusted_mode->HDisplay = dev_priv->panel_fixed_mode->HDisplay;
-	adjusted_mode->HSyncStart = dev_priv->panel_fixed_mode->HSyncStart;
-	adjusted_mode->HSyncEnd = dev_priv->panel_fixed_mode->HSyncEnd;
-	adjusted_mode->HTotal = dev_priv->panel_fixed_mode->HTotal;
-	adjusted_mode->VDisplay = dev_priv->panel_fixed_mode->VDisplay;
-	adjusted_mode->VSyncStart = dev_priv->panel_fixed_mode->VSyncStart;
-	adjusted_mode->VSyncEnd = dev_priv->panel_fixed_mode->VSyncEnd;
-	adjusted_mode->VTotal = dev_priv->panel_fixed_mode->VTotal;
-	adjusted_mode->Clock = dev_priv->panel_fixed_mode->Clock;
-	xf86SetModeCrtc(adjusted_mode, INTERLACE_HALVE_V);
+    adjusted_mode->HDisplay = dev_priv->panel_fixed_mode->HDisplay;
+    adjusted_mode->HSyncStart = dev_priv->panel_fixed_mode->HSyncStart;
+    adjusted_mode->HSyncEnd = dev_priv->panel_fixed_mode->HSyncEnd;
+    adjusted_mode->HTotal = dev_priv->panel_fixed_mode->HTotal;
+    adjusted_mode->VDisplay = dev_priv->panel_fixed_mode->VDisplay;
+    adjusted_mode->VSyncStart = dev_priv->panel_fixed_mode->VSyncStart;
+    adjusted_mode->VSyncEnd = dev_priv->panel_fixed_mode->VSyncEnd;
+    adjusted_mode->VTotal = dev_priv->panel_fixed_mode->VTotal;
+    adjusted_mode->Clock = dev_priv->panel_fixed_mode->Clock;
+    xf86SetModeCrtc(adjusted_mode, INTERLACE_HALVE_V);
+
+    /* Native modes don't need fitting */
+    if (adjusted_mode->HDisplay == mode->HDisplay &&
+	adjusted_mode->VDisplay == mode->VDisplay) {
+	pfit_control = 0;
+	pfit_pgm_ratios = 0;
+	border = 0;
+	goto out;
+    }
+
+    /* Basic panel fitting options */
+    if (!IS_I965G(pI830)) {
+	if (dev_priv->panel_wants_dither)
+	    pfit_control |= PANEL_8TO6_DITHER_ENABLE;
+    } else {
+	pfit_control |= (intel_crtc->pipe << PFIT_PIPE_SHIFT) |
+	    PFIT_FILTER_FUZZY;
     }
 
+    /*
+     * Deal with panel fitting options.  Figure out how to stretch the image
+     * based on its aspect ratio & the current panel fitting mode.
+     */
+    panel_ratio = (float)adjusted_mode->HDisplay /
+ 	(float)adjusted_mode->VDisplay;
+    desired_ratio = (float)mode->HDisplay /
+	(float)mode->VDisplay;
+
+    /*
+     * Enable automatic panel scaling for non-native modes so that they fill
+     * the screen.  Should be enabled before the pipe is enabled, according to
+     * register description and PRM.
+     */
+    /* Change the value here to see the borders for debugging */
+    OUTREG(BCLRPAT_A, 0);
+    OUTREG(BCLRPAT_B, 0);
+    switch (dev_priv->fitting_mode) {
+    case CENTER:
+	/*
+	 * For centered modes, we have to calculate border widths & heights and
+	 * modify the values programmed into the CRTC.  Also need to make sure
+	 * LVDS borders are enabled (see i830_display.c).
+	 */
+	left_border =
+	    (dev_priv->panel_fixed_mode->HDisplay - mode->HDisplay) / 2;
+	right_border = left_border;
+	if (mode->HDisplay & 1)
+	    right_border++;
+	top_border =
+	    (dev_priv->panel_fixed_mode->VDisplay - mode->VDisplay) / 2;
+	bottom_border = top_border;
+	if (mode->VDisplay & 1)
+	    bottom_border++;
+
+	/* Set active & border values */
+	adjusted_mode->CrtcHDisplay = mode->HDisplay;
+	adjusted_mode->CrtcHBlankStart = mode->HDisplay + right_border - 1;
+	adjusted_mode->CrtcHBlankEnd = adjusted_mode->CrtcHTotal -
+	    left_border - 1;
+	adjusted_mode->CrtcHSyncStart = adjusted_mode->CrtcHBlankStart;
+	adjusted_mode->CrtcHSyncEnd = adjusted_mode->CrtcHBlankEnd;
+	adjusted_mode->CrtcVDisplay = mode->VDisplay;
+	adjusted_mode->CrtcVBlankStart = mode->VDisplay + bottom_border - 1;
+	adjusted_mode->CrtcVBlankEnd = adjusted_mode->CrtcVTotal -
+	    top_border - 1;
+	adjusted_mode->CrtcVSyncStart = adjusted_mode->CrtcVBlankStart;
+	adjusted_mode->CrtcVSyncEnd = adjusted_mode->CrtcVBlankEnd;
+	border = 1;
+	break;
+    case FULL_ASPECT:
+	/* Scale but preserve aspect ratio */
+	pfit_control |= PFIT_ENABLE;
+	if (IS_I965G(pI830)) {
+	    /*
+	     * 965+ is easy, it does everything in hw
+	     */
+	    if (panel_ratio > desired_ratio)
+		pfit_control |= PFIT_SCALING_PILLAR;
+	    else if (panel_ratio < desired_ratio)
+		pfit_control |= PFIT_SCALING_LETTER;
+	    else
+		pfit_control |= PFIT_SCALING_AUTO;
+	} else {
+	    /*
+	     * For earlier chips we have to calculate the scaling ratio
+	     * by hand and program it into the PFIT_PGM_RATIOS reg.
+	     */
+	    uint32_t horiz_bits, vert_bits, bits = 12;
+
+	    horiz_ratio = ((float)mode->HDisplay) /
+		((float)adjusted_mode->HDisplay);
+	    vert_ratio = ((float)mode->VDisplay) /
+		((float)adjusted_mode->VDisplay);
+
+	    horiz_scale = ((float)adjusted_mode->HDisplay) /
+		((float)mode->HDisplay);
+	    vert_scale = ((float)adjusted_mode->VDisplay) /
+		((float)mode->VDisplay);
+
+	    /* Retain aspect ratio */
+	    if (panel_ratio > desired_ratio) { /* Pillar */
+		unsigned long scaled_width = (float)mode->HDisplay * vert_scale;
+
+		horiz_ratio = vert_ratio;
+		pfit_control |= VERT_AUTO_SCALE | VERT_INTERP_BILINEAR |
+		    HORIZ_INTERP_BILINEAR;
+
+		/* Pillar will have left/right borders */
+		left_border =  (dev_priv->panel_fixed_mode->HDisplay -
+				scaled_width) / 2;
+		right_border = left_border;
+		if (mode->HDisplay & 1) /* odd resolutions */
+		    right_border++;
+
+		adjusted_mode->CrtcHDisplay = scaled_width;
+		adjusted_mode->CrtcHBlankStart = scaled_width +
+		    right_border - 1;
+		adjusted_mode->CrtcHBlankEnd = adjusted_mode->CrtcHTotal -
+		    left_border - 1;
+		adjusted_mode->CrtcHSyncStart = adjusted_mode->CrtcHBlankStart;
+		adjusted_mode->CrtcHSyncEnd = adjusted_mode->CrtcHBlankEnd;
+		border = 1;
+	    } else if (panel_ratio < desired_ratio) { /* Letter */
+		unsigned long scaled_height = (float)mode->VDisplay *
+		    horiz_scale;
+
+		vert_ratio = horiz_ratio;
+		pfit_control |= HORIZ_AUTO_SCALE | VERT_INTERP_BILINEAR |
+		    HORIZ_INTERP_BILINEAR;
+
+		/* Letterbox will have top/bottom borders */
+		top_border = (dev_priv->panel_fixed_mode->VDisplay -
+			      mode->VDisplay) / 2;
+		bottom_border = top_border;
+		if (mode->VDisplay & 1)
+		    bottom_border++;
+
+		adjusted_mode->CrtcVDisplay = scaled_height;
+		adjusted_mode->CrtcVBlankStart = scaled_height +
+		    bottom_border - 1;
+		adjusted_mode->CrtcVBlankEnd = adjusted_mode->CrtcVTotal -
+		    top_border - 1;
+		adjusted_mode->CrtcVSyncStart = adjusted_mode->CrtcVBlankStart;
+		adjusted_mode->CrtcVSyncEnd = adjusted_mode->CrtcVBlankEnd;
+		border = 1;
+	    } else { /* Aspects match, let hw scale both directions */
+		pfit_control |= VERT_AUTO_SCALE | HORIZ_AUTO_SCALE |
+		    VERT_INTERP_BILINEAR | HORIZ_INTERP_BILINEAR;
+	    }
+
+	    horiz_bits = 0.5 + (1 << bits) * horiz_ratio;
+	    vert_bits = 0.5 + (1 << bits) * vert_ratio;
+
+	    pfit_pgm_ratios = (((vert_bits << PFIT_VERT_SCALE_SHIFT) &
+				PFIT_VERT_SCALE_MASK) |
+			       ((horiz_bits << PFIT_HORIZ_SCALE_SHIFT) &
+				PFIT_HORIZ_SCALE_MASK));
+	}
+	break;
+    case FULL:
+	/*
+	 * Full scaling, even if it changes the aspect ratio.  Fortunately
+	 * this is all done for us in hw.
+	 */
+	pfit_control |= PFIT_ENABLE;
+	if (IS_I965G(pI830))
+	    pfit_control |= PFIT_SCALING_AUTO;
+	else
+	    pfit_control |= VERT_AUTO_SCALE | HORIZ_AUTO_SCALE |
+		VERT_INTERP_BILINEAR | HORIZ_INTERP_BILINEAR;
+	break;
+    default:
+	/* shouldn't happen */
+	xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "error: bad fitting mode\n");
+	break;
+    }
+  
+out:
+    dev_priv->pfit_control = pfit_control;
+    dev_priv->pfit_pgm_ratios = pfit_pgm_ratios;
+    dev_priv->need_border = border;
+
     /* XXX: It would be nice to support lower refresh rates on the
      * panels to reduce power consumption, and perhaps match the
      * user's requested refresh rate.
@@ -527,42 +732,43 @@ i830_lvds_mode_fixup(xf86OutputPtr output, DisplayModePtr mode,
 }
 
 static void
-i830_lvds_mode_set(xf86OutputPtr output, DisplayModePtr mode,
-		   DisplayModePtr adjusted_mode)
+i830_lvds_prepare(xf86OutputPtr output)
 {
     I830OutputPrivatePtr    intel_output = output->driver_private;
     struct i830_lvds_priv   *dev_priv = intel_output->dev_priv;
     ScrnInfoPtr		    pScrn = output->scrn;
     I830Ptr		    pI830 = I830PTR(pScrn);
-    I830CrtcPrivatePtr	    intel_crtc = output->crtc->driver_private;
-    uint32_t		    pfit_control;
+    uint32_t		    lvds;
 
-    /* The LVDS pin pair will already have been turned on in
-     * i830_crtc_mode_set since it has a large impact on the DPLL settings.
-     */
+    lvds = INREG(LVDS);
 
-    /* Enable automatic panel scaling for non-native modes so that they fill
-     * the screen.  Should be enabled before the pipe is enabled, according to
-     * register description and PRM.
+    i830_lvds_dpms(output, DPMSModeOff);
+    /*
+     * ->prepare will be called after the CRTC is off but before
+     * we set the mode, so program the PFIT regs here.
      */
-    if (mode->HDisplay != adjusted_mode->HDisplay ||
-	mode->VDisplay != adjusted_mode->VDisplay)
-    {
-	pfit_control = PFIT_ENABLE |
-	    VERT_AUTO_SCALE | HORIZ_AUTO_SCALE |
-	    VERT_INTERP_BILINEAR | HORIZ_INTERP_BILINEAR;
-    } else {
-	pfit_control = 0;
-    }
+    if (dev_priv->need_border)
+	OUTREG(LVDS, lvds | LVDS_BORDER_ENABLE);
+    else
+	OUTREG(LVDS, lvds & (~LVDS_BORDER_ENABLE));
+}
 
-    if (!IS_I965G(pI830)) {
-	if (dev_priv->panel_wants_dither)
-	    pfit_control |= PANEL_8TO6_DITHER_ENABLE;
-    } else {
-	pfit_control |= intel_crtc->pipe << PFIT_PIPE_SHIFT;
-    }
+static void
+i830_lvds_mode_set(xf86OutputPtr output, DisplayModePtr mode,
+		   DisplayModePtr adjusted_mode)
+{
+    I830OutputPrivatePtr    intel_output = output->driver_private;
+    struct i830_lvds_priv   *dev_priv = intel_output->dev_priv;
+    ScrnInfoPtr		    pScrn = output->scrn;
+    I830Ptr		    pI830 = I830PTR(pScrn);
 
-    OUTREG(PFIT_CONTROL, pfit_control);
+    /*
+     * PFIT must be enabled/disabled while LVDS is on but pipes are still off
+     */
+    OUTREG(PFIT_PGM_RATIOS, dev_priv->pfit_pgm_ratios);
+    OUTREG(PFIT_CONTROL, dev_priv->pfit_control);
+    /* It's harmless to turn on the LVDS if it's already on */
+    i830_lvds_dpms(output, DPMSModeOn);
 }
 
 /**
@@ -653,6 +859,17 @@ static char *backlight_control_names[] = {
 static Atom backlight_control_atom;
 static Atom backlight_control_name_atoms[NUM_BACKLIGHT_CONTROL_METHODS];
 
+#define PANEL_FITTING_NAME "PANEL_FITTING"
+#define NUM_PANEL_FITTING_TYPES 3
+static char *panel_fitting_names[] = {
+    "center",
+    "full_aspect",
+    "full",
+};
+static Atom panel_fitting_atom;
+static Atom panel_fitting_name_atoms[NUM_PANEL_FITTING_TYPES];
+
+
 static int
 i830_backlight_control_lookup(char *name)
 {
@@ -709,6 +926,18 @@ i830_lvds_set_backlight_control(xf86OutputPtr output)
 
     return Success;
 }
+
+static int
+i830_panel_fitting_lookup(char *name)
+{
+    int i;
+
+    for (i = 0; i < NUM_PANEL_FITTING_TYPES; i++)
+	if (!strcmp(name, panel_fitting_names[i]))
+	    return i;
+
+    return -1;
+}
 #endif /* RANDR_12_INTERFACE */
 
 static void
@@ -775,6 +1004,33 @@ i830_lvds_create_resources(xf86OutputPtr output)
 	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
 		   "failed to set backlight control, %d\n", err);
     }
+
+    /*
+     * Panel fitting control
+     */
+    panel_fitting_atom = MakeAtom(PANEL_FITTING_NAME,
+				  sizeof(PANEL_FITTING_NAME) - 1, TRUE);
+    for (i = 0; i < NUM_PANEL_FITTING_TYPES; i++) {
+	panel_fitting_name_atoms[i] = MakeAtom(panel_fitting_names[i],
+					       strlen(panel_fitting_names[i]),
+					       TRUE);
+    }
+    err = RRConfigureOutputProperty(output->randr_output,
+				    panel_fitting_atom, TRUE, FALSE, FALSE,
+				    NUM_PANEL_FITTING_TYPES,
+				    (INT32 *)panel_fitting_name_atoms);
+    if (err != 0) {
+	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+		   "RRConfigureOutputProperty error, %d\n", err);
+    }
+    err = RRChangeOutputProperty(output->randr_output, panel_fitting_atom,
+				 XA_ATOM, 32, PropModeReplace, 1,
+				 &panel_fitting_name_atoms[dev_priv->fitting_mode],
+				 FALSE, TRUE);
+    if (err != 0) {
+	xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+		   "failed to set panel fitting mode, %d\n", err);
+    }   
 #endif /* RANDR_12_INTERFACE */
 }
 
@@ -846,6 +1102,36 @@ i830_lvds_set_property(xf86OutputPtr output, Atom property,
 		       "RRChangeOutputProperty error, %d\n", ret);
 	}
 	return TRUE;
+    } else if (property == panel_fitting_atom) {
+	Atom			atom;
+	char			*name;
+	int			ret;
+
+	if (value->type != XA_ATOM || value->format != 32 || value->size != 1)
+	    return FALSE;
+
+	memcpy(&atom, value->data, 4);
+	name = NameForAtom(atom);
+	
+	ret = i830_panel_fitting_lookup(name);
+	if (ret < 0)
+	    return FALSE;
+
+	dev_priv->fitting_mode = ret;
+
+	if (output->crtc) {
+	    xf86CrtcPtr crtc = output->crtc;
+	    if (crtc->enabled) {
+		if (!xf86CrtcSetMode(crtc, &crtc->desiredMode,
+				     crtc->desiredRotation,
+				     crtc->desiredX, crtc->desiredY)) {
+		    xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
+			       "Failed to set mode after panel fitting change!\n");
+		    return FALSE;
+		}
+	    }
+	}
+	return TRUE;
     }
 
     return TRUE;
@@ -886,7 +1172,7 @@ static const xf86OutputFuncsRec i830_lvds_output_funcs = {
     .restore = i830_lvds_restore,
     .mode_valid = i830_lvds_mode_valid,
     .mode_fixup = i830_lvds_mode_fixup,
-    .prepare = i830_output_prepare,
+    .prepare = i830_lvds_prepare,
     .mode_set = i830_lvds_mode_set,
     .commit = i830_output_commit,
     .detect = i830_lvds_detect,
@@ -1075,6 +1361,12 @@ i830_lvds_init(ScrnInfoPtr pScrn)
 
     dev_priv->backlight_duty_cycle = dev_priv->get_backlight(output);
 
+    /*
+     * Default to filling the whole screen if the mode is less than the
+     * native size, without breaking aspect ratio.
+     */
+    dev_priv->fitting_mode = FULL_ASPECT;
+
     return;
 
 disable_exit:


More information about the xorg-commit mailing list