Bug 77060

Summary: cairo fails to compile with gcc 4.9
Product: cairo Reporter: yunlian <yunlian>
Component: generalAssignee: Chris Wilson <chris>
Status: RESOLVED FIXED QA Contact: cairo-bugs mailing list <cairo-bugs>
Severity: normal    
Priority: medium CC: amigadave, andyrtr, darxus, jjardon, tetromino
Version: 1.12.14   
Hardware: Other   
OS: All   
Whiteboard:
i915 platform: i915 features:
Bug Depends on:    
Bug Blocks: 68382    
Attachments: Self-contained Makefile to reproduce this issue

Description yunlian 2014-04-04 16:42:02 UTC
When using gcc 4.9, I got the following errors.

This is because for gcc 4.9 When using a linker plugin, compiling with the -flto option now generates slim objects files (.o) which only contain intermediate language representation for LTO. Use -ffat-lto-objects to create files which contain additionally the object code.
So a quick fix is to add '-ffat-lto-objects' when -flto is used.

  CCLD   cairo-sphinx
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_matrix_init_identity'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_matrix_init'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_scaled_font_reference'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_pattern_reference'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_font_face_reference'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_reference'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_scaled_font_destroy'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_pattern_destroy'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_font_face_destroy'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_font_options_set_antialias'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: error: undefined reference to 'cairo_font_options_set_subpixel_order'
../../util/cairo-script/.libs/libcairo-script-interpreter.so: esphinx.c:979: error: undefined reference to 'cairo_surface_create_similar'
sphinx.c:981: error: undefined reference to 'cairo_surface_get_type'
sphinx.c:984: error: undefined reference to 'cairo_boilerplate_xmalloc'
sphinx.c:987: error: undefined reference to 'cairo_surface_set_user_data'
sphinx.c:874: error: undefined reference to 'cairo_surface_get_type'
sphinx.c:881: error: undefined reference to 'cairo_surface_get_user_data'
sphinx.c:875: error: undefined reference to 'cairo_image_surface_get_width'
sphinx.c:876: error: undefined reference to 'cairo_image_surface_get_height'
sphinx.c:877: error: undefined reference to 'cairo_image_surface_get_format'
sphinx.c:890: error: undefined reference to 'cairo_create'
sphinx.c:891: error: undefined reference to 'cairo_clip_extents'
Comment 1 yunlian 2014-04-17 21:50:17 UTC
It is because when linking some .so, the flag -flto is not added.
Comment 2 Bryce Harrington 2014-07-10 23:29:32 UTC
I'm a little unclear of your use case, but I've added a --disable-lto configuration option; does that address your needs, or do you actually need to have -ffat-lto-objects set?

If you'd like to suggest a patch, that might help understand what needs changed.
Comment 3 yunlian 2014-07-10 23:43:35 UTC
I think disable lto is fine. It behaves the same as -ffat-lto-objects in this case (and behaves the same as the gcc 4.8).
If one wants lto enabled, then he needs to add -flto at link time stage.
Comment 4 Bryce Harrington 2014-07-12 01:38:46 UTC
Okay thanks, I'll close the bug out.  If you find different flags are needed, feel free to reopen.
Comment 5 Uli Schlachter 2014-07-13 12:32:56 UTC
Does anyone know why this bug actually occurs? I just got the command line that is used for calling libtool via "make V=1", added "../boilerplate/.libs/*.o" at the end, hit enter and everything linked fine.

So the problem is the static convenience library which we use for boilerplate/cairo-boilerplate.la and somehow something cannot work with LTO and static libraries. However, I can't find anything mentioning this online.

@yunlian:
In comment 1 you wrote: "It is because when linking some .so, the flag -flto is not added."
What makes you think so? Can you provide more details? That doesn't seem to match my findings.
Comment 6 Uli Schlachter 2014-07-13 14:08:17 UTC
Created attachment 102703 [details]
Self-contained Makefile to reproduce this issue

So I tried to reproduce this issue outside of cairo. The result is the attached Makefile.

