Bug 10017

Summary: Solid source surface cache can cause cross-thread unhappiness
Product: cairo Reporter: Carlos Garcia Campos <carlosgc>
Component: generalAssignee: Carl Worth <cworth>
Status: RESOLVED FIXED QA Contact: cairo-bugs mailing list <cairo-bugs>
Severity: blocker    
Priority: medium CC: krh
Version: 1.3.15   
Hardware: Other   
OS: All   
Whiteboard:
i915 platform: i915 features:

Description Carlos Garcia Campos 2007-02-18 05:05:14 UTC
I'm having some threads problems with cairo 1.3.14 that I didn't have with 1.3.12. The problem is reproducible for me with evince, but not always and not with every document. Evince hangs and a typical Xlib async error is displayed:

Xlib: unexpected async reply (sequence 0x1421)!

We are only using X from the main thread in evince. Finally, I managed to get a backtrace:

Breakpoint 4, gdk_x_error (display=0x80fb748, error=0xb68844c8) at gdkmain-x11.c:608
608       if (error->error_code)
(gdb) thread apply all bt

Thread 2 (Thread -1232577632 (LWP 15320)):
#0  gdk_x_error (display=0x80fb748, error=0xb68844c8) at gdkmain-x11.c:608
#1  0xb7e4a845 in bonobo_x_error_handler (display=0x80fb748, error=0xb68844c8) at bonobo-ui-main.c:58
#2  0xb6df2dfa in _XError () from /usr/lib/libX11.so.6
#3  0xb6df49e4 in _XReply () from /usr/lib/libX11.so.6
#4  0xb6deba5a in XSync () from /usr/lib/libX11.so.6
#5  0xb6debbd5 in XSetAfterFunction () from /usr/lib/libX11.so.6
#6  0xb6e84c52 in XRenderFreePicture (dpy=0x80fb748, picture=35652160) at Picture.c:242
#7  0xb6fbf213 in _cairo_xlib_surface_finish (abstract_surface=0x8478f38) at cairo-xlib-surface.c:337
#8  0xb6f9bec3 in *INT_cairo_surface_finish (surface=0x8478f38) at cairo-surface.c:441
#9  0xb6f9bf70 in *INT_cairo_surface_destroy (surface=0x8478f38) at cairo-surface.c:386
#10 0xb6fa0152 in _cairo_pattern_acquire_surface_for_solid (pattern=0xb68848fc, dst=0xb4e37e38, x=<value optimized out>, y=286, width=18, height=18, 
    out=0xb6884a8c, attribs=0xb6884a40) at cairo-pattern.c:1086
#11 0xb6fa02d1 in _cairo_pattern_acquire_surface (pattern=0xb68848fc, dst=0xb4e37e38, x=64, y=286, width=18, height=18, surface_out=0xb6884a8c, 
    attributes=0xb6884a40) at cairo-pattern.c:1326
#12 0xb6fa1a10 in _cairo_pattern_acquire_surfaces (src=0xb6884ea4, mask=0xb6884bf8, dst=0xb4e37e38, src_x=64, src_y=286, mask_x=0, mask_y=0, width=18, 
    height=18, src_out=0xb6884a8c, mask_out=0xb6884a88, src_attributes=0xb6884a40, mask_attributes=0xb68849f8) at cairo-pattern.c:1468
#13 0xb6f90c73 in _cairo_image_surface_composite (op=CAIRO_OPERATOR_OVER, src_pattern=0xb6884ea4, mask_pattern=0xb6884bf8, abstract_dst=0xb4e37e38, 
    src_x=64, src_y=286, mask_x=0, mask_y=0, dst_x=64, dst_y=286, width=18, height=18) at cairo-image-surface.c:829
#14 0xb6f9b00e in _cairo_surface_composite (op=CAIRO_OPERATOR_OVER, src=0xb6884ea4, mask=0xb6884bf8, dst=0xb4e37e38, src_x=64, src_y=286, mask_x=0, 
    mask_y=0, dst_x=64, dst_y=286, width=18, height=18) at cairo-surface.c:1084
#15 0xb6f9ce34 in _clip_and_composite (clip=0xb4e4c53c, op=CAIRO_OPERATOR_OVER, src=0xb6884ea4, draw_func=0xb6f9da10 <_composite_traps_draw_func>, 
    draw_closure=0xb6884dd8, dst=0xb4e37e38, extents=0xb6884de0) at cairo-surface-fallback.c:172
