[cgma-dev] Problems with mixed-language linking [Was: Re: [Fathom] Problems building Lasso]

Jason Kraftcheck kraftche at cae.wisc.edu
Fri Jan 15 13:31:01 CST 2010


There's been a recent discussion of a link issue Robert encountered when
building Lasso.  Because rtestc.c is C source, libtool will try to link it
using the C compiler.  This failed because libtool was not aware that the
libraries it was linking with (Lasso, MOAB. etc.) were implemented in C++
and therefore required additionally including the C++ runtime libraries
(-lstdc++ for GNU).  Those libraries are normally added automatically *if*
you link using the C++ compiler.  Robert was the first to encounter this
issue because he attempted to link Lasso with a CGM build that included no
external geometry engines.  Because the external engines (e.g. ACIS or
OpenCascade) are typically built as shared libraries, they include an
dependency on the C++ runtime that resulted in the necessary libraries being
pulled in implicitly.

So the issue here is how to best support linking a *static* library written
in C++ that implements a C API.  I can think of a few possible solutions,
none of which are optimal.  Any other suggestions are welcome.  I also sent
a message to the libtool mailing list in hopes that someone on that list
might suggest a better solution.

1) Require everything to be linked using the C++ compiler.

This will always work, but somewhat defeats the purpose of having C APIs
like iMesh.  And will require all of our C tests to be compiled with the C++
compiler to get GNU autotools to link things correctly.

2) Hard-code the necessary C++ runtime libraries for different platform and
compiler combinations into our configure scripts and then explicitly include
the libraries in link statements (e.g. -lstdc++).

This is more work, will require ongoing maintenance, and limits the
platforms/compilers we can build on to those for which we know the c++
runtime library(s).

This also may not work on all platforms.  Including the C++ runtime may not
be sufficient to ensure that static initializations are done for C++ code.
On some platforms it may be necessary to link with the C++ compiler anyway.
 This does not appear to be the case on Linux.  I don't have access to
platforms other than Linux right now, so I can't test this elsewhere.  I've
attached a simple test code in case anyone feels inclined to try it on other
platforms.  If static initialization works correctly, the two output values
should be the same and not be zero.

Also, if anyone has access to other unixy platforms, it would be nice to
start accumulating a list of C++ runtime libraries for different
platform/compiler combinations.  This can typically be found in the output
of 'ldd libsomething.so', where libsomething.so is a shared library
implemented using C++.

3) Build our stuff as shared libraries.

This will make these issues go away.  Shared libraries have their own
dependency list which will automatically include c++ runtime libraries.
Shared libraries also contain initialization and finalization sections that
are used to handle construction and destruction of static/global C++
objects.  It will also eliminate other mixed-language issues such as using
ld or the fortran compiler to link with fortran code and not finding the C
runtime.

There area few disadvantages to this approach:

a) Not all platforms support shared libraries.  This was often the case on
large parallel computers in the past.  However, this is becoming much less
common now.  There are many advantages to shared libraries other than just
reducing memory requirements (for example, this very issue.)  Shared
libraries are the modern way of doing things.  Further, we wouldn't need to
disable the ability to build static libraries.  Anyone who must use static
libraries will just have to do a little more work to get things to link
correctly.

b) All dependencies must be shared libraries.  A few libraries (e.g netcdf)
have the annoying tendency to build only static libs by default (then again,
so do we right now.)

c) Messing with LD_LIBRARY_PATH and/or special linker flags to find
libraries at runtime.  Libtool will largely take care of these details for
us, but for those building w/out libtool some extra work may be required.
I'm not sure how much of an issue this really is, as users already face this
kind of issue for many of the dependencies.


Thoughs?  Suggestions?  Preferences?

- jason
-------------- next part --------------
A non-text attachment was scrubbed...
Name: mixed.tar.gz
Type: application/x-gzip
Size: 615 bytes
Desc: not available
URL: <http://lists.mcs.anl.gov/pipermail/cgma-dev/attachments/20100115/ff845ed4/attachment.bin>


More information about the cgma-dev mailing list