Пример #1
0
static void
xf86CrtcDamageShadow(xf86CrtcPtr crtc)
{
    ScrnInfoPtr pScrn = crtc->scrn;
    BoxRec damage_box;
    RegionRec damage_region;
    ScreenPtr pScreen = xf86ScrnToScreen(pScrn);

    damage_box.x1 = 0;
    damage_box.x2 = crtc->mode.HDisplay;
    damage_box.y1 = 0;
    damage_box.y2 = crtc->mode.VDisplay;
    if (!pixman_transform_bounds(&crtc->crtc_to_framebuffer, &damage_box)) {
        damage_box.x1 = 0;
        damage_box.y1 = 0;
        damage_box.x2 = pScreen->width;
        damage_box.y2 = pScreen->height;
    }
    if (damage_box.x1 < 0)
        damage_box.x1 = 0;
    if (damage_box.y1 < 0)
        damage_box.y1 = 0;
    if (damage_box.x2 > pScreen->width)
        damage_box.x2 = pScreen->width;
    if (damage_box.y2 > pScreen->height)
        damage_box.y2 = pScreen->height;
    RegionInit(&damage_region, &damage_box, 1);
    DamageDamageRegion(&(*pScreen->GetScreenPixmap) (pScreen)->drawable,
                       &damage_region);
    RegionUninit(&damage_region);
    crtc->shadowClear = TRUE;
}
Пример #2
0
static Bool
xf86CrtcFitsScreen(xf86CrtcPtr crtc, struct pict_f_transform *crtc_to_fb)
{
    ScrnInfoPtr pScrn = crtc->scrn;
    BoxRec b;

    /* When called before PreInit, the driver is
     * presumably doing load detect
     */
    if (pScrn->is_gpu) {
	ScreenPtr pScreen = xf86ScrnToScreen(pScrn);
	if (pScreen->current_master)
	    pScrn = xf86ScreenToScrn(pScreen->current_master);
    }

    if (pScrn->virtualX == 0 || pScrn->virtualY == 0)
        return TRUE;

    b.x1 = 0;
    b.y1 = 0;
    b.x2 = crtc->mode.HDisplay;
    b.y2 = crtc->mode.VDisplay;
    if (crtc_to_fb)
        pixman_f_transform_bounds(crtc_to_fb, &b);
    else {
        b.x1 += crtc->x;
        b.y1 += crtc->y;
        b.x2 += crtc->x;
        b.y2 += crtc->y;
    }

    return (0 <= b.x1 && b.x2 <= pScrn->virtualX &&
            0 <= b.y1 && b.y2 <= pScrn->virtualY);
}
Пример #3
0
static void
VGAarbiterAdjustFrame(ScrnInfoPtr pScrn, int x, int y)
{
    ScreenPtr pScreen = xf86ScrnToScreen(pScrn);
    VGAarbiterScreenPtr pScreenPriv =
        (VGAarbiterScreenPtr) dixLookupPrivate(&pScreen->devPrivates,
                                               VGAarbiterScreenKey);

    VGAGet(pScreen);
    (*pScreenPriv->AdjustFrame) (pScrn, x, y);
    VGAPut();
}
Пример #4
0
static void
VGAarbiterFreeScreen(ScrnInfoPtr pScrn)
{
    ScreenPtr pScreen = xf86ScrnToScreen(pScrn);
    VGAarbiterScreenPtr pScreenPriv =
        (VGAarbiterScreenPtr) dixLookupPrivate(&pScreen->devPrivates,
                                               VGAarbiterScreenKey);

    VGAGet(pScreen);
    (*pScreenPriv->FreeScreen) (pScrn);
    VGAPut();
}
Пример #5
0
static Bool
VGAarbiterSwitchMode(ScrnInfoPtr pScrn, DisplayModePtr mode)
{
    Bool val;
    ScreenPtr pScreen = xf86ScrnToScreen(pScrn);
    VGAarbiterScreenPtr pScreenPriv =
        (VGAarbiterScreenPtr) dixLookupPrivate(&pScreen->devPrivates,
                                               VGAarbiterScreenKey);

    VGAGet(pScreen);
    val = (*pScreenPriv->SwitchMode) (pScrn, mode);
    VGAPut();
    return val;
}
Пример #6
0
static void
VGAarbiterLeaveVT(ScrnInfoPtr pScrn)
{
    ScreenPtr pScreen = xf86ScrnToScreen(pScrn);
    VGAarbiterScreenPtr pScreenPriv =
        (VGAarbiterScreenPtr) dixLookupPrivate(&pScreen->devPrivates,
                                               VGAarbiterScreenKey);

    VGAGet(pScreen);
    pScrn->LeaveVT = pScreenPriv->LeaveVT;
    (*pScreenPriv->LeaveVT) (pScrn);
    pScreenPriv->LeaveVT = pScrn->LeaveVT;
    pScrn->LeaveVT = VGAarbiterLeaveVT;
    VGAPut();
}
Пример #7
0
static void
exaXorgEnableDisableFBAccess(ScrnInfoPtr pScrn, Bool enable)
{
    ScreenPtr pScreen = xf86ScrnToScreen(pScrn);
    ExaXorgScreenPrivPtr pScreenPriv = (ExaXorgScreenPrivPtr)
        dixLookupPrivate(&pScreen->devPrivates, exaXorgScreenPrivateKey);

    if (!enable)
        exaEnableDisableFBAccess(pScreen, enable);

    if (pScreenPriv->SavedEnableDisableFBAccess)
        pScreenPriv->SavedEnableDisableFBAccess(pScrn, enable);

    if (enable)
        exaEnableDisableFBAccess(pScreen, enable);
}
Пример #8
0
static Bool
VGAarbiterEnterVT(ScrnInfoPtr pScrn)
{
    Bool val;
    ScreenPtr pScreen = xf86ScrnToScreen(pScrn);
    VGAarbiterScreenPtr pScreenPriv =
        (VGAarbiterScreenPtr) dixLookupPrivate(&pScreen->devPrivates,
                                               VGAarbiterScreenKey);

    VGAGet(pScreen);
    pScrn->EnterVT = pScreenPriv->EnterVT;
    val = (*pScrn->EnterVT) (pScrn);
    pScreenPriv->EnterVT = pScrn->EnterVT;
    pScrn->EnterVT = VGAarbiterEnterVT;
    VGAPut();
    return val;
}
Пример #9
0
void
xf86RotateDestroy(xf86CrtcPtr crtc)
{
    ScrnInfoPtr pScrn = crtc->scrn;
    ScreenPtr pScreen = xf86ScrnToScreen(pScrn);
    xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
    int c;

    /* Free memory from rotation */
    if (crtc->rotatedPixmap || crtc->rotatedData) {
        crtc->funcs->shadow_destroy(crtc, crtc->rotatedPixmap,
                                    crtc->rotatedData);
        crtc->rotatedPixmap = NULL;
        crtc->rotatedData = NULL;
    }

    for (c = 0; c < xf86_config->num_crtc; c++)
        if (xf86_config->crtc[c]->rotatedData)
            return;

    /*
     * Clean up damage structures when no crtcs are rotated
     */
    if (xf86_config->rotation_damage) {
        DrawablePtr screenDrawable = NULL;
        if (pScreen && pScreen->root)
            screenDrawable = &pScreen->root->drawable;
        /* Free damage structure */
        if (xf86_config->rotation_damage_registered) {
            xf86_config->rotation_damage_registered = FALSE;
            DisableLimitedSchedulingLatency();
        }
        DamageDestroy(xf86_config->rotation_damage);
        xf86_config->rotation_damage = NULL;
    }
}
Пример #10
0
Bool
xf86CrtcRotate(xf86CrtcPtr crtc)
{
    ScrnInfoPtr pScrn = crtc->scrn;
    xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
    ScreenPtr pScreen = xf86ScrnToScreen(pScrn);
    PictTransform crtc_to_fb;
    struct pict_f_transform f_crtc_to_fb, f_fb_to_crtc;
    xFixed *new_params = NULL;
    int new_nparams = 0;
    PictFilterPtr new_filter = NULL;
    int new_width = 0;
    int new_height = 0;
    RRTransformPtr transform = NULL;
    Bool damage = FALSE;

    if (pScreen->isGPU)
        return TRUE;
    if (crtc->transformPresent)
        transform = &crtc->transform;

    if (!RRTransformCompute(crtc->x, crtc->y,
                            crtc->mode.HDisplay, crtc->mode.VDisplay,
                            crtc->rotation,
                            transform,
                            &crtc_to_fb,
                            &f_crtc_to_fb,
                            &f_fb_to_crtc) &&
        xf86CrtcFitsScreen(crtc, &f_crtc_to_fb)) {
        /*
         * If the untranslated transformation is the identity,
         * disable the shadow buffer
         */
        xf86RotateDestroy(crtc);
        crtc->transform_in_use = FALSE;
        free(new_params);
        new_params = NULL;
        new_nparams = 0;
        new_filter = NULL;
        new_width = 0;
        new_height = 0;
    }
    else {
        if (crtc->driverIsPerformingTransform) {
            xf86RotateDestroy(crtc);
        }
        else {
            /*
             * these are the size of the shadow pixmap, which
             * matches the mode, not the pre-rotated copy in the
             * frame buffer
             */
            int width = crtc->mode.HDisplay;
            int height = crtc->mode.VDisplay;
            void *shadowData = crtc->rotatedData;
            PixmapPtr shadow = crtc->rotatedPixmap;
            int old_width = shadow ? shadow->drawable.width : 0;
            int old_height = shadow ? shadow->drawable.height : 0;

            /* Allocate memory for rotation */
            if (old_width != width || old_height != height) {
                if (shadow || shadowData) {
                    crtc->funcs->shadow_destroy(crtc, shadow, shadowData);
                    crtc->rotatedPixmap = NULL;
                    crtc->rotatedData = NULL;
                }
                shadowData = crtc->funcs->shadow_allocate(crtc, width, height);
                if (!shadowData)
                    goto bail1;
                crtc->rotatedData = shadowData;
                /* shadow will be damaged in xf86RotatePrepare */
            }
            else {
                /* mark shadowed area as damaged so it will be repainted */
                damage = TRUE;
            }

            if (!xf86_config->rotation_damage) {
                /* Create damage structure */
                xf86_config->rotation_damage = DamageCreate(NULL, NULL,
                                                            DamageReportNone,
                                                            TRUE, pScreen,
                                                            pScreen);
                if (!xf86_config->rotation_damage)
                    goto bail2;

                /* Wrap block handler */
                if (!xf86_config->BlockHandler) {
                    xf86_config->BlockHandler = pScreen->BlockHandler;
                    pScreen->BlockHandler = xf86RotateBlockHandler;
                }
            }

            if (0) {
 bail2:
                if (shadow || shadowData) {
                    crtc->funcs->shadow_destroy(crtc, shadow, shadowData);
                    crtc->rotatedPixmap = NULL;
                    crtc->rotatedData = NULL;
                }
 bail1:
                if (old_width && old_height)
                    crtc->rotatedPixmap =
                        crtc->funcs->shadow_create(crtc, NULL, old_width,
                                                   old_height);
                return FALSE;
            }
        }
#ifdef RANDR_12_INTERFACE
        if (transform) {
            if (transform->nparams) {
                new_params = malloc(transform->nparams * sizeof(xFixed));
                if (new_params) {
                    memcpy(new_params, transform->params,
                           transform->nparams * sizeof(xFixed));
                    new_nparams = transform->nparams;
                    new_filter = transform->filter;
                }
            }
            else
                new_filter = transform->filter;
            if (new_filter) {
                new_width = new_filter->width;
                new_height = new_filter->height;
            }
        }
#endif
        crtc->transform_in_use = TRUE;
    }
    crtc->crtc_to_framebuffer = crtc_to_fb;
    crtc->f_crtc_to_framebuffer = f_crtc_to_fb;
    crtc->f_framebuffer_to_crtc = f_fb_to_crtc;
    free(crtc->params);
    crtc->params = new_params;
    crtc->nparams = new_nparams;
    crtc->filter = new_filter;
    crtc->filter_width = new_width;
    crtc->filter_height = new_height;
    crtc->bounds.x1 = 0;
    crtc->bounds.x2 = crtc->mode.HDisplay;
    crtc->bounds.y1 = 0;
    crtc->bounds.y2 = crtc->mode.VDisplay;
    pixman_f_transform_bounds(&f_crtc_to_fb, &crtc->bounds);

    if (damage)
        xf86CrtcDamageShadow(crtc);

    /* All done */
    return TRUE;
}
Пример #11
0
void intel_batch_submit(ScrnInfoPtr scrn)
{
	intel_screen_private *intel = intel_get_screen_private(scrn);
	int ret;

	assert (!intel->in_batch_atomic);

	if (intel->vertex_flush)
		intel->vertex_flush(intel);
	intel_end_vertex(intel);

	if (intel->batch_flush)
		intel->batch_flush(intel);

	if (intel->batch_used == 0)
		return;

	/* Mark the end of the batchbuffer. */
	OUT_BATCH(MI_BATCH_BUFFER_END);
	/* Emit a padding dword if we aren't going to be quad-word aligned. */
	if (intel->batch_used & 1)
		OUT_BATCH(MI_NOOP);

	if (DUMP_BATCHBUFFERS) {
	    FILE *file = fopen(DUMP_BATCHBUFFERS, "a");
	    if (file) {
		fwrite (intel->batch_ptr, intel->batch_used*4, 1, file);
		fclose(file);
	    }
	}

	ret = dri_bo_subdata(intel->batch_bo, 0, intel->batch_used*4, intel->batch_ptr);
	if (ret == 0) {
		ret = drm_intel_bo_mrb_exec(intel->batch_bo,
				intel->batch_used*4,
				NULL, 0, 0xffffffff,
				(HAS_BLT(intel) ?
				 intel->current_batch:
				 I915_EXEC_DEFAULT));
	}

	if (ret != 0) {
		static int once;
		if (!once) {
			if (ret == -EIO) {
				/* The GPU has hung and unlikely to recover by this point. */
				xf86DrvMsg(scrn->scrnIndex, X_ERROR, "Detected a hung GPU, disabling acceleration.\n");
				xf86DrvMsg(scrn->scrnIndex, X_ERROR, "When reporting this, please include i915_error_state from debugfs and the full dmesg.\n");
			} else {
				/* The driver is broken. */
				xf86DrvMsg(scrn->scrnIndex, X_ERROR,
					   "Failed to submit batch buffer, expect rendering corruption: %s.\n ",
					   strerror(-ret));
			}
			uxa_set_force_fallback(xf86ScrnToScreen(scrn), TRUE);
			intel->force_fallback = TRUE;
			once = 1;
		}
	}

	while (!list_is_empty(&intel->batch_pixmaps)) {
		struct intel_pixmap *entry;

		entry = list_first_entry(&intel->batch_pixmaps,
					 struct intel_pixmap,
					 batch);

		entry->busy = -1;
		entry->dirty = 0;
		list_del(&entry->batch);
	}

	if (intel->debug_flush & DEBUG_FLUSH_WAIT)
		drm_intel_bo_wait_rendering(intel->batch_bo);

	intel_next_batch(scrn, intel->current_batch == I915_EXEC_BLT);

	if (intel->batch_commit_notify)
		intel->batch_commit_notify(intel);

	intel->current_batch = 0;
}
Пример #12
0
int
I810WaitLpRing(ScrnInfoPtr pScrn, int n, int timeout_millis)
{
   I810Ptr pI810 = I810PTR(pScrn);
   I810RingBuffer *ring = pI810->LpRing;
   int iters = 0;
   int start = 0;
   int now = 0;
   int last_head = 0;
   int first = 0;

   /* If your system hasn't moved the head pointer in 2 seconds, I'm going to
    * call it crashed.
    */
   if (timeout_millis == 0)
      timeout_millis = 2000;

   if (I810_DEBUG & DEBUG_VERBOSE_ACCEL) {
      ErrorF("I810WaitLpRing %d\n", n);
      first = GetTimeInMillis();
   }

   while (ring->space < n) {
      ring->head = INREG(LP_RING + RING_HEAD) & HEAD_ADDR;
      ring->space = ring->head - (ring->tail + 8);

      if (ring->space < 0)
	 ring->space += ring->mem.Size;

      iters++;
      now = GetTimeInMillis();
      if (start == 0 || now < start || ring->head != last_head) {
	 if (I810_DEBUG & DEBUG_VERBOSE_ACCEL)
	    if (now > start)
	       ErrorF("space: %d wanted %d\n", ring->space, n);
	 start = now;
	 last_head = ring->head;
      } else if (now - start > timeout_millis) {
	 ErrorF("Error in I810WaitLpRing(), now is %d, start is %d\n", now,
		start);
	 I810PrintErrorState(pScrn);
	 ErrorF("space: %d wanted %d\n", ring->space, n);
#ifdef HAVE_DRI1
	 if (pI810->directRenderingEnabled) {
	    DRIUnlock(xf86ScrnToScreen(pScrn));
	    DRICloseScreen(xf86ScrnToScreen(pScrn));
	 }
#endif
#if HAVE_XAA_H
	 pI810->AccelInfoRec = NULL;	/* Stops recursive behavior */
#endif
	 FatalError("lockup\n");
      }

      DELAY(10000);
   }

   if (I810_DEBUG & DEBUG_VERBOSE_ACCEL) {
      now = GetTimeInMillis();
      if (now - first) {
	 ErrorF("Elapsed %d ms\n", now - first);
	 ErrorF("space: %d wanted %d\n", ring->space, n);
      }
   }

   return iters;
}