aboutsummaryrefslogtreecommitdiff
path: root/xorg-server/glamor
diff options
context:
space:
mode:
Diffstat (limited to 'xorg-server/glamor')
-rw-r--r--xorg-server/glamor/glamor_copy.c55
-rw-r--r--xorg-server/glamor/glamor_font.c7
-rw-r--r--xorg-server/glamor/glamor_xv.c13
3 files changed, 72 insertions, 3 deletions
diff --git a/xorg-server/glamor/glamor_copy.c b/xorg-server/glamor/glamor_copy.c
index bfcde43db..6f422d419 100644
--- a/xorg-server/glamor/glamor_copy.c
+++ b/xorg-server/glamor/glamor_copy.c
@@ -233,6 +233,56 @@ bail:
return FALSE;
}
+/**
+ * Implements CopyArea from the GPU to the CPU using glReadPixels from the
+ * source FBO.
+ */
+static Bool
+glamor_copy_fbo_cpu(DrawablePtr src,
+ DrawablePtr dst,
+ GCPtr gc,
+ BoxPtr box,
+ int nbox,
+ int dx,
+ int dy,
+ Bool reverse,
+ Bool upsidedown,
+ Pixel bitplane,
+ void *closure)
+{
+ ScreenPtr screen = dst->pScreen;
+ glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
+ PixmapPtr src_pixmap = glamor_get_drawable_pixmap(src);
+ FbBits *dst_bits;
+ FbStride dst_stride;
+ int dst_bpp;
+ int src_xoff, src_yoff;
+ int dst_xoff, dst_yoff;
+
+ if (gc && gc->alu != GXcopy)
+ goto bail;
+
+ if (gc && !glamor_pm_is_solid(dst, gc->planemask))
+ goto bail;
+
+ glamor_make_current(glamor_priv);
+ glamor_prepare_access(dst, GLAMOR_ACCESS_RW);
+
+ glamor_get_drawable_deltas(src, src_pixmap, &src_xoff, &src_yoff);
+
+ fbGetDrawable(dst, dst_bits, dst_stride, dst_bpp, dst_xoff, dst_yoff);
+
+ glamor_download_boxes(src_pixmap, box, nbox, src_xoff + dx, src_yoff + dy,
+ dst_xoff, dst_yoff,
+ (uint8_t *) dst_bits, dst_stride * sizeof (FbBits));
+ glamor_finish_access(dst);
+
+ return TRUE;
+
+bail:
+ return FALSE;
+}
+
/*
* Copy from GPU to GPU by using the source
* as a texture and painting that into the destination
@@ -584,6 +634,11 @@ glamor_copy_gl(DrawablePtr src,
if (bitplane == 0)
return glamor_copy_cpu_fbo(src, dst, gc, box, nbox, dx, dy,
reverse, upsidedown, bitplane, closure);
+ } else if (GLAMOR_PIXMAP_PRIV_HAS_FBO(src_priv) &&
+ dst_priv->type != GLAMOR_DRM_ONLY &&
+ bitplane == 0) {
+ return glamor_copy_fbo_cpu(src, dst, gc, box, nbox, dx, dy,
+ reverse, upsidedown, bitplane, closure);
}
return FALSE;
}
diff --git a/xorg-server/glamor/glamor_font.c b/xorg-server/glamor/glamor_font.c
index 57c607dc2..0ca91fa2e 100644
--- a/xorg-server/glamor/glamor_font.c
+++ b/xorg-server/glamor/glamor_font.c
@@ -46,6 +46,8 @@ glamor_font_get(ScreenPtr screen, FontPtr font)
CharInfoPtr glyph;
unsigned long count;
+ if (glamor_priv->glsl_version < 130)
+ return NULL;
privates = FontGetPrivate(font, glamor_font_private_index);
if (!privates) {
@@ -167,6 +169,11 @@ glamor_unrealize_font(ScreenPtr screen, FontPtr font)
Bool
glamor_font_init(ScreenPtr screen)
{
+ glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
+
+ if (glamor_priv->glsl_version < 130)
+ return TRUE;
+
if (glamor_font_generation != serverGeneration) {
glamor_font_private_index = AllocateFontPrivateIndex();
if (glamor_font_private_index == -1)
diff --git a/xorg-server/glamor/glamor_xv.c b/xorg-server/glamor/glamor_xv.c
index 3f3e064d5..26bdef66b 100644
--- a/xorg-server/glamor/glamor_xv.c
+++ b/xorg-server/glamor/glamor_xv.c
@@ -136,6 +136,11 @@ glamor_init_xv_shader(ScreenPtr screen)
void
glamor_xv_stop_video(glamor_port_private *port_priv)
{
+}
+
+static void
+glamor_xv_free_port_data(glamor_port_private *port_priv)
+{
int i;
for (i = 0; i < 3; i++) {
@@ -144,6 +149,8 @@ glamor_xv_stop_video(glamor_port_private *port_priv)
port_priv->src_pix[i] = NULL;
}
}
+ RegionUninit(&port_priv->clip);
+ RegionNull(&port_priv->clip);
}
int
@@ -381,6 +388,8 @@ glamor_xv_render(glamor_port_private *port_priv)
glDisableVertexAttribArray(GLAMOR_VERTEX_SOURCE);
DamageDamageRegion(port_priv->pDraw, &port_priv->clip);
+
+ glamor_xv_free_port_data(port_priv);
}
int
@@ -468,9 +477,7 @@ glamor_xv_put_image(glamor_port_private *port_priv,
else
port_priv->pPixmap = (PixmapPtr) pDrawable;
- if (!RegionEqual(&port_priv->clip, clipBoxes)) {
- RegionCopy(&port_priv->clip, clipBoxes);
- }
+ RegionCopy(&port_priv->clip, clipBoxes);
port_priv->src_x = src_x;
port_priv->src_y = src_y;