Then I found the GCC LTO FAQ which states that you have to use gcc-ar, gcc-ranlib and gcc-nm instead of the tools without those prefixes. With my Makefile I tested this and noticed (after some comparing to what cairo does) that "ranlib" breaks the .a files that cairo builds by replacing the symbol index. Using my Makefile with "make RANLIB=gcc-ranlib" is enough to make it work.

Then I fought a bit against cairo's configure script and can now build cairo again, if I use
  ./configure ac_cv_prog_RANLIB=gcc-ranlib RANLIB="gcc-ranlib" AR="gcc-ar"

(No, I do not know why just "RANLIB=gcc-ranlib" isn't enough. It's just silently ignored and libtool will happily continue to use ranlib.)

We can just ignore this issue until a binutils version with plugin support is used everywhere, at which point "ranlib" and "gcc-ranlib" are equally fine. Besides that, any idea for fixing this properly?
Comment 7 Uli Schlachter 2014-08-01 21:31:36 UTC
commit c7ff9bb32e20679d6da4e8a2856be716e5bd9e12
Author: Uli Schlachter <psychon@znc.in>
Date:   Mon Jul 21 17:10:16 2014 +0200

    Remove LTO support
    
    This just never worked too well and caused too many issues. I don't think anyone
    will miss this.
    
    As mentioned in the below bug report, proper LTO support also requires using
    special versions of ranlib, nm and ar which support the LTO object files.
    Otherwise, calling the normal ranlib on an .a library breaks the list of
    exported symbols and thus completely breaks the static library.
    
    This (partly) reverts the following commits:
    
    c3645d97ebd24c6f7ad850785d585aebc706a11c configure.ac: Add a --disable-lto configure option
    d486ea30f1a58640a1178de74f705a73845b1cda configure: Conditionally include -flto
    0870c6fb5b39dcc04fa376123848adde2d06d2ce gcc-4.5 warnings and optimisation flags.
    
    (The last commit is the one which brought us -flto in the first place even
    though it doesn't talk about this. It's also the one which is only reverted
    partly.)
    
    Fixes: https://bugs.freedesktop.org/show_bug.cgi?id=77060
    CC: Chris Wilson <chris@chris-wilson.co.uk>
    Signed-off-by: Uli Schlachter <psychon@znc.in>
    Reviewed-by: Bryce Harrington <b.harrington@samsung.com>
Comment 8 Darxus 2016-07-14 17:05:14 UTC
In case anybody else ends up wanting to build commits from the several years where -flto was enabled, between the commits mentioned above, this has worked well for me:

sed -i -e 's/-flto//g' build/configure.ac.warnings

Mailing list thread where this came up, trying to find where tests started failing:  https://lists.cairographics.org/archives/cairo/2016-July/027613.html

The error that led me to this bug, and this solution, was:
undefined reference to `cairo_boilerplate_xmalloc'


Commits between which I expect this error to show up:

commit c7ff9bb32e20679d6da4e8a2856be716e5bd9e12
Author:     Uli Schlachter <psychon@znc.in>
Commit:     Bryce Harrington <bryce@osg.samsung.com>
CommitDate: Fri Aug 1 13:11:31 2014 -0700
    Remove LTO support

commit 0870c6fb5b39dcc04fa376123848adde2d06d2ce
Author:     Chris Wilson <chris@chris-wilson.co.uk>
Commit:     Chris Wilson <chris@chris-wilson.co.uk>
CommitDate: Wed May 12 20:54:49 2010 +0100
    gcc-4.5 warnings and optimisation flags.


With the above sed command I've been able to build commits back to at least:

commit 493aaf0f15bfedc88371ffab07d862a400b0da38
Author:     Andrea Canciani <ranma42@gmail.com>
Commit:     Andrea Canciani <ranma42@gmail.com>
CommitDate: Wed Nov 24 14:45:19 2010 +0100


This one and before fails:

commit 852e789b756f9589b102a4b24b85642f199d0915
Author:     Andrea Canciani <ranma42@gmail.com>
Commit:     Andrea Canciani <ranma42@gmail.com>
CommitDate: Mon Nov 1 15:53:10 2010 +0100

With:
configure: error: cannot find install-sh, install.sh, or shtool in "." "./.." "./../.."

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.