Compiling Software From Source Code

One of the big challenges of linux that newbies face is compiling software. Generally, if you run a binary based distribution, you should try to avoid compiling software. Compiling software on a binary distribution has a couple of downsides. First, the software is not managed by the distribution package manager, and secondly, it’s hard and generally unnecessary – you should be able to find a package for your distribution somewhere. However, if you do need to compile software – say you need a bleeding edge version of something, or there is no compatible package for your distribution – this howto could help you to compile the software successfully.

pre-requisites

Compiling software requires (obviously) a compiler. GCC is the default compiler used in almost every distribution I’ve ever come across. You will also need the automake tools, and the various applications that may be required to compile software like flex and bison. A lot of distributions have a complete development toolchain installed by default. However, some desktop focussed distributions allow for installing development as an option at install time, or leave it to you to add them later. For example, (k)ubuntu does not install any development tools by default. However, they do provide a special package called build-essential that installs a development toolchain for you. To install, type the following into a terminal:

sudo aptitude install build-essential

Alternatively, if you are not running Ubuntu, you’ll need to make sure you have (at the very least) the gcc and make packages installed.

how source code is distributed

To compile an application, you’ll need the source code. The source code is the code that a programmer writes into an editor. The compiler then converts it into the binary code that a computer can understand. When a programmer releases an application in source form, it is usually released as a series of files and directories all rolled up into what is commonly called a tarball – file that has either a tar.gz (a tar file compressed with gzip) or tar.bz2 (a tar file compressed with bzip2) extension. When you download one of these files, before you can do anything with it, you’ll need to extract all the files and directories. So, you’ll need to cd to the directory where the tarball is, and use the following command for a gzip archive:

tar -zxpf appname.tar.gz

or this command for a bzip2 archive:

tar -jxpf appname.tar.bz2

dependencies

Before we get into how to actually compile software, a quick word about dependencies. Often when developers make open source software, they incorporate features or functionality from other people’s software provide functionality in their own. For example, a video application may use features from the ffmpeg package. Accordingly, the video application will need to have access to the ffmpeg source code in order for it to compile.

Often when you download a tarball from a developer’s website, they’ll tell you what the programme depends on. However, more often than not, you’ll find out when you start compiling, and you’ll have to install the relevant packages yourself. In most binary based distributions, when a source package depends on another application, you actually need to install two packages – the main package and a package with the same name, but includes a dev or devel suffix. So, for example, if the application depends on gstreamer, you’d need to install libgstreamer0.10-0 and libgstreamer0.10-dev. I’ll talk more about how to resolve dependency issues in the next section.

actually compiling stuff

I’ll run you through an install of basket as an example to show you how to install software from source. Having downloaded the tarball file to ~/tmp, I change to the tmp directory:

matt@laptop:~$ cd tmp

then untar the basket tarball and change to the resulting directory:

matt@laptop:~/tmp$ tar -zxpf basket-0.6.0.tar.gz
matt@laptop:~/tmp$ cd basket-0.6.0/

We then want to see if there are any specific compile time options for basket. These are options you can add to the compilation commands that are optional, but customise the way the application is compiled and installed. So enter:

matt@laptop:~$ ./configure --help=short

The relevant parts of the output are under the headings Optional Features: and Optional Packages:. What follows is just a sample of the output of the above command from basket. The output will be different for each application.

Optional Features:
--disable-mt            link to non-threaded Qt (deprecated)
--disable-threading     disables threading even if libpthread found
--disable-rpath         do not use the rpath feature of ld
--disable-path-check    dont try to find out, where to install
--disable-largefile     omit support for large files
Optional Packages:
--with-qt-includes=DIR  where the Qt includes are.
--with-qt-libraries=DIR where the Qt library is installed.
--without-arts          build without aRts default=no

There are no options there, that are of interest to us. Sometimes there are options to disable or enable certain features of the software application. You can usually do this by adding –disable-feature or –enable-feature as arguments to the configure script. You should also note that under Optional Packages: sometimes, each line ends with (default: test) (although not in the case of basket). This means that the configuration script will test to see if you have those packages, if not, then support fo that package won’t be included. One other configuration option you should be aware of is the –prefix option. This tells the application where to install all its bits. Normally compiled software is installed in the /usr/local directory tree. The executables go in /usr/local/bin, the library files go in /usr/local/lib and so on. Using the –prefix option, you can tell the configuration script to install it somewhere else. This is very important for kde based applications, which need to be installed in the same place as the rest of kde. So for ubuntu, fedora and mandriva (and their derivatives), you would set –prefix=/usr. You should be able to find where your kde installation is by typing echo $KDEDIR.

So having said all that, to install basket under /usr (which is where kubuntu puts kde and associated applications), we enter this command:

matt@laptop:~/tmp/basket-0.6.0$ ./configure --prefix=/usr

You should get a long list of output that looks a bit like this:

checking build system type... i686-pc-linux-gnu
checking host system type... i686-pc-linux-gnu
checking for a BSD-compatible install... /usr/bin/install -c
checking whether build environment is sane... yes
checking for gawk... gawk

However, in this case I’ve encountered a dependency problem. I’ve got this at the end of the output:

====================================
===  BasKet Note Pads - WARNING  ===================================
====================================
=
= BasKet Note Pads requires kdepim.
= BasKet Note Pads will still be built, but there is no
= Kontact integration.
=
= Packages you need to install if you want Kontact integration:
=  Suse:         kdepim3-devel
=  Kubuntu:      kdepim-dev
=  Fedora Core:  kdepim-devel
=  Mandriva:     libkdepim2-common-devel & libkdepim2-kontact-devel
=  Gentoo:       kde-base/kontact
=

I actually don’t want PIM support for basket, so I am happy to ignore this warning. Also note that this is quite a user-friendly error. Sometimes they’re not so friendly, for example this error I came across when trying to compile avidemux:

checking for pkg-config... /usr/bin/pkg-config
Package gtk+-2.0 was not found in the pkg-config search path.
Perhaps you should add the directory containing "gtk+-2.0.pc" to the PKG_CONFIG_PATH environment variable
No package "gtk+-2.0" found
************ Cannot identify gtk2 version ***************
configure: error: *** pkg-config installed incorrectly or gtk2-dev absent ! ***

This means I need to install the gtk+-2.0 development package. Often a dependency is a library file, rather than the application itself in this case, there is no gtk2-dev package. The package I need is actually libgtk2.0-dev. Often you’ll have to have a look through the packages in your package manager to see what package is the appropriate one.

Sometimes you need to repeat this process several times to get the ./configure script to run through without error. A lot of the time, you can run the ./configure script and get no errors. Anyway, back to basket … Once you’ve successfully run the ./configure script without any errors, you can move on to the next step – make. This is pretty straightforward. Just type:

matt@laptop:~/tmp/basket-0.6.0$ make

This will spit out a lot of output, and could go on for quite some time – depending on the size of the application, and the speed of your cpu. Almost without exception, if you’ve successfully run the ./configure script without error, the make command should run without a hitch.

Once make is finished, you need to install the various files that make up the application. You need to be root to do this if you are installing to a directory outside of your home directory. So type the command:

matt@laptop:~/tmp/basket-0.6.0$ sudo make install
Password:

Enter your root password, and you will get a whole lot more output telling you where all the files in the application are being installed. If that runs without error (and it should if you’ve done everything else without error), then you should be able to start the application. In our case, we simply type basket at the prompt, and basket runs.