diff options
author | Chris Wilson <chris@chris-wilson.co.uk> | 2010-08-25 12:56:43 +0100 |
---|---|---|
committer | Chris Wilson <chris@chris-wilson.co.uk> | 2010-09-08 13:33:37 +0100 |
commit | 2b96c18165d713cd6781dbf217ec33e11cc961bc (patch) | |
tree | 92b4c9b3b0fa31e0ec20b6ac348011de9ea59df2 | |
parent | 0fa4321a765126228170ecb9536f32c134886d51 (diff) |
Enable a shadow buffer and disable GPU acceleration.
An attempt to workaround the incoherency in gen2 chipsets, we avoid
using dynamic reallocation as much as possible.
The first step is to disable allocation of pixmaps using GEM and simply
create them in system memory without a backing buffer object. This
forces all rendering to use S/W fallbacks.
The second step is to allocate a shadow front buffer and assign that to
the Screen pixmap. This ensure that the front buffer remains in the GTT
and pinned for scanout. The shadow buffer will be rendered to in the
normal fashion via the Screen pixmap, and be marked dirty. In the block
handler, the dirty shadow buffer is then blitted (using the GPU) over
the front buffer. This should completely avoid having to move pages
around in the GTT and avoid incurring the wrath of those early chipsets.
Secondly, performance should be reasonable as we avoid the ping-pong
caused by the small aperture and weak GPU forcing software fallbacks.
Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
-rw-r--r-- | man/intel.man | 14 | ||||
-rw-r--r-- | src/intel.h | 14 | ||||
-rw-r--r-- | src/intel_batchbuffer.h | 3 | ||||
-rw-r--r-- | src/intel_display.c | 45 | ||||
-rw-r--r-- | src/intel_dri.c | 9 | ||||
-rw-r--r-- | src/intel_driver.c | 52 | ||||
-rw-r--r-- | src/intel_memory.c | 4 | ||||
-rw-r--r-- | src/intel_uxa.c | 217 | ||||
-rw-r--r-- | src/intel_video.c | 4 | ||||
-rw-r--r-- | uxa/uxa-glyphs.c | 27 | ||||
-rw-r--r-- | uxa/uxa.c | 15 |
11 files changed, 342 insertions, 62 deletions
diff --git a/man/intel.man b/man/intel.man index c2447bec..31860f2c 100644 --- a/man/intel.man +++ b/man/intel.man @@ -156,6 +156,20 @@ i.e. perform synchronous rendering. .IP Default: Disabled .TP +.BI "Option \*qShadow\*q \*q" boolean \*q +This option controls the use of GPU acceleration and placement of auxiliary +buffers in memory. Enabling the Shadow will disable all use of the GPU for +RENDER acceleration and force software-fallbacks for all but updating the +scan-out buffer. Hardware overlay is still supported so Xv will continue to +playback videos using the GPU, but GL will be forced to use software +rasterisation as well. This is a last resort measure for systems with +crippling bugs, such as early 8xx chipsets. It is still hoped that we will +find a workaround to enable as much hardware acceleration on those +architectures as is possible, but until then, using a shadow buffer should +maintain system stability. +.IP +Default: Disabled +.TP .BI "Option \*qSwapbuffersWait\*q \*q" boolean \*q This option controls the behavior of glXSwapBuffers and glXCopySubBufferMESA calls by GL applications. If enabled, the calls will avoid tearing by making diff --git a/src/intel.h b/src/intel.h index 9e8323c2..c258a87e 100644 --- a/src/intel.h +++ b/src/intel.h @@ -271,6 +271,7 @@ enum dri_type { }; typedef struct intel_screen_private { + ScrnInfoPtr scrn; unsigned char *MMIOBase; int cpp; @@ -281,7 +282,10 @@ typedef struct intel_screen_private { long GTTMapSize; void *modes; - drm_intel_bo *front_buffer; + drm_intel_bo *front_buffer, *shadow_buffer; + long front_pitch, front_tiling; + PixmapPtr shadow_pixmap; + DamagePtr shadow_damage; dri_bufmgr *bufmgr; @@ -415,6 +419,7 @@ typedef struct intel_screen_private { Bool use_pageflipping; Bool force_fallback; + Bool use_shadow; /* Broken-out options. */ OptionInfoPtr Options; @@ -446,7 +451,9 @@ extern int intel_get_pipe_from_crtc_id(drm_intel_bufmgr *bufmgr, xf86CrtcPtr crt extern int intel_crtc_id(xf86CrtcPtr crtc); extern int intel_output_dpms_status(xf86OutputPtr output); -extern Bool intel_do_pageflip(ScreenPtr screen, dri_bo *new_front, void *data); +extern Bool intel_do_pageflip(intel_screen_private *intel, + dri_bo *new_front, + void *data); static inline intel_screen_private * intel_get_screen_private(ScrnInfoPtr scrn) @@ -501,7 +508,8 @@ void intel_set_gem_max_sizes(ScrnInfoPtr scrn); drm_intel_bo *intel_allocate_framebuffer(ScrnInfoPtr scrn, int w, int h, int cpp, - unsigned long *pitch); + unsigned long *pitch, + uint32_t *tiling); /* i830_render.c */ Bool i830_check_composite(int op, diff --git a/src/intel_batchbuffer.h b/src/intel_batchbuffer.h index 02997bab..bf7a5d90 100644 --- a/src/intel_batchbuffer.h +++ b/src/intel_batchbuffer.h @@ -153,6 +153,9 @@ intel_batch_emit_reloc_pixmap(intel_screen_private *intel, PixmapPtr pixmap, #define OUT_RELOC(bo, read_domains, write_domains, delta) \ intel_batch_emit_reloc(intel, bo, read_domains, write_domains, delta, 0) +#define OUT_RELOC_FENCED(bo, read_domains, write_domains, delta) \ + intel_batch_emit_reloc(intel, bo, read_domains, write_domains, delta, 1) + #define OUT_RELOC_PIXMAP(pixmap, reads, write, delta) \ intel_batch_emit_reloc_pixmap(intel, pixmap, reads, write, delta, 0) diff --git a/src/intel_display.c b/src/intel_display.c index ed3fdd07..e22c4153 100644 --- a/src/intel_display.c +++ b/src/intel_display.c @@ -488,12 +488,14 @@ intel_crtc_shadow_allocate(xf86CrtcPtr crtc, int width, int height) struct intel_crtc *intel_crtc = crtc->driver_private; struct intel_mode *mode = intel_crtc->mode; unsigned long rotate_pitch; + uint32_t tiling; int ret; intel_crtc->rotate_bo = intel_allocate_framebuffer(scrn, width, height, mode->cpp, - &rotate_pitch); + &rotate_pitch, + &tiling); if (!intel_crtc->rotate_bo) { xf86DrvMsg(crtc->scrn->scrnIndex, X_ERROR, @@ -580,7 +582,7 @@ intel_crtc_shadow_destroy(xf86CrtcPtr crtc, PixmapPtr rotate_pixmap, void *data) intel_crtc->rotate_bo = NULL; } - intel->shadow_present = FALSE; + intel->shadow_present = intel->use_shadow; } static void @@ -1310,11 +1312,10 @@ intel_xf86crtc_resize(ScrnInfoPtr scrn, int width, int height) intel_screen_private *intel = intel_get_screen_private(scrn); drm_intel_bo *old_front = NULL; Bool ret; - ScreenPtr screen = screenInfo.screens[scrn->scrnIndex]; - PixmapPtr pixmap; uint32_t old_fb_id; int i, old_width, old_height, old_pitch; unsigned long pitch; + uint32_t tiling; if (scrn->virtualX == width && scrn->virtualY == height) return TRUE; @@ -1328,7 +1329,8 @@ intel_xf86crtc_resize(ScrnInfoPtr scrn, int width, int height) intel->front_buffer = intel_allocate_framebuffer(scrn, width, height, intel->cpp, - &pitch); + &pitch, + &tiling); if (!intel->front_buffer) goto fail; @@ -1339,14 +1341,11 @@ intel_xf86crtc_resize(ScrnInfoPtr scrn, int width, int height) if (ret) goto fail; + intel->front_pitch = pitch; + intel->front_tiling = tiling; + scrn->virtualX = width; scrn->virtualY = height; - scrn->displayWidth = pitch / intel->cpp; - - pixmap = screen->GetScreenPixmap(screen); - screen->ModifyPixmapHeader(pixmap, width, height, -1, -1, pitch, NULL); - intel_set_pixmap_bo(pixmap, intel->front_buffer); - intel_get_pixmap_private(pixmap)->busy = 1; for (i = 0; i < xf86_config->num_crtc; i++) { xf86CrtcPtr crtc = xf86_config->crtc[i]; @@ -1358,6 +1357,8 @@ intel_xf86crtc_resize(ScrnInfoPtr scrn, int width, int height) goto fail; } + intel_uxa_create_screen_resources(scrn->pScreen); + if (old_fb_id) drmModeRmFB(mode->fd, old_fb_id); if (old_front) @@ -1380,10 +1381,11 @@ fail: } Bool -intel_do_pageflip(ScreenPtr screen, dri_bo *new_front, void *data) +intel_do_pageflip(intel_screen_private *intel, + dri_bo *new_front, + void *data) { - ScrnInfoPtr scrn = xf86Screens[screen->myNum]; - intel_screen_private *intel = intel_get_screen_private(scrn); + ScrnInfoPtr scrn = intel->scrn; xf86CrtcConfigPtr config = XF86_CRTC_CONFIG_PTR(scrn); struct intel_crtc *crtc = config->crtc[0]->driver_private; struct intel_mode *mode = crtc->mode; @@ -1454,22 +1456,31 @@ intel_page_flip_handler(int fd, unsigned int frame, unsigned int tv_sec, { struct intel_mode *mode = event_data; + mode->flip_count--; if (mode->flip_count > 0) return; drmModeRmFB(mode->fd, mode->old_fb_id); + if (mode->event_data == NULL) + return; + I830DRI2FlipEventHandler(frame, tv_sec, tv_usec, mode->event_data); } static void drm_wakeup_handler(pointer data, int err, pointer p) { - struct intel_mode *mode = data; - fd_set *read_mask = p; + struct intel_mode *mode; + fd_set *read_mask; + + if (data == NULL || err < 0) + return; - if (err >= 0 && FD_ISSET(mode->fd, read_mask)) + mode = data; + read_mask = p; + if (FD_ISSET(mode->fd, read_mask)) drmHandleEvent(mode->fd, &mode->event_context); } diff --git a/src/intel_dri.c b/src/intel_dri.c index 07782c60..db1f81ab 100644 --- a/src/intel_dri.c +++ b/src/intel_dri.c @@ -488,10 +488,10 @@ I830DRI2ExchangeBuffers(DrawablePtr draw, DRI2BufferPtr front, * flipping buffers as necessary. */ static Bool -I830DRI2ScheduleFlip(ClientPtr client, DrawablePtr draw, DRI2BufferPtr front, +I830DRI2ScheduleFlip(struct intel_screen_private *intel, + ClientPtr client, DrawablePtr draw, DRI2BufferPtr front, DRI2BufferPtr back, DRI2SwapEventPtr func, void *data) { - ScreenPtr screen = draw->pScreen; I830DRI2BufferPrivatePtr back_priv; DRI2FrameEventPtr flip_info; @@ -507,7 +507,7 @@ I830DRI2ScheduleFlip(ClientPtr client, DrawablePtr draw, DRI2BufferPtr front, /* Page flip the full screen buffer */ back_priv = back->driverPrivate; - return intel_do_pageflip(screen, + return intel_do_pageflip(intel, intel_get_pixmap_bo(back_priv->pixmap), flip_info); } @@ -567,7 +567,8 @@ void I830DRI2FrameEventHandler(unsigned int frame, unsigned int tv_sec, if (DRI2CanFlip(drawable) && !intel->shadow_present && intel->use_pageflipping && can_exchange(event->front, event->back) && - I830DRI2ScheduleFlip(event->client, drawable, event->front, + I830DRI2ScheduleFlip(intel, + event->client, drawable, event->front, event->back, event->event_complete, event->event_data)) { I830DRI2ExchangeBuffers(drawable, diff --git a/src/intel_driver.c b/src/intel_driver.c index 9b2fdaf1..eab5c2c7 100644 --- a/src/intel_driver.c +++ b/src/intel_driver.c @@ -98,6 +98,7 @@ typedef enum { OPTION_COLOR_KEY, OPTION_FALLBACKDEBUG, OPTION_TILING, + OPTION_SHADOW, OPTION_SWAPBUFFERS_WAIT, #ifdef INTEL_XVMC OPTION_XVMC, @@ -115,6 +116,7 @@ static OptionInfoRec I830Options[] = { {OPTION_VIDEO_KEY, "VideoKey", OPTV_INTEGER, {0}, FALSE}, {OPTION_FALLBACKDEBUG, "FallbackDebug", OPTV_BOOLEAN, {0}, FALSE}, {OPTION_TILING, "Tiling", OPTV_BOOLEAN, {0}, TRUE}, + {OPTION_SHADOW, "Shadow", OPTV_BOOLEAN, {0}, FALSE}, {OPTION_SWAPBUFFERS_WAIT, "SwapbuffersWait", OPTV_BOOLEAN, {0}, TRUE}, #ifdef INTEL_XVMC {OPTION_XVMC, "XvMC", OPTV_BOOLEAN, {0}, TRUE}, @@ -536,6 +538,7 @@ static Bool I830PreInit(ScrnInfoPtr scrn, int flags) scrn->driverPrivate = intel; } + intel->scrn = scrn; intel->pEnt = pEnt; scrn->displayWidth = 640; /* default it */ @@ -726,13 +729,16 @@ static Bool intel_init_initial_framebuffer(ScrnInfoPtr scrn) { intel_screen_private *intel = intel_get_screen_private(scrn); + int width = scrn->virtualX; + int height = scrn->virtualY; unsigned long pitch; + uint32_t tiling; intel->front_buffer = intel_allocate_framebuffer(scrn, - scrn->virtualX, - scrn->virtualY, + width, height, intel->cpp, - &pitch); + &pitch, + &tiling); if (!intel->front_buffer) { xf86DrvMsg(scrn->scrnIndex, X_ERROR, @@ -740,6 +746,8 @@ intel_init_initial_framebuffer(ScrnInfoPtr scrn) return FALSE; } + intel->front_pitch = pitch; + intel->front_tiling = tiling; scrn->displayWidth = pitch / intel->cpp; return TRUE; @@ -828,6 +836,9 @@ I830ScreenInit(int scrnIndex, ScreenPtr screen, int argc, char **argv) intel->directRenderingType = DRI_DRI2; #endif + intel->force_fallback = FALSE; + intel->use_shadow = FALSE; + /* Enable tiling by default */ intel->tiling = TRUE; @@ -839,6 +850,17 @@ I830ScreenInit(int scrnIndex, ScreenPtr screen, int argc, char **argv) intel->tiling = FALSE; } + if (xf86IsOptionSet(intel->Options, OPTION_SHADOW)) { + if (xf86ReturnOptValBool(intel->Options, OPTION_SHADOW, FALSE)) + intel->force_fallback = intel->use_shadow = TRUE; + } + + if (intel->use_shadow) { + xf86DrvMsg(scrn->scrnIndex, X_CONFIG, + "Shadow buffer enabled," + " GPU acceleration disabled.\n"); + } + /* SwapBuffers delays to avoid tearing */ intel->swapbuffers_wait = TRUE; @@ -1101,6 +1123,8 @@ static Bool I830CloseScreen(int scrnIndex, ScreenPtr screen) I830LeaveVT(scrnIndex, 0); } + DeleteCallback(&FlushCallback, intel_flush_callback, scrn); + if (intel->uxa_driver) { uxa_driver_fini(screen); free(intel->uxa_driver); @@ -1108,13 +1132,31 @@ static Bool I830CloseScreen(int scrnIndex, ScreenPtr screen) } if (intel->front_buffer) { - intel_set_pixmap_bo(screen->GetScreenPixmap(screen), NULL); + if (!intel->use_shadow) + intel_set_pixmap_bo(screen->GetScreenPixmap(screen), + NULL); intel_mode_remove_fb(intel); drm_intel_bo_unreference(intel->front_buffer); intel->front_buffer = NULL; } - DeleteCallback(&FlushCallback, intel_flush_callback, scrn); + if (intel->shadow_pixmap) { + PixmapPtr pixmap = intel->shadow_pixmap; + + if (intel->shadow_damage) { + DamageUnregister(&pixmap->drawable, + intel->shadow_damage); + DamageDestroy(intel->shadow_damage); + intel->shadow_damage = NULL; + } + + if (intel->shadow_buffer) { + drm_intel_bo_unreference(intel->shadow_buffer); + intel->shadow_buffer = NULL; + } + + intel->shadow_pixmap = NULL; + } intel_batch_teardown(scrn); diff --git a/src/intel_memory.c b/src/intel_memory.c index 091e3d09..4f1b009b 100644 --- a/src/intel_memory.c +++ b/src/intel_memory.c @@ -178,7 +178,8 @@ static inline int intel_pad_drawable_width(int width) */ drm_intel_bo *intel_allocate_framebuffer(ScrnInfoPtr scrn, int width, int height, int cpp, - unsigned long *out_pitch) + unsigned long *out_pitch, + uint32_t *out_tiling) { intel_screen_private *intel = intel_get_screen_private(scrn); drm_intel_bo *front_buffer; @@ -241,6 +242,7 @@ retry: intel_set_gem_max_sizes(scrn); *out_pitch = pitch; + *out_tiling = tiling_mode; return front_buffer; } diff --git a/src/intel_uxa.c b/src/intel_uxa.c index 1681b708..706d6341 100644 --- a/src/intel_uxa.c +++ b/src/intel_uxa.c @@ -688,9 +688,6 @@ static void intel_uxa_finish_access(PixmapPtr pixmap) struct intel_pixmap *priv = intel_get_pixmap_private(pixmap); dri_bo *bo = priv->bo; - if (bo == intel->front_buffer) - intel->need_sync = TRUE; - if (priv->tiling || bo->size <= intel->max_gtt_map_size) drm_intel_gem_bo_unmap_gtt(bo); else @@ -892,14 +889,197 @@ static Bool intel_uxa_get_image(PixmapPtr pixmap, scratch->drawable.pScreen->DestroyPixmap(scratch); return ret; +} + +static dri_bo * +intel_shadow_create_bo(intel_screen_private *intel, + int16_t x1, int16_t y1, + int16_t x2, int16_t y2, + int *pitch) +{ + int w = x2 - x1, h = y2 - y1; + int size = h * w * intel->cpp; + dri_bo *bo; + + bo = drm_intel_bo_alloc(intel->bufmgr, "shadow", size, 0); + if (bo && drm_intel_gem_bo_map_gtt(bo) == 0) { + char *dst = bo->virtual; + char *src = intel->shadow_pixmap->devPrivate.ptr; + int src_pitch = intel->shadow_pixmap->devKind; + int row_length = w * intel->cpp; + int num_rows = h; + src += y1 * src_pitch + x1 * intel->cpp; + do { + memcpy (dst, src, row_length); + src += src_pitch; + dst += row_length; + } while (--num_rows); + drm_intel_gem_bo_unmap_gtt(bo); + } + + *pitch = w * intel->cpp; + return bo; +} + +static void +intel_shadow_blt(intel_screen_private *intel) +{ + ScrnInfoPtr scrn = intel->scrn; + unsigned int dst_pitch; + uint32_t blt, br13; + RegionPtr region; + BoxPtr box; + int n; + + dst_pitch = intel->front_pitch; + + blt = XY_SRC_COPY_BLT_CMD; + if (intel->cpp == 4) + blt |= (XY_SRC_COPY_BLT_WRITE_ALPHA | + XY_SRC_COPY_BLT_WRITE_RGB); + + if (IS_I965G(intel)) { + if (intel->front_tiling) { + dst_pitch >>= 2; + blt |= XY_SRC_COPY_BLT_DST_TILED; + } + } + + br13 = ROP_S << 16 | dst_pitch; + switch (intel->cpp) { + default: + case 4: br13 |= 1 << 25; /* RGB8888 */ + case 2: br13 |= 1 << 24; /* RGB565 */ + case 1: break; + } + + region = DamageRegion(intel->shadow_damage); + box = REGION_RECTS(region); + n = REGION_NUM_RECTS(region); + while (n--) { + int pitch; + dri_bo *bo; + int offset; + + if (intel->shadow_buffer) { + bo = intel->shadow_buffer; + offset = box->x1 | box->y1 << 16; + pitch = intel->shadow_pixmap->devKind; + } else { + bo = intel_shadow_create_bo(intel, + box->x1, box->y1, + box->x2, box->y2, + &pitch); + if (bo == NULL) + return; + + offset = 0; + } + + BEGIN_BATCH(8); + OUT_BATCH(blt); + OUT_BATCH(br13); + OUT_BATCH(box->y1 << 16 | box->x1); + OUT_BATCH(box->y2 << 16 | box->x2); + OUT_RELOC_FENCED(intel->front_buffer, + I915_GEM_DOMAIN_RENDER, + I915_GEM_DOMAIN_RENDER, + 0); + OUT_BATCH(offset); + OUT_BATCH(pitch); + OUT_RELOC(bo, I915_GEM_DOMAIN_RENDER, 0, 0); + + ADVANCE_BATCH(); + if (bo != intel->shadow_buffer) + drm_intel_bo_unreference(bo); + box++; + } +} + +static void intel_shadow_create(struct intel_screen_private *intel) +{ + ScrnInfoPtr scrn = intel->scrn; + ScreenPtr screen = scrn->pScreen; + PixmapPtr pixmap; + int stride; + + if (IS_I8XX(intel)) + pixmap = screen->GetScreenPixmap(screen); + else + pixmap = intel->shadow_pixmap; + + if (intel->shadow_damage) { + DamageUnregister(&pixmap->drawable, intel->shadow_damage); + DamageDestroy(intel->shadow_damage); + } + + if (IS_I8XX(intel)) { + dri_bo *bo; + int size; + + /* Reduce the incoherency worries for gen2 + * by only allocating a static shadow, at about 2-3x + * performance cost for forcing rendering to uncached memory. + */ + if (intel->shadow_buffer) { + drm_intel_gem_bo_unmap_gtt(intel->shadow_buffer); + drm_intel_bo_unreference(intel->shadow_buffer); + intel->shadow_buffer = NULL; + } + + stride = ALIGN(scrn->virtualX * intel->cpp, 4); + size = stride * scrn->virtualY; + bo = drm_intel_bo_alloc(intel->bufmgr, + "shadow", size, + 0); + if (bo && drm_intel_gem_bo_map_gtt(bo) == 0) { + screen->ModifyPixmapHeader(pixmap, + scrn->virtualX, + scrn->virtualY, + -1, -1, + stride, + bo->virtual); + intel->shadow_buffer = bo; + } + } else { + if (intel->shadow_pixmap) + fbDestroyPixmap(intel->shadow_pixmap); + + pixmap = fbCreatePixmap(screen, + scrn->virtualX, + scrn->virtualY, + scrn->depth, + 0); + + screen->SetScreenPixmap(pixmap); + stride = pixmap->devKind; + } + + intel->shadow_pixmap = pixmap; + intel->shadow_damage = DamageCreate(NULL, NULL, + DamageReportNone, + TRUE, + screen, + intel); + DamageRegister(&pixmap->drawable, intel->shadow_damage); + DamageSetReportAfterOp(intel->shadow_damage, TRUE); + + scrn->displayWidth = stride / intel->cpp; } void intel_uxa_block_handler(intel_screen_private *intel) { - if (intel->need_sync) { - dri_bo_wait_rendering(intel->front_buffer); - intel->need_sync = FALSE; + if (intel->shadow_damage && + pixman_region_not_empty(DamageRegion(intel->shadow_damage))) { + intel_shadow_blt(intel); + /* Emit a flush of the rendering cache, or on the 965 + * and beyond rendering results may not hit the + * framebuffer until significantly later. + */ + intel_batch_submit(intel->scrn, TRUE); + + DamageEmpty(intel->shadow_damage); } } @@ -1045,17 +1225,27 @@ static Bool intel_uxa_destroy_pixmap(PixmapPtr pixmap) return TRUE; } - void intel_uxa_create_screen_resources(ScreenPtr screen) { ScrnInfoPtr scrn = xf86Screens[screen->myNum]; intel_screen_private *intel = intel_get_screen_private(scrn); - dri_bo *bo = intel->front_buffer; - if (bo != NULL) { - PixmapPtr pixmap = screen->GetScreenPixmap(screen); - intel_set_pixmap_bo(pixmap, bo); - intel_get_pixmap_private(pixmap)->busy = 1; + if (intel->use_shadow) { + intel_shadow_create(intel); + } else { + dri_bo *bo = intel->front_buffer; + if (bo != NULL) { + PixmapPtr pixmap = screen->GetScreenPixmap(screen); + intel_set_pixmap_bo(pixmap, bo); + intel_get_pixmap_private(pixmap)->busy = 1; + screen->ModifyPixmapHeader(pixmap, + scrn->virtualX, + scrn->virtualY, + -1, -1, + intel->front_pitch, + NULL); + } + scrn->displayWidth = intel->front_pitch / intel->cpp; } } @@ -1131,8 +1321,6 @@ Bool intel_uxa_init(ScreenPtr screen) memset(intel->uxa_driver, 0, sizeof(*intel->uxa_driver)); - intel->force_fallback = FALSE; - intel->bufferOffset = 0; intel->uxa_driver->uxa_major = 1; intel->uxa_driver->uxa_minor = 0; @@ -1206,6 +1394,7 @@ Bool intel_uxa_init(ScreenPtr screen) } uxa_set_fallback_debug(screen, intel->fallback_debug); + uxa_set_force_fallback(screen, intel->force_fallback); return TRUE; } diff --git a/src/intel_video.c b/src/intel_video.c index cde596cb..30a0c375 100644 --- a/src/intel_video.c +++ b/src/intel_video.c @@ -362,7 +362,9 @@ void I830InitVideo(ScreenPtr screen) /* Set up textured video if we can do it at this depth and we are on * supported hardware. */ - if (scrn->bitsPerPixel >= 16 && (IS_I9XX(intel) || IS_I965G(intel))) { + if (scrn->bitsPerPixel >= 16 && + (IS_I9XX(intel) || IS_I965G(intel)) && + !intel->use_shadow) { texturedAdaptor = I830SetupImageVideoTextured(screen); if (texturedAdaptor != NULL) { xf86DrvMsg(scrn->scrnIndex, X_INFO, diff --git a/uxa/uxa-glyphs.c b/uxa/uxa-glyphs.c index 8c00e900..ad4f3877 100644 --- a/uxa/uxa-glyphs.c +++ b/uxa/uxa-glyphs.c @@ -197,13 +197,6 @@ bail: Bool uxa_glyphs_init(ScreenPtr pScreen) { - /* We are trying to initialise per screen resources prior to the - * complete initialisation of the screen. So ensure the components - * that we depend upon are initialsed prior to our use. - */ - if (!CreateScratchPixmapsForScreen(pScreen->myNum)) - return FALSE; - #if HAS_DIXREGISTERPRIVATEKEY if (!dixRegisterPrivateKey(&uxa_glyph_key, PRIVATE_GLYPH, 0)) return FALSE; @@ -212,6 +205,17 @@ Bool uxa_glyphs_init(ScreenPtr pScreen) return FALSE; #endif + /* Skip pixmap creation if we don't intend to use it. */ + if (uxa_get_screen(pScreen)->force_fallback) + return TRUE; + + /* We are trying to initialise per screen resources prior to the + * complete initialisation of the screen. So ensure the components + * that we depend upon are initialsed prior to our use. + */ + if (!CreateScratchPixmapsForScreen(pScreen->myNum)) + return FALSE; + if (!uxa_realize_glyph_caches(pScreen)) return FALSE; @@ -293,18 +297,19 @@ uxa_glyph_cache_upload_glyph(ScreenPtr screen, } void -uxa_glyph_unrealize(ScreenPtr pScreen, - GlyphPtr pGlyph) +uxa_glyph_unrealize(ScreenPtr screen, + GlyphPtr glyph) { struct uxa_glyph *priv; - priv = uxa_glyph_get_private(pGlyph); + /* Use Lookup in case we have not attached to this glyph. */ + priv = dixLookupPrivate(&glyph->devPrivates, &uxa_glyph_key); if (priv == NULL) return; priv->cache->glyphs[priv->pos] = NULL; - uxa_glyph_set_private(pGlyph, NULL); + uxa_glyph_set_private(glyph, NULL); free(priv); } @@ -385,12 +385,15 @@ static Bool uxa_close_screen(int i, ScreenPtr pScreen) uxa_glyphs_fini(pScreen); - /* Destroy the pixmap created by miScreenInit() *before* chaining up as - * we finalize ourselves here and so this is the last chance we have of - * releasing our resources associated with the Pixmap. So do it first. - */ - (void) (*pScreen->DestroyPixmap) (pScreen->devPrivate); - pScreen->devPrivate = NULL; + if (pScreen->devPrivate) { + /* Destroy the pixmap created by miScreenInit() *before* + * chaining up as we finalize ourselves here and so this + * is the last chance we have of releasing our resources + * associated with the Pixmap. So do it first. + */ + (void) (*pScreen->DestroyPixmap) (pScreen->devPrivate); + pScreen->devPrivate = NULL; + } pScreen->CreateGC = uxa_screen->SavedCreateGC; pScreen->CloseScreen = uxa_screen->SavedCloseScreen; |