#16 0xb6f9d616 in _clip_and_composite_trapezoids (src=0xb6f95d60, op=3062385916, dst=0xb4e37e38, traps=0xb6884e30, clip=0xb4e4c53c, 
    antialias=CAIRO_ANTIALIAS_DEFAULT) at cairo-surface-fallback.c:644
#17 0xb6f9db7e in _cairo_surface_fallback_stroke (surface=0xb4e37e38, op=CAIRO_OPERATOR_OVER, source=0xb6884ea4, path=0xb4e45fb8, stroke_style=0xb4e4c4c8, 
    ctm=0xb6884f40, ctm_inverse=0xb6884f10, tolerance=0.10000000000000001, antialias=CAIRO_ANTIALIAS_DEFAULT) at cairo-surface-fallback.c:801
#18 0xb6f9b564 in _cairo_surface_stroke (surface=0xb4e37e38, op=CAIRO_OPERATOR_OVER, source=0xb6884fe0, path=0xb4e45fb8, stroke_style=0xb4e4c4c8, 
    ctm=0xb4e4c564, ctm_inverse=0xb4e4c594, tolerance=0.10000000000000001, antialias=CAIRO_ANTIALIAS_DEFAULT) at cairo-surface.c:1346
#19 0xb6f8e9ba in _cairo_gstate_stroke (gstate=0xb4e4c4b8, path=0xb4e45fb8) at cairo-gstate.c:932
#20 0xb6f87549 in *INT_cairo_stroke_preserve (cr=0xb4e45fb0) at cairo.c:1906
#21 0xb6f87572 in cairo_stroke (cr=0xb4e45fb0) at cairo.c:1882
#22 0xb7944689 in CairoOutputDev::stroke (this=0x837a800, state=0xb4e3be30) at CairoOutputDev.cc:352
#23 0xb782e0bc in Gfx::opStroke (this=0xb4e11790, args=0xb6885150, numArgs=0) at Gfx.cc:1205
#24 0xb782f31d in Gfx::execOp (this=0xb4e11790, cmd=0xb68851b0, args=0xb6885150, numArgs=<value optimized out>) at Gfx.cc:712
#25 0xb782f4db in Gfx::go (this=0xb4e11790, topLevel=1) at Gfx.cc:580
#26 0xb782fedf in Gfx::display (this=0xb4e11790, obj=0xb6885270, topLevel=1) at Gfx.cc:543
#27 0xb7877c9d in Page::displaySlice (this=0x835a990, out=0x837a800, hDPI=162.69613838195801, vDPI=162.69613838195801, rotate=0, useMediaBox=0, crop=1, 
    sliceX=0, sliceY=0, sliceW=820, sliceH=615, links=0x0, catalog=0x8356880, abortCheckCbk=0, abortCheckCbkData=0x0, annotDisplayDecideCbk=0, 
    annotDisplayDecideCbkData=0x0) at Page.cc:396
---Type <return> to continue, or q <return> to quit---
#28 0xb7940469 in poppler_page_render_to_pixbuf (page=0x835f5b8, src_x=0, src_y=0, src_width=820, src_height=615, scale=2.2596685886383057, rotation=0, 
    pixbuf=0x8379690) at poppler-page.cc:395
#29 0x0809f62e in pdf_document_render_pixbuf (document=0x8337b40, rc=0x82f9740) at ev-poppler.cc:459
#30 0x0809a780 in ev_document_render_pixbuf (document=0x8337b40, rc=0x82f9740) at ev-document.c:243
#31 0x080685e1 in ev_job_render_run (job=0x82d8578) at ev-jobs.c:328
#32 0x08067029 in handle_job (job=0x82d8578) at ev-job-queue.c:102
#33 0x0806759c in ev_render_thread (data=0x0) at ev-job-queue.c:187
#34 0xb6d2c6df in g_thread_create_proxy (data=0x811b400) at gthread.c:553
#35 0xb79cd504 in start_thread () from /lib/tls/i686/cmov/libpthread.so.0
#36 0xb771c51e in clone () from /lib/tls/i686/cmov/libc.so.6

