summaryrefslogtreecommitdiff
path: root/src/intel_display.c
diff options
context:
space:
mode:
authorDave Airlie <airlied@redhat.com>2012-07-26 10:37:04 +1000
committerDave Airlie <airlied@redhat.com>2012-09-03 12:28:29 +1000
commit6705d8237aca90964449e4dbee97b4f62b87c28b (patch)
treeed10f61099cc352b170c69a2e7f95299e8f905cf /src/intel_display.c
parent69827126abdfa289417b55fe7db8ae0535037185 (diff)
intel: add pixmap tracking and scanout support. (v2)
This adds support for pixmap tracking and scanout of alternate pixmaps. v2: do dirty updates after uxa block handler, check if kernel can flush vmap for us so we don't have to. Signed-off-by: Dave Airlie <airlied@redhat.com>
Diffstat (limited to 'src/intel_display.c')
-rw-r--r--src/intel_display.c60
1 files changed, 56 insertions, 4 deletions
diff --git a/src/intel_display.c b/src/intel_display.c
index 6dfc8e63..4bc8a7b4 100644
--- a/src/intel_display.c
+++ b/src/intel_display.c
@@ -86,6 +86,8 @@ struct intel_crtc {
uint32_t rotate_fb_id;
xf86CrtcPtr crtc;
struct list link;
+ PixmapPtr scanout_pixmap;
+ uint32_t scanout_fb_id;
};
struct intel_property {
@@ -378,6 +380,7 @@ intel_crtc_apply(xf86CrtcPtr crtc)
ScrnInfoPtr scrn = crtc->scrn;
struct intel_crtc *intel_crtc = crtc->driver_private;
struct intel_mode *mode = intel_crtc->mode;
+ intel_screen_private *intel = intel_get_screen_private(scrn);
xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(crtc->scrn);
uint32_t *output_ids;
int output_count = 0;
@@ -401,13 +404,15 @@ intel_crtc_apply(xf86CrtcPtr crtc)
output_count++;
}
+ if (!intel_crtc->scanout_fb_id) {
#if XORG_VERSION_CURRENT < XORG_VERSION_NUMERIC(1,5,99,0,0)
- if (!xf86CrtcRotate(crtc, mode, rotation))
- goto done;
+ if (!xf86CrtcRotate(crtc, mode, rotation))
+ goto done;
#else
- if (!xf86CrtcRotate(crtc))
- goto done;
+ if (!xf86CrtcRotate(crtc))
+ goto done;
#endif
+ }
#if XORG_VERSION_CURRENT >= XORG_VERSION_NUMERIC(1,7,0,0,0)
crtc->funcs->gamma_set(crtc, crtc->gamma_red, crtc->gamma_green,
@@ -421,6 +426,10 @@ intel_crtc_apply(xf86CrtcPtr crtc)
fb_id = intel_crtc->rotate_fb_id;
x = 0;
y = 0;
+ } else if (intel_crtc->scanout_fb_id && intel_crtc->scanout_pixmap->drawable.width >= crtc->mode.HDisplay && intel_crtc->scanout_pixmap->drawable.height >= crtc->mode.VDisplay) {
+ fb_id = intel_crtc->scanout_fb_id;
+ x = 0;
+ y = 0;
}
ret = drmModeSetCrtc(mode->fd, crtc_id(intel_crtc),
fb_id, x, y, output_ids, output_count,
@@ -684,6 +693,42 @@ intel_crtc_destroy(xf86CrtcPtr crtc)
crtc->driver_private = NULL;
}
+#ifdef INTEL_PIXMAP_SHARING
+static Bool
+intel_set_scanout_pixmap(xf86CrtcPtr crtc, PixmapPtr ppix)
+{
+ struct intel_crtc *intel_crtc = crtc->driver_private;
+ ScrnInfoPtr scrn = crtc->scrn;
+ intel_screen_private *intel = intel_get_screen_private(scrn);
+ dri_bo *bo;
+ int ret;
+
+ if (ppix == intel_crtc->scanout_pixmap)
+ return TRUE;
+
+ if (!ppix) {
+ intel_crtc->scanout_pixmap = NULL;
+ if (intel_crtc->scanout_fb_id) {
+ drmModeRmFB(intel->drmSubFD, intel_crtc->scanout_fb_id);
+ intel_crtc->scanout_fb_id = 0;
+ }
+ return TRUE;
+ }
+
+ bo = intel_get_pixmap_bo(ppix);
+ if (intel->front_buffer) {
+ ErrorF("have front buffer\n");
+ }
+
+ intel_crtc->scanout_pixmap = ppix;
+ ret = drmModeAddFB(intel->drmSubFD, ppix->drawable.width,
+ ppix->drawable.height, ppix->drawable.depth,
+ ppix->drawable.bitsPerPixel, ppix->devKind,
+ bo->handle, &intel_crtc->scanout_fb_id);
+ return TRUE;
+}
+#endif
+
static const xf86CrtcFuncsRec intel_crtc_funcs = {
.dpms = intel_crtc_dpms,
.set_mode_major = intel_crtc_set_mode_major,
@@ -697,6 +742,9 @@ static const xf86CrtcFuncsRec intel_crtc_funcs = {
.shadow_destroy = intel_crtc_shadow_destroy,
.gamma_set = intel_crtc_gamma_set,
.destroy = intel_crtc_destroy,
+#ifdef INTEL_PIXMAP_SHARING
+ .set_scanout_pixmap = intel_set_scanout_pixmap,
+#endif
};
static void
@@ -1662,6 +1710,10 @@ Bool intel_mode_pre_init(ScrnInfoPtr scrn, int fd, int cpp)
for (i = 0; i < mode->mode_res->count_connectors; i++)
intel_output_init(scrn, mode, i);
+#ifdef INTEL_PIXMAP_SHARING
+ xf86ProviderSetup(scrn, NULL, "Intel");
+#endif
+
xf86InitialConfiguration(scrn, TRUE);
mode->event_context.version = DRM_EVENT_CONTEXT_VERSION;