4. Integration in Tulip project

The build of Tulip uses a mechanism of the GNU operating system. GNU has several tools used for the management of the configuration files. It modifies the makefile to adapt them to the distribution you have and the tools you need : the most important tools are autoconf, automake and libtool. Tulip generates three libraries : libtulip, libtulip-ogl, libtulip-qt, a software : tulip and a script : tulip-config. In a thirdparty, Tulip compiles several external libraries needed by the software : ftgl, gle, gzstream, triangle.

GNU Build system

Presentation

The goals of this system is to simplify the development of portable programs and the building of programs that are distributed as source code.

Autoconf is a tool of GNU producing shell scripts that automtically configure software packages to adapt to many kinds of UNIX systems. It is not the unique tool, it runs with others to solve all problems to making portable software. It generates configurations files : specially the configure script from a configure.in or configure.ac file. Running this script, you produce the customized Makefiles, and other files. It checks for the presence of each feature that the software need. Autoconf requires GNU M4 in order to generate the scripts.

To this end, GNU has developed a set of integrated utilities to finish the job of Autoconf. Automake is the next in run. It is a tool for generating Makefile.in from files called Makefile.am. Each Makefile.am is basically a series of make variable definitions, with the GNU Makefile standards. Automake requires Autoconf in order to be used properly.

The last is Libtool. It makes it possible to compile position independent code and build shared libraries in a portable manner. It does not require either Autoconf, or Automake and can be used independently. Automake however supports libtool and operates with it in a seamless manner.

A simple example

... to understand the basic mechanism.

To create a configure script with autoconf, you need so to write an autoconf input file configure.ac (or configure.in, use in previous versions of Autoconf). In this example, it is created a configure.ac file but Tulip contains configure.in. The both files are correct.

`hello.c` 
  #include <stdio.h>
  main(){
     printf("Hello world!\n");
  }

`Makefile.am` 
  bin_PROGRAMS = hello
  hello_SOURCES = hello.c

`configure.ac`
  AC_INIT(hello, 1.0)
  AC_CONFIG_SRCDIR(hello.c)
  AM_INIT_AUTOMAKE()
  AC_PROG_CC
  AC_OUTPUT(Makefile)

1

bin_PROGRAMS : specifies the name of programs that are building.

2

hello_SOURCES : specifies the sources code that composed the program hello.

3

AC_INIT : initializes the configure script. It must be passed as argument the name of the package and the version.

4

AC_CONFIG_SRCDIR : specifies a file in the source directory. configure script checks for the existence of this file to make sur that directory that it is told contains the source code in fact does. Any source file could do.

5

AC_INIT_AUTOMAKE : performs some further initializations that are related to the fact that we are using Automake. If you are writing your Makefile.in by hand, then you do not need to call this command.

6

AC_PROG_CC : checks to see which C compiler you have

7

AC_OUTPUT : tells the configure script to generate Makefile from Makefile.in

Create the files and Run :

$ aclocal
$ autoconf

The aclocal command installs a file called `aclocal.m4'. It contains the knowned Autoconf macros to be in use in configure.ac, like AC_PROG_CC. If you want to include your macros, you can create an acinclude.m4 file. An other cache directory is created to store the traces of the runs of m4. It is called autom4te.cache.

The autoconf command create the configure script. Then, Run :

$ automake -a 

It displays :

configure.ac: installing `./install-sh'
configure.ac: installing `./missing'
Makefile.am: installing `./INSTALL'
Makefile.am: required file `./NEWS' not found
Makefile.am: required file `./README' not found
Makefile.am: required file `./AUTHORS' not found
Makefile.am: required file `./ChangeLog' not found
Makefile.am: installing `./COPYING'
Makefile.am: installing `./depcomp'

This creates copies of install-sh, missing, COPYING, depcomp. These files are required to be present by the GNU coding standards. But NEWS, README, AUTHORS, ChangeLog are not generated. You have to create them. If you have not them and you attempt to do make distcheck, then it will deliberately fail. To create it :

$ touch NEWS README AUTHORS ChangeLog

Then, you have to run automake -a a second time. This one has created a Makefile.in file from Makefile.am. In this file, we have specify what are building and the used sources. For a library, you should define the lib_LIBRARIES variable.

Now the package is exactly in the state that the end-user will find it when person unpacks it from a source code distribution. To test you program, you can write :

$ ./configure
$ make
$ ./hello

and ...

$ make install
$ make uninstall
$ make dist
...

File adds

To integrate a new module, set of types, in the Tulip project, you must to know which library is concerned : General library, OpenGL library, QT library, ... For each case, the procedure is the same. tulip/library/tulip-ogl/ is the directory to integrate a library attached to the Opengl library. All of the .cpp files are pasted in the src subdirectory, the .h files in include/tulip and cxx files in include/tulip/cxx. Some modifications of your code should be necessary. The inclusion of files of Tulip project (included your work) is made with < and > because the compiler knows the path. For Tulip, the header files is in a special directory : tulip.

#include <tulip/TheFile.h> is an exemple of the inclusion.

So, you have to modify two files in the directory of your library to indicate the new files. include/Makefile.am is the first. You have to complete a variable containing all .h and .cxx files with your header files named nobase_include_HEADERS. This name is a choice for the processing of the GNU build system. The second one is src/Makefile.am and so, you complete the variable containing all .cpp files with your source files : libtulip_ogl_la_SOURCES, libtulip_la_SOURCES or libtulip_qt_la_SOURCES depending of the librairie you complete. You have modified the both Makefile.am but the Makefile not. To update it, you have to recreate the configure file at the root directory and run it again. To do it, run ./gen-conf and ./configure. To avoid this procedure at each modification of the Makefile.am, you can specify an option when you use configure script : --enable-maintainer-mode. See Section 1, “Options”, for more details about the options. Now, the next compilation includes your work.

