Jason Stelzer on 4 Feb 2010 16:52:48 -0800


[Date Prev] [Date Next] [Thread Prev] [Thread Next] [Date Index] [Thread Index]

Re: [PLUG] Co-existing with the package system & compiled


I've done this on various scales from completely parallel gnome
installs to a simple command line utility.

In order to do it, here are the important bits to know... but i suck
at explaining things so this is probably only going to be partially
coherent.

It all comes down to understanding how your system loads and executes
binaries. This usually is as simple as setting PATH and
LD_LIBRARY_PATH at run time.

So, in the scenario where you want to install a relatively simple
program from source a package, you could do the following....

1. Make a prefix for it. I usually use /usr/local/jps and chown it to
me. Somewhere under $HOME would work too. Anywhere really... You're
going to wind up with a $PREFIX/bin, $PREFIX/lib and $PREFIX/include
type setup.

2. Do the build... usually it's as simple as "./configure
--prefix=$PREFIX" and install

3. Set $PATH and $LD_LIBRARY_PATH in your .bashrc to include
$PREFIXE/bin and $PREFIX/lib respectively or create wrapper scripts.
Whatever you like.



##############################################


Things get slightly more complicated when you start talking about
shared libraries, but it's still very workable provided you care to be
bothered with it. Inevitably I wind up needing libFoo in order to
support weirdApp and libFoo is neither needed by nor packaged for the
distro I'm using....

Lets start simple and say that you're NOT going to have shared
libraries that are managed both by your package system AND present in
$PREFIX since this is easier and much saner to pull off.  Assume that
your system provides all the basic, boiler plate libs (from libc to
libgtk) that all your software is happy with.

Do the above steps with the following changes:

for step 2:
At build time, in order for the programs you are building to find and
use libs that you installed to $PREFIX for other programs in $PREFIX
to use, you are going to need to tell gcc to include $PREFIX/lib in
the link path, and $PREFIX/include in the #include path. To do this,
you can set (or add) the following to $CFLAGS:
export CFLAGS="${CFLAGS} -I${PREFIX}/include -L${PREFIX}/lib "

If you're building C++ code, the convention is to set CXXFLAGS.

This will cause the software you are building to 'see' the stuff you
built and installed in your custom prefix. More correctly, it allows
the configure tests to pass because the compiler and linker can find
the libs you installed.

This assumes the usual ./configure stuff. For things that build using
newer versions of autoconf/automake, there's been a trend to use
pkg-config to look up stuff like the -I and -L flags to pass to gcc
via m4 macros. For pkg-config, you set PKG_CONFIG_PATH to include the
prefix where your pkgconfig stuff was installed to. Usually this is
$PREFIX/pkgconfig.

The beauty of this method is that it generally is self contained.
There are the odd packages that want to install something to /etc/ or
install something suid. I usually avoid those, but they're out there.

Also, in most cases this doesn't even require super user privileges
and uninstalling the whole thing is as simple as rm -rf $PREFIX



#########################

Finally, if for some reason you really need 2 different builds of
libFoo v1.0 to live side by side used by different programs, you will
need to understand how shared library resolution works. Before I
really get into it, I admit that it is a GIANT pain in the ass at
times.

Also, you're going to spend time fighting with makefiles for software
that doesn't do a good job of passing user supplied options to gcc.

At build time, you can link to specific paths via -rpath /
-rpath-link. You can usually pass these options to gcc via the usual
CFLAGS method.

The man page for ld (the linker) says this about rpath-link
           When using ELF or SunOS, one shared library may require
another.  This happens when an "ld -shared" link includes a shared
library as one of the input files.

           When the linker encounters such a dependency when doing a
non-shared, non-relocatable link, it will automatically try to locate
the required shared library and include it in the link, if it is not
included explicitly.  In such a case, the -rpath-link option specifies
the first set of directories to search.  The -rpath-link option may
specify a sequence of directory names either by specifying a list of
names separated by colons, or by appearing multiple times.

           This option should be used with caution as it overrides the
search path that may have been hard compiled into a shared library. In
such a case it is possible to use unintentionally a different search
path than the runtime linker would do.

           The linker uses the following search paths to locate
required shared libraries:

           1.  Any directories specified by -rpath-link options.

           2.  Any directories specified by -rpath options.  The
difference between -rpath and -rpath-link is that directories
specified by  -rpath options are included in the executable and used
at runtime, whereas the -rpath-link option is only effective at link
time. Searching -rpath in this way is only supported by native linkers
and cross linkers which have been configured with the  --with-sysroot
option.

           3.  On an ELF system, for native linkers, if the -rpath and
