[cairo] Endless loop in _cairo_stroker_line_to_dashed()

Hans Breuer hans at breuer.org
Sun Jun 28 03:00:04 PDT 2009


a Dia user has a proprietary diagram to reproduce the above error
on Linux and Windows [1] with cairo 1.8.4, 1.8.6 and current master.

The trigger seems to be a combination of very thin lines (Dia's buggy 
attempt to support hairlines [2]), dashing that line and some 'unstable' 
math assumption in _cairo_stroker_line_to_dashed().

It is going into an endless loop in 
cairo-stroke-path.c:_cairo_stroker_line_to_dashed().
To me this looks like a bug in cairo, very hard to work around by 
application code.

The loop "while (remain)" is only left if 'remain' evaluates to exactly 
zero, but in the given case it never gets closer than 5.3172935301562e-315.

Furher loop cycles don't modify that value anymore. 
_cairo_stroker_add_sub_edge() adds no edge due to p1==p2 (in cairo fixed 
oordinates). The patch below adds an additional check to leave the loop but 
I'm uncertain if this is the right way to fix the issue.

Regards,
	Hans

[1] http://mail.gnome.org/archives/dia-list/2009-June/msg00062.html
[2] http://git.gnome.org/cgit/dia/tree/plug-ins/cairo/diacairo-renderer.c#n170


diff --git a/src/cairo-path-stroke.c b/src/cairo-path-stroke.c
index 79bf09b..9e641c7 100644
--- a/src/cairo-path-stroke.c
+++ b/src/cairo-path-stroke.c
@@ -934,6 +934,9 @@ _cairo_stroker_line_to_dashed (void *closure,
             }
         }

+       if (_cairo_fixed_from_double (step_length) <= CAIRO_FIXED_EPSILON)
+           break; /* avoid an endless loop with very small values */
+
         _cairo_stroker_dash_step (&stroker->dash, step_length);
         segment.p1 = segment.p2;
      }


-------- Hans "at" Breuer "dot" Org -----------
Tell me what you need, and I'll tell you how to
get along without it.                -- Dilbert


More information about the cairo mailing list