Autotools

Warning

These tools are still experimental (so subject to breaking changes) but with very stable syntax. We encourage the usage of it to be prepared for Conan 2.0.

The Autotools build helper is a wrapper around the command line invocation of autotools. It will abstract the calls like ./configure or make into Python method calls.

The Autotools helper can be used like:

from conans import conanfile
from conan.tools.gnu import Autotools

class App(ConanFile):
    settings = "os", "arch", "compiler", "build_type"

    def build(self):
        autotools = Autotools(self)
        autotools.configure()
        autotools.make()

It will read the conanbuild.conf file generated by the AutotoolsToolchain to know read the arguments for calling the configure and make scripts:

  • configure_args: Arguments to call the configure script.

  • make_args: Arguments to call the make script.

Methods

constructor

def __init__(self, conanfile, namespace=None):
  • conanfile: the current recipe object. Always use self.

  • namespace: this argument avoids collisions when you have multiple toolchain calls in the same recipe. By setting this argument, the conanbuild.conf file used to pass information to the toolchain will be named as: <namespace>_conanbuild.conf. The default value is None meaning that the name of the generated file is conanbuild.conf. This namespace must be also set with the same value in the constructor of the AutotoolsToolchain so that it reads the information from the proper file.

configure(self, build_script_folder=None, args=None):

def configure(self, build_script_folder=None, args=None):

Call the configure script.

  • build_script_folder (Optional, Defaulted to None): Subfolder where the configure script is located.

    If None, conanfile.source_folder will be used.

  • args (Optional, Defaulted to None): List of arguments to use for the

    configure call.

autoreconf(self, args=None):

def autoreconf(self, args=None)

Call the autoreconf program.

Parameters:
  • args (Optional, Defaulted to None): List of arguments to use for the

    autoreconf call.

make(self, target=None, args=None):

def make(self, target=None)

Call the make program.

Parameters:
  • target (Optional, Defaulted to None): Choose which target to build. This allows building of e.g., docs, shared libraries or install for some AutoTools projects.

  • args (Optional, Defaulted to None): List of arguments to use for the make call.

install(self, args=None):

def install(self, args=None)

This is just an “alias” of self.make(target="install")

Parameters:
  • args (Optional, Defaulted to None): List of arguments to use for the make install call. By default an argument DESTDIR=self.package_folder is added to the call if the passed value is None.

A note about relocatable shared libraries in macOS built the Autotools build helper

When building a shared library with Autotools in macOS a section LC_ID_DYLIB and another LC_LOAD_DYLIB are added to the .dylib. These sections store install_name information, which is the location of the folder where the library or its dependencies are installed. You can check the install_name of your shared libraries using the otool command:

$ otool -l path/to/libMyLib.dylib
...
cmd LC_ID_DYLIB
    cmdsize 48
        name path/to/libMyLib.dylib (offset 24)
time stamp 1 Thu Jan  1 01:00:01 1970
    current version 0.0.0
compatibility version 0.0.0
...
Load command 11
        cmd LC_LOAD_DYLIB
    cmdsize 48
        name path/to/dependency.dylib (offset 24)
time stamp 2 Thu Jan  1 01:00:02 1970
    current version 1.0.0
compatibility version 1.0.0
...

Why is this a problem when using Conan?

When using Conan the library will be built in the local cache and this means that this location will point to Conan’s local cache folder where the library was installed. This location is where the library tells any other binaries using it where to load it at runtime. This is a problem since you can build the shared library in one machine, then upload it to a server and install it in another machine to use it. In this case, as Autotools behaves by default, you would have a library storing an install_name pointing to a folder that does not exist in your current machine so you would get linker errors when building.

How to adress this problem in Conan

The only thing Conan can do to make these shared libraries relocatable is to patch the built binaries after installation. To do this, when using the Autotools build helper and after running the Makefile’s install() step, you can use the fix_apple_shared_install_name() tool to search for the built .dylib files and patch them by running the install_name_tool macOS utility, like this:

from conan.tools.apple import fix_apple_shared_install_name
class HelloConan(ConanFile):
  ...
  def package(self):
      autotools = Autotools(self)
      autotools.install()
      fix_apple_shared_install_name(self)

This will change the value of the LC_ID_DYLIB and LC_LOAD_DYLIB sections in the .dylib file to:

$ otool -l path/to/libMyLib.dylib
...
cmd LC_ID_DYLIB
    cmdsize 48
        name @rpath/libMyLib.dylib (offset 24)
time stamp 1 Thu Jan  1 01:00:01 1970
    current version 0.0.0
compatibility version 0.0.0
...
Load command 11
        cmd LC_LOAD_DYLIB
    cmdsize 48
        name @rpath/dependency.dylib (offset 24)
time stamp 2 Thu Jan  1 01:00:02 1970
    current version 1.0.0
compatibility version 1.0.0
...

The @rpath special keyword will tell the loader to search a list of paths to find the library. These paths can be defined by the consumer of that library by defining the LC_RPATH field. This is done by passing the -Wl,-rpath -Wl,/path/to/libMyLib.dylib linker flag when building the consumer of the library. Then if Conan builds an executable that consumes the libMyLib.dylib library, it will automatically add the -Wl,-rpath -Wl,/path/to/libMyLib.dylib flag so that the library is correctly found when building.