[PATCH 1/2] rotate: Unregister damage across modesetting

Chris Wilson chris at chris-wilson.co.uk
Thu Aug 25 06:46:07 PDT 2011


The driver is at liberty to modify the Screen Pixmap, for example if it
creates a new ordinary Pixmap for use as a shadow scanout buffer, and so
the cached registration of the damage may become stale and lead to an
eventual crash.

Signed-off-by: Chris Wilson <chris at chris-wilson.co.uk>
---
 hw/xfree86/modes/xf86Crtc.h   |    2 +-
 hw/xfree86/modes/xf86Rotate.c |   43 +++++++++++++++++++++++++---------------
 2 files changed, 28 insertions(+), 17 deletions(-)

diff --git a/hw/xfree86/modes/xf86Crtc.h b/hw/xfree86/modes/xf86Crtc.h
index 68a968c..db94e98 100644
--- a/hw/xfree86/modes/xf86Crtc.h
+++ b/hw/xfree86/modes/xf86Crtc.h
@@ -647,7 +647,7 @@ typedef struct _xf86CrtcConfig {
     
     /* For crtc-based rotation */
     DamagePtr		rotation_damage;
-    Bool		rotation_damage_registered;
+    DrawablePtr		rotation_damage_registered;
 
     /* DGA */
     unsigned int	dga_flags;
diff --git a/hw/xfree86/modes/xf86Rotate.c b/hw/xfree86/modes/xf86Rotate.c
index c378391..da8a8f4 100644
--- a/hw/xfree86/modes/xf86Rotate.c
+++ b/hw/xfree86/modes/xf86Rotate.c
@@ -194,9 +194,10 @@ xf86RotatePrepare (ScreenPtr pScreen)
 	    if (!xf86_config->rotation_damage_registered)
 	    {
 		/* Hook damage to screen pixmap */
-		DamageRegister (&(*pScreen->GetScreenPixmap)(pScreen)->drawable,
+		xf86_config->rotation_damage_registered =
+			&(*pScreen->GetScreenPixmap)(pScreen)->drawable;
+		DamageRegister (xf86_config->rotation_damage_registered,
 				xf86_config->rotation_damage);
-		xf86_config->rotation_damage_registered = TRUE;
 		EnableLimitedSchedulingLatency();
 	    }
 	    
@@ -304,9 +305,9 @@ xf86RotateDestroy (xf86CrtcPtr crtc)
 	/* Free damage structure */
 	if (xf86_config->rotation_damage_registered)
 	{
-	    DamageUnregister (&(*pScreen->GetScreenPixmap)(pScreen)->drawable,
+	    DamageUnregister (xf86_config->rotation_damage_registered,
 			      xf86_config->rotation_damage);
-	    xf86_config->rotation_damage_registered = FALSE;
+	    xf86_config->rotation_damage_registered = NULL;
 	    DisableLimitedSchedulingLatency();
 	}
 	DamageDestroy (xf86_config->rotation_damage);
@@ -450,20 +451,30 @@ xf86CrtcRotate (xf86CrtcPtr crtc)
 	    damage = TRUE;
 	}
 
-	if (!xf86_config->rotation_damage)
+	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;
+	    /* Free damage structure */
+	    if (xf86_config->rotation_damage_registered)
+	    {
+		DamageUnregister (xf86_config->rotation_damage_registered,
+				  xf86_config->rotation_damage);
+		xf86_config->rotation_damage_registered = NULL;
+		DisableLimitedSchedulingLatency();
 	    }
+	    DamageDestroy (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;
 	}
 #ifdef RANDR_12_INTERFACE
 	if (transform)
-- 
1.7.5.4



More information about the xorg-devel mailing list