copyArea() sometimes crashed GTK. This was caused by 0 size passed into
it (that caused a malloc with 0 length and an assertion error). I fixed
the safety check in CairoGraphics2D as well as the calling code to not
call copyArea() in the first place.


2006-10-18  Roman Kennke  <[EMAIL PROTECTED]>

        PR 29419
        * gnu/java/awt/peer/gtk/CairoGraphics2D.java
        (copyArea): Changed size comparison to return when size == 0
        too.
        * javax/swing/JViewport.java
        (paintBackingStore): Check width and height of blitted area
        and only do blit if its > 0.
        (paintBlit): Check width and height of blitted area
        and only do blit if its > 0.

/Roman

Index: gnu/java/awt/peer/gtk/CairoGraphics2D.java
===================================================================
RCS file: /cvsroot/classpath/classpath/gnu/java/awt/peer/gtk/CairoGraphics2D.java,v
retrieving revision 1.45
diff -u -1 -5 -r1.45 CairoGraphics2D.java
--- gnu/java/awt/peer/gtk/CairoGraphics2D.java	17 Oct 2006 18:59:19 -0000	1.45
+++ gnu/java/awt/peer/gtk/CairoGraphics2D.java	18 Oct 2006 22:27:03 -0000
@@ -1210,31 +1210,31 @@
 				      (Point2D) null);
     Point2D dim = transform.transform(new Point2D.Double(ox + owidth, 
 							 oy + oheight),
 				      (Point2D) null);
     Point2D p2 = transform.transform(new Point2D.Double(ox + odx, oy + ody),
 				     (Point2D) null);
     int x = (int)pos.getX();
     int y = (int)pos.getY();
     int width = (int)(dim.getX() - pos.getX());
     int height = (int)(dim.getY() - pos.getY());
     int dx = (int)(p2.getX() - pos.getX());
     int dy = (int)(p2.getY() - pos.getY());
 
     Rectangle2D r = getRealBounds();
 
-    if( width < 0 || height < 0 )
+    if( width <= 0 || height <= 0 )
       return;
     // Return if outside the surface
     if( x + dx > r.getWidth() || y + dy > r.getHeight() )
       return;
 
     if( x + dx + width < r.getX() || y + dy + height < r.getY() )
       return;
 
     // Clip edges if necessary 
     if( x + dx < r.getX() ) // left
       {
 	width = x + dx + width;
 	x = (int)r.getX() - dx;
       }
 
Index: javax/swing/JViewport.java
===================================================================
RCS file: /cvsroot/classpath/classpath/javax/swing/JViewport.java,v
retrieving revision 1.50
diff -u -1 -5 -r1.50 JViewport.java
--- javax/swing/JViewport.java	12 Oct 2006 10:20:52 -0000	1.50
+++ javax/swing/JViewport.java	18 Oct 2006 22:27:04 -0000
@@ -825,34 +825,37 @@
       }
     // Otherwise we can perform the blitting on the backing store image:
     // First we move the part that remains visible after scrolling, then
     // we only need to paint the bit that becomes newly visible.
     else
       {
         Graphics g2 = backingStoreImage.getGraphics();
         Point viewPosition = getViewPosition();
         int dx = viewPosition.x - lastPaintPosition.x;
         int dy = viewPosition.y - lastPaintPosition.y;
         boolean canBlit = computeBlit(dx, dy, cachedBlitFrom, cachedBlitTo,
                                       cachedBlitSize, cachedBlitPaint);
         if (canBlit)
           {
             // Copy the part that remains visible during scrolling.
-            g2.copyArea(cachedBlitFrom.x, cachedBlitFrom.y,
-                        cachedBlitSize.width, cachedBlitSize.height,
-                        cachedBlitTo.x - cachedBlitFrom.x,
-                        cachedBlitTo.y - cachedBlitFrom.y);
+            if (cachedBlitSize.width > 0 && cachedBlitSize.height > 0)
+              {
+                g2.copyArea(cachedBlitFrom.x, cachedBlitFrom.y,
+                            cachedBlitSize.width, cachedBlitSize.height,
+                            cachedBlitTo.x - cachedBlitFrom.x,
+                            cachedBlitTo.y - cachedBlitFrom.y);
+              }
             // Now paint the part that becomes newly visible.
             g2.setClip(cachedBlitPaint.x, cachedBlitPaint.y,
                        cachedBlitPaint.width, cachedBlitPaint.height);
             paintSimple(g2);
           }
         // If blitting is not possible for some reason, fall back to repainting
         // everything.
         else
           {
             // If the image has not been scrolled at all, only the changed
             // clip must be updated in the buffer.
             if (dx == 0 && dy == 0)
               g2.setClip(g.getClip());
             
             paintSimple(g2);
@@ -876,34 +879,37 @@
    *
    * @param g the graphics context to use
    */
   void paintBlit(Graphics g)
   {
     // First we move the part that remains visible after scrolling, then
     // we only need to paint the bit that becomes newly visible.
     Point viewPosition = getViewPosition();
     int dx = viewPosition.x - lastPaintPosition.x;
     int dy = viewPosition.y - lastPaintPosition.y;
     boolean canBlit = computeBlit(dx, dy, cachedBlitFrom, cachedBlitTo,
                                   cachedBlitSize, cachedBlitPaint);
     if (canBlit && isPaintRoot)
       {
         // Copy the part that remains visible during scrolling.
-        g.copyArea(cachedBlitFrom.x, cachedBlitFrom.y,
-                   cachedBlitSize.width, cachedBlitSize.height,
-                   cachedBlitTo.x - cachedBlitFrom.x,
-                   cachedBlitTo.y - cachedBlitFrom.y);
+        if (cachedBlitSize.width > 0 && cachedBlitSize.width > 0)
+          {
+            g.copyArea(cachedBlitFrom.x, cachedBlitFrom.y,
+                       cachedBlitSize.width, cachedBlitSize.height,
+                       cachedBlitTo.x - cachedBlitFrom.x,
+                       cachedBlitTo.y - cachedBlitFrom.y);
+          }
         // Now paint the part that becomes newly visible.
         Shape oldClip = g.getClip();
         g.clipRect(cachedBlitPaint.x, cachedBlitPaint.y,
                   cachedBlitPaint.width, cachedBlitPaint.height);
         try
           {
             paintSimple(g);
           }
         finally
           {
             g.setClip(oldClip);
           }
       }
     // If blitting is not possible for some reason, fall back to repainting
     // everything.

Reply via email to