-rpath-link options were not used, search the contents of the
environment variable "LD_RUN_PATH".

           4.  On SunOS, if the -rpath option was not used, search any
directories specified using -L options.

           5.  For a native linker, the search the contents of the
environment variable "LD_LIBRARY_PATH".

           6.  For a native ELF linker, the directories in
"DT_RUNPATH" or "DT_RPATH" of a shared library are searched for shared
libraries  needed by it. The "DT_RPATH" entries are ignored if
"DT_RUNPATH" entries exist.

           7.  The default directories, normally /lib and /usr/lib.

           8.  For a native linker on an ELF system, if the file
/etc/ld.so.conf exists, the list of directories found in that file.

           If the required shared library is not found, the linker
will issue a warning and continue with the link.



At run time, ld.so is the man page you want. The 2 options that are
handy for environments and wrapper scripts are LD_LIBRARY_PATH and
LD_PRELOAD. From the ld.so man page:

       LD_PRELOAD
              A whitespace-separated list of additional,
user-specified, ELF shared libraries to be loaded before all others.
This can be  used to  selectively  override  functions  in  other
shared libraries.  For setuid/setgid ELF binaries, only libraries in
the standard search directories that are also setgid will be loaded.

You can check on the sysroot stuff via gcc -v.


If it were me... well I do the whole $PREFIX thing all the time with
few issues. Now and then you may have an issue where a system upgrade
breaks compatibility with what is in $PREFIX and a rebuild of
something is needed. But... really... that's not something you can
avoid anyhow unless you package everything for your distro or only use
official packages.



On Thu, Feb 4, 2010 at 5:50 PM, JP Vossen <jp@jpsdomain.org> wrote:
> I recently mentioned how much more I like roxterm than Gnome-term, and
> that I'd suggested an "indicator" system for when background tabs
> change.  Well, the developer has graciously implemented that suggestion,
> and now I need to test it.
>
> If I do 'sudo make install', I'll nuke the stock Karmic package.  I
> think I'm OK with that--unless something breaks.  According to the docs
> there is an uninstall target, so 'sudo make uninstall && sudo aptitude
> reinstall roxterm' *should* fix everything.  I think...
>
> I tried running the compiled binary without installing it, but it broke,
> I assume due to mis-matched $other_stuff in $various_places from the
> existing version.
>
> Since I am using Ubuntu (and not Gentoo :), I vastly prefer to stay
> within the packaging system, and while I've used PPAs (for e.g., newer
> OpenOffice on Hardy) I don't think I've ever had this kind of overlap
> before.
>
> What is going to bite me?  Any suggestions?
>
>
> If anyone else wants to test it out:
>
> ### https://bugs.launchpad.net/bugs/509544
>
> $ sudo aptitude install autoconf2.13 libtool gettext libglib2.0-dev
> libgtk2.0-dev libdbus-glib-1-dev libvte-dev libglade2-dev
> ### Other things might be needed, that was all I needed, but
> ### I've already got quite a bit installed on my Karmic
> $ svn co
> https://roxterm.svn.sourceforge.net/svnroot/roxterm/trunk/roxterm ROXTerm
> $ cd ROXTerm/
> $ ./bootstrap.sh
> $ ./configure
> $ make
> #### $ sudo make install
> #### $ sudo make uninstall
>
> Thanks,
> JP
> ----------------------------|:::======|-------------------------------
> JP Vossen, CISSP            |:::======|      http://bashcookbook.com/
> My Account, My Opinions     |=========|      http://www.jpsdomain.org/
> ----------------------------|=========|-------------------------------
> "Microsoft Tax" = the additional hardware & yearly fees for the add-on
> software required to protect Windows from its own poorly designed and
> implemented self, while the overhead incidentally flattens Moore's Law.
> ___________________________________________________________________________
> Philadelphia Linux Users Group         --        http://www.phillylinux.org
> Announcements - http://lists.phillylinux.org/mailman/listinfo/plug-announce
> General Discussion  --   http://lists.phillylinux.org/mailman/listinfo/plug
>



-- 
J.
___________________________________________________________________________
Philadelphia Linux Users Group         --        http://www.phillylinux.org
Announcements - http://lists.phillylinux.org/mailman/listinfo/plug-announce
General Discussion  --   http://lists.phillylinux.org/mailman/listinfo/plug