Here's my patch below. Sorry for late response. I wonder what pixmap_is_scanout does. It always returns FALSE. Patch for intel driver 2.14.0 (the one in Ubuntu distro). Gen6 wait for scanline event support -------------------------------- src/i830_reg.h -------------------------------- index 93d03cf..0a5946c 100644 @@ -65,6 +65,19 @@ #define MI_LOAD_SCAN_LINES_DISPLAY_PIPEA (0) #define MI_LOAD_SCAN_LINES_DISPLAY_PIPEB (0x1<<20) +/* Gen6 wait for scan line support */ +#define MI_LOAD_REGISTER_IMM (0x22<<23) +#define MI_DISPLAY_PIPEA_SCAN_LINE_WAIT (1) +#define MI_DISPLAY_PIPEB_SCAN_LINE_WAIT (1<<8) +#define MI_DISPLAY_PIPEA_VBLANK_WAIT (1<<3) +#define MI_DISPLAY_PIPEB_VBLANK_WAIT (1<<11) + +/* Scan lines register */ +#define DE_LOAD_SL_ADDR (0x4f100) +#define DE_LOAD_SL_PIPEA (0x110<<29) +#define DE_LOAD_SL_PIPEB (0x111<<29) +#define DERRMR_ADDR (0x44050) + /* BLT commands */ #define COLOR_BLT_CMD ((2<<29)|(0x40<<22)|(0x3)) #define COLOR_BLT_WRITE_ALPHA (1<<21) ------------------------------ src/intel_video.c ------------------------------ index 5294f73..506178f 100644 @@ -1365,6 +1365,83 @@ intel_wait_for_scanline(ScrnInfoPtr scrn, PixmapPtr pixmap, ADVANCE_BATCH(); } +static void +intel_wait_for_scanline_gen6(ScrnInfoPtr scrn, PixmapPtr pixmap, + xf86CrtcPtr crtc, RegionPtr clipBoxes) +{ + intel_screen_private *intel = intel_get_screen_private(scrn); + pixman_box16_t box, crtc_box; + int pipe, event; + Bool full_height; + int y1, y2; + + pipe = -1; + if (pixmap_is_scanout(pixmap)) + { + pipe = intel_crtc_to_pipe(crtc); + } + if (pipe < 0) + return; + + box = *REGION_EXTENTS(unused, clipBoxes); + + if (crtc->transform_in_use) + pixman_f_transform_bounds(&crtc->f_framebuffer_to_crtc, &box); + + /* We could presume the clip was correctly computed... */ + intel_crtc_box(crtc, &crtc_box); + intel_box_intersect(&box, &crtc_box, &box); + + /* + * Make sure we don't wait for a scanline that will + * never occur + */ + y1 = (crtc_box.y1 <= box.y1) ? box.y1 - crtc_box.y1 : 0; + y2 = (box.y2 <= crtc_box.y2) ? + box.y2 - crtc_box.y1 : crtc_box.y2 - crtc_box.y1; + + if (y2 <= y1) + return; + + full_height = FALSE; + if (y1 == 0 && y2 == (crtc_box.y2 - crtc_box.y1)) + full_height = TRUE; + + if (pipe == 0) { + pipe = DE_LOAD_SL_PIPEA; + event = MI_DISPLAY_PIPEA_SCAN_LINE_WAIT; + if (full_height) + event = MI_DISPLAY_PIPEA_VBLANK_WAIT; + } else { + pipe = DE_LOAD_SL_PIPEB; + event = MI_DISPLAY_PIPEB_SCAN_LINE_WAIT; + if (full_height) + event = MI_DISPLAY_PIPEB_VBLANK_WAIT; + } + + /* According to docs only upper 10 bits are significant */ + if(!(y2 & 0x3)) + y2 += 8; + + + y1 &= 0x1ff8; + y2 &= 0x1ff8; + + if (crtc->mode.Flags & V_INTERLACE) { + /* DSL count field lines */ + y1 /= 2; + y2 /= 2; + } + + BEGIN_BATCH(4); + OUT_BATCH(MI_LOAD_REGISTER_IMM | 1); + OUT_BATCH(DE_LOAD_SL_ADDR); + OUT_BATCH(pipe | (y1 << 16) | y2); + OUT_BATCH(MI_WAIT_FOR_EVENT | event); + ADVANCE_BATCH(); +} + + static Bool intel_setup_video_buffer(ScrnInfoPtr scrn, intel_adaptor_private *adaptor_priv, int alloc_size, int id, unsigned char *buf) @@ -1578,8 +1655,11 @@ I830PutImageTextured(ScrnInfoPtr scrn, return BadAlloc; } - if (crtc && adaptor_priv->SyncToVblank != 0 && INTEL_INFO(intel)->gen < 60) { - intel_wait_for_scanline(scrn, pixmap, crtc, clipBoxes); + if (crtc && adaptor_priv->SyncToVblank != 0) { + if(INTEL_INFO(intel)->gen < 60) + intel_wait_for_scanline(scrn, pixmap, crtc, clipBoxes); + else + intel_wait_for_scanline_gen6(scrn, pixmap, crtc, clipBoxes); } if (INTEL_INFO(intel)->gen >= 60) {