Thread 1 (Thread -1231083328 (LWP 15318)):
#0  0xb7689efa in cuserid () from /lib/tls/i686/cmov/libc.so.6
#1  0xb768de4d in vfprintf () from /lib/tls/i686/cmov/libc.so.6
#2  0xb768f0c2 in vfprintf () from /lib/tls/i686/cmov/libc.so.6
#3  0xb768b030 in vfprintf () from /lib/tls/i686/cmov/libc.so.6
#4  0xb7693d22 in fprintf () from /lib/tls/i686/cmov/libc.so.6
#5  0xb6df2432 in _XSetLastRequestRead () from /usr/lib/libX11.so.6
#6  0xb6df2d08 in _XError () from /usr/lib/libX11.so.6
#7  0xb6df49e4 in _XReply () from /usr/lib/libX11.so.6
#8  0xb6deba5a in XSync () from /usr/lib/libX11.so.6
#9  0xb6debbd5 in XSetAfterFunction () from /usr/lib/libX11.so.6
#10 0xb6de947b in XSetClipMask () from /usr/lib/libX11.so.6
#11 0xb70d32d2 in _gdk_windowing_gc_set_clip_region (gc=0x831c600, region=0x80fb748) at gdkgc-x11.c:620
#12 0xb70a95c4 in _gdk_gc_set_clip_region_internal (gc=0x8324100, region=0x0) at gdkgc.c:557
#13 0xb70bbcb6 in IA__gdk_window_end_paint (window=0x8348320) at gdkwindow.c:1090
#14 0xb723becf in IA__gtk_main_do_event (event=0xbfadcd64) at gtkmain.c:1528
#15 0xb70bc28f in gdk_window_process_updates_internal (window=0x8348320) at gdkwindow.c:2338
#16 0xb70bc4c7 in IA__gdk_window_process_all_updates () at gdkwindow.c:2401
#17 0xb70bc545 in gdk_window_update_idle (data=0x0) at gdkwindow.c:2259
#18 0xb6d0cb31 in g_idle_dispatch (source=0x845a700, callback=0xb7768740 <_itoa_lower_digits>, user_data=0x0) at gmain.c:4073
#19 0xb6d0e9d2 in IA__g_main_context_dispatch (context=0x810c2d0) at gmain.c:2049
#20 0xb6d11abf in g_main_context_iterate (context=0x810c2d0, block=1, dispatch=1, self=0x80e02c8) at gmain.c:2681
#21 0xb6d11e69 in IA__g_main_loop_run (loop=0x8115fc0) at gmain.c:2885
#22 0xb723c124 in IA__gtk_main () at gtkmain.c:1148
#23 0x0808c8f0 in main (argc=3, argv=Cannot access memory at address 0x11e0e
) at main.c:319
608       if (error->error_code)
(gdb)

It seems that a cairo_xlib_surface is destroyed, however, poppler doesn't use any xlib surface, but image surfaces.
Comment 1 Owen Taylor 2007-02-18 09:00:50 UTC
The backtrace shows you using an Xlib surface from something other than the
main thread! This particular problem could be solved (most likely) by calling
XInitThreads(), but note that there are unresolved problems using FreeType
fonts from multiple threads simultaneously, so even using a image surface from
one thread and and Xlib surface from another (like the GTK+ user interface)
could cause problems.
Comment 2 Kristian Høgsberg 2007-02-20 07:39:08 UTC
Font locking problems aside, why is there an xlib surface in there to begin with?  Evince only renders to image surfaces, and frame #13 (_cairo_image_surface_composite) shows that we're trying to composite the stroke traps into an image surface.  It looks like _cairo_pattern_acquire_surface_for_solid goes and creates an xlib surface?

Carlos, can reproduce the backtrace and try to get more info about 'dst' and 'pattern' in frame #10?
Comment 3 Carlos Garcia Campos 2007-02-27 07:57:05 UTC
Ok, I've just realized that the problem is not actually present in 1.3.14 snapshot. I got cairo from git and the latest commit in my local copy was this:

http://gitweb.freedesktop.org/?p=cairo.git;a=commitdiff;h=2715f2098127d04d2f9e304580a26cd0842c0e64;hp=b31179478bf8c18245917caa1bee19bb61f336c1

I confirm that reverting this commit fixes the problem. 
Comment 4 Carl Worth 2007-02-28 09:05:39 UTC
OK, so the solid surface cache in that commit is the source of the problem.

I'd like to get the mailing list involved in coming up with the right fix, so I'll call this bug to their attention now.

Carlos, I know you tried mailing the list already and were blocked because you weren't subscribed. I've now whitelisted your address so you shouldn't have that problem again.

-Carl
Comment 5 Behdad Esfahbod 2007-02-28 13:07:11 UTC
Reverted the patch -> d0fe666a6ab1664af36a7b242d763c72f4e9f81b

Use of freedesktop.org services, including Bugzilla, is subject to our Code of Conduct. How we collect and use information is described in our Privacy Policy.