New LFS Hint: gcc_multiple_versions
rtompkin at cs.odu.edu
Tue Jul 31 18:38:34 PDT 2001
I've put together a hint for very easily changing between GCC versions. I
think you'll find it representative of a fundamental misunderstanding of the
how GCC and its associated files work. Seriously though, 'gcc -V' does not
work well (or at all) for this kind of thing. The GCC FAQ recommends two
solutions for using concurrent GCC versions so I've taken one of the
suggestions and clarified, simplified, and automated it. Please let me know
what you think.
TITLE: GCC Multiple Versions
LFS VERSION: All
AUTHOR: R. Cortland Tompkins <rtompkin at cs.odu.edu>
How to install multiple versions of GCC with a simple method of
switching between them.
version 1.0 (7/31/01)
Disclaimer: This hint has yet to be extensively tested.
TABLE OF CONTENTS:
3.1) Install GCC versions
3.2) Remove old binaries and libraries
3.3) Manually create gcc-swap infrastructure
4) swap-gcc script
As of this writing, LFS is beginning to move towards the relatively new GCC
version 3.0. Unfortunately, there are still many software packages that will
not compile with GCC 3.0; KDE maintainers advise against compiling current
versions of KDE with GCC 3.0. The GCC FAQ suggests two methods for achieving
concurrent GCC versions, one of which simply doesn't work and the other of
which is the basis for this hint. The method suggested here will allow you
to install an unlimited number of GCC versions and change between them with
a single command.
An easy way to install multiple versions of the compiler on the same system is
to configure the two compilers with different paths. We will use a shell
script to create and remove symlinks from the various compilers' individual
directories to a common directory, such as /usr/bin. By maintaining the
traditional binaries' names and paths ('/usr/bin/gcc' instead of
'/usr/bin/gcc-VERSION' or '/usr/gcc-VERSION/bin/gcc'), we can eliminate much
of the fuss of dealing with multiple compilers.
3.1) Install GCC versions:
You'll need to be super-user to complete this hint. First, create the
directory which will be home to the various GCC versions. I recommend
Next, compile GCC just as you did when creating your LFS system, but modify
the prefix path:
mkdir ../gcc-build &&
cd ../gcc-build &&
../gcc-VERSION/configure --prefix=/usr/local/gcc/VERSION \
--with-slibdir=/lib --enable-shared &&
make bootstrap &&
Repeat the above procedure for all versions of GCC you wish to install,
substituting the VERSION number where indicated (such that GCC 3.0 will be
installed in /usr/local/gcc/3.0). You must repeat the above procedure even
for the GCC version that is already installed (but specifying the new
prefix, of course). For instance, if I currently had gcc-220.127.116.11 installed
and wanted gcc-3.0 as well, I would compile gcc-18.104.22.168 (again)
with-prefix=/usr/local/gcc/22.214.171.124 as well as compile gcc-3.0
3.2) Remove old binaries and libraries:
The GCC-related binaries and libraries will reside exclusively in
/usr/local/gcc/VERSION/, therefore we can delete the libraries and
binaries originally installed in /usr. First however, you should edit
/etc/ld.so.conf to include the ./lib directories of each gcc version,
replacing VERSION as appropriate:
echo /usr/local/gcc/VERSION/lib >> /etc/ld.so.conf
Repeat the above command for each VERSION of GCC installed. Enact these
changes by running ldconfig:
Verify that the shared libraries in the various /usr/local/gcc/VERSION/lib
directories appear in ldconfig's output. Next, from the bash prompt,
execute the following command to delete your original GCC installations'
binaries from /usr/bin, substituting the version of GCC you installed with the
original LFS instructions with VERSION (i.e. 126.96.36.199 for LFS-3.0pre4):
for GCC_BINARY in $(/bin/ls --color=no /usr/local/gcc/VERSION/bin)
> /bin/rm -f /usr/bin/$GCC_BINARY
Next, we'll remove your original GCC installation's libraries from /usr/lib in
the same way. Substitute the version of your original GCC installation in
place of VERSION.
for GCC_LIBRARY in $(/bin/ls --color=no /usr/local/gcc/VERSION/lib)
> /bin/rm -f /usr/lib/$GCC_LIBRARY
You may also remove your old installation's gcc-lib directory:
rm -rf /usr/lib/gcc-lib
You have nothing to fear when deleting these formerly important files. All of
the required binaries and libraries now reside in each respective
/usr/local/gcc/VERSION directory. As long as you remebered to add the
required entries to /etc/ld.co.conf, you're good to go.
3.3) Manually create gcc-swap infrastructure:
We will be using a script called swap-gcc to change between GCC versions, but
this script relies on a few files and locations that must be set up manually
before it is run. First we'll create the symbolic links from your original
GCC version (i.e. 188.8.131.52 for LFS-3.0pre4) to /usr/bin:
for GCC_BINARY in $(/bin/ls --color=no /usr/local/gcc/VERSION/bin)
> /bin/ln -sf /usr/local/gcc/VERSION/bin/$GCC_BINARY \
swap-gcc relies on a file /usr/local/gcc/.active to figure out which GCC
version is currently active. Create it using the following command,
substituting the same GCC version number you used above (your original GCC
version) with VERSION:
echo "ACTIVE=VERSION" > /usr/local/gcc/.active
The swap-gcc script allows you to change the current GCC version with a single
command. Its contents is as follows:
---- Begin copy here ----
# Begin /usr/bin/swap-gcc
# Source the file containing the version of active GCC
# Verify that the given parameter is a valid (i.e. installed) GCC version
if [ -d /usr/local/gcc/"$1" ] && [ "$1" != "" ]; then
# For every file in the current GCC version's bin directory...
for GCC_OLD_BINARY in $(/bin/ls --color=no /usr/local/gcc/$ACTIVE/bin)
# Delete its symlinks in /usr/bin
/bin/rm -f /usr/bin/$GCC_OLD_BINARY
# For every file in the new GCC version's bin directory...
for GCC_NEW_BINARY in $(/bin/ls --color=no /usr/local/gcc/$1/bin)
# Make a symlink to the new version in /usr/bin
/bin/ln -sf /usr/local/gcc/$1/bin/$GCC_NEW_BINARY \
# Update with the current GCC version
echo "ACTIVE=$1" > /usr/local/gcc/.active
echo "Changed from GCC version $ACTIVE to GCC version $1"
echo Usage: swap-gcc gcc-version
echo " Current GCC version: $ACTIVE"
echo -n " Available GCC versions: "
# This should return all available GCC versions if set up properly
for DIRNAME in $(ls /usr/local/gcc)
echo -n "$DIRNAME "
# End /usr/bin/swap-gcc
---- End copy here ----
Put the above script in /usr/bin. Make it executable:
chmod 0755 /usr/bin/swap-gcc
Now run swap-gcc with no arguments:
You will see the currently active GCC version as well as the other available
gcc versions. You can verify the active GCC version by running 'gcc -v'. To
change the active GCC version simply use the following command, substituting
VERSION with the GCC version you want to become active:
Obviously only root will be able to change the GCC version successfully,
although I suppose you could do some fancy things with groups and permissions
to allow other users to, as well.
When it comes time to install another compiler (GCC 3.1, for example),
simply configure it with-prefix=/usr/local/gcc/3.1 and swap-gcc will require
no changes to work with the new compiler.
While I have used the above method to great success by compiling my LFS base
system with GCC 3.0 and reverting to GCC 2.95.3 to compile KDE 2.1.1, your
mileage will almost certainly vary. If you have any insights or suggestions
for this hint, please contact me at rtompkin at cs.odu.edu.
More information about the hints