Compilation directives : Makefile.am

If you want to change the directive of compilation for a program or a library, then you have to complete or modify the variables attached to the program or library. This section gives the essential variables (with their forms) for a customized compilation.

Makefile.am can use the same syntax as with ordinary makefiles. General variable can be defined, available for all your building objects.

INCLUDES = -I/dir1 -I/dir2 -I$(top_srcdir)/src...

Insert the -I flags that you want to pass to your compiler when it builds executables.

LDFLAGS = -L/dir1 -L/dir2 ...

Lists all the library files that will be compiled with make and installed with make install under prefix/lib.

LDADD = MyClasse.o ... $(top_builddir)/dir1/libmylib.la ... -lmylib ...

List a set of object files, uninstalled libraries and installed libraries that you want to link in with all of your executables. Please refer to uninstalled libraries with absolute pathnames. Because uninstalled libraries are built files, you should start your path with $(top_builddir).

There is a set of variables like top_builddir which are defined by configure when it processes a Makefile and they can be used in all others variables presented here.

srcdir

The relative path to the directory that contains the source code for that Makefile.

abs_srcdir

Absolute path of srcdir.

top_srcdir

The relative path to the top-level of the current build tree. In the top-level directory, this is the same as srcdir.

abs_top_srcdir

Absolute path of top_srcdir.

builddir

Rigorously equal to ./. Added for the symmetry only.

abs_builddir

Absolute path of builddir.

top_builddir

The relative path to the top-level of the current build tree. In the top-level directory, this is the same as builddir.

abs_top_builddir

Absolute path of top_builddir.

The following targets are used for a special directory or for special buildings:

bin_PROGRAMS = prog1 prog2 ...

Lists the executable files that will be compiled with make and installed with make install under prefix/bin, where prefix is usually /usr/local but you can specify to an other value.

lib_LIBRARIES = lib1.la lib2.la ...

Lists all the library files that will be compiled with make and installed with make install under prefix/lib.

SUBDIRS = dir1 dir2 ...

Lists all the subdirectories that we want to build before building this directory. make will recursively invoke itself in each subdirectory before doing anything on the current directory. If you mention the current directory . in SUBDIRS then the current directory will be built first, and the subdirectories will be build afterwards.

EXTRA_DIST = file1 file2 ...

Lists any files that you want to include into your source code distribution.

include_HEADERS = fich1.h fich2.h ...

Lists all the public header files in this directory that you want to install to prefix/include. If you change the keyword include by noinst, then you can specify headers that will not be installed.

For each progam, a set of variables should be declared :

prog_SOURCES = fich1.c fich2.c ...

Lists all the files that compose the source code of the program. Header files can be specified here.

prog_LDADD = $(top_builddir)/dir1/lib1.a -lext1 -lext2 ...

Lists the libraries that need to be linked with your source code. Installed libraries should be mentioned using '-l' flags. Uninstalled libraries must be mentioned using absolute pathnames. Please use $(top_buiddir) to build a path to a directory.

prog_LDFLAGS = -L/dir1 -L/dir2 -L/dir3 ...

Adds the '-L' flags that are needed to find the installed libraries that you want to link in prog_LDADD.

prog_DEPENDENCIES = dep1 dep2 dep3 ...

Lists any targets that you want to build before building this program.

In the same way, you can specify variable for a specialy library or shared library by prefixing the variable by the name of the library.

Occasionally it is useful to know which Makefile variables that Automake uses for compilations. For instance you might need to do your own compilation in some special cases. Some variables are inherited from Autoconf; these are CC, CFLAGS, CPPFLAGS, DEFS, LDFLAGS, LIBS, CXX, CXXFLAGS, ... There are some additional variables which Automake defines itself:

AM_CPPFLAGS

The contents of this variable are passed to every compilation which invokes the C preprocessor; it is a list of arguments to the preprocessor. For instance, -I and -D options should be listed here. Automake already provides some -I options automatically. AM_CPPFLAGS is ignored in preference to a per-executable (or per-library) _CPPFLAGS variable if it is defined.

INCLUDES

This does the same job as AM_CPPFLAGS. It is an older name for the same functionality. This variable is deprecated; we suggest using AM_CPPFLAGS instead.

AM_CFLAGS

This is the variable which the Makefile.am author can use to pass in additional C compiler flags. It is more fully documented elsewhere. In some situations, this is not used, in preference to the per-executable (or per-library) _CFLAGS.

COMPILE

This is the command used to actually compile a C source file. The filename is appended to form the complete command line.

AM_LDFLAGS

This is the variable which the Makefile.am author can use to pass in additional linker flags. In some situations, this is not used, in preference to the per-executable (or per-library) _LDFLAGS.

LINK

This is the command used to actually link a C program. It already includes -o $@ and the usual variable references (for instance, CFLAGS); it takes as arguments the names of the object files and libraries to link in.

Variable prefix

nobase_

e.g. nobase_include_HEADERS, mentionned that all the headers files will not be installed in the same place. It is possible to make subdirectories. nobase_ should be specified first when used in conjunction with either dist_ or nodist_.

noinst_

denotes data which do not need to be installed.

dist_ /nodist_

denotes files or data that will be included to the distribution (or not with nodist_).

References

Developing software with GNU : the GNU build system - http://www.amath.washington.edu/~lf/tutorials/autoconf/toolsmanual.html#SEC30

Autoconf Manual - http://www.gnu.org/software/autoconf/manual/

Automake Manual - http://www.gnu.org/software/automake/manual/