Checking Run Time Behavior

Sometimes you need to find out how a system performs at run time, such as whether a given function has a certain capability or bug. If you can, make such checks when your program runs instead of when it is configured. You can check for things like the machine's endianness when your program initializes itself.

If you really need to test for a run-time behavior while configuring, you can write a test program to determine the result, and compile and run it using AC_TRY_RUN. Avoid running test programs if possible, because this prevents people from configuring your package for cross-compiling.

Running Test Programs

Use the following macro if you need to test run-time behavior of the system while configuring.

function>AC_TRY_RUN/function> (program, [action-if-true], [action-if-false], [action-if-cross-compiling]) If program compiles and links successfully and returns an exit status of 0 when executed, run shell commands action-if-true. Otherwise, run shell commands action-if-false.

This macro double quotes program, the text of a program in the current language (the section called “Language Choice”), on which shell variable and back quote substitutions are performed. This macro uses CFLAGS or CXXFLAGS, CPPFLAGS, LDFLAGS, and LIBS when compiling.

If the C compiler being used does not produce executables that run on the system where configure is being run, then the test program is not run. If the optional shell commands action-if-cross-compiling are given, they are run instead. Otherwise, configure prints an error message and exits.

In the action-if-false section, the exit status of the program is available in the shell variable $?, but be very careful to limit yourself to positive values smaller than 127; bigger values shall be saved into a file by the program. Note also that you have simply no guarantee that this exit status is issued by the program, or by the failure of its compilation. In other words, use this feature if sadist only, it was reestablished because the Autoconf maintainers grew tired of receiving "bug reports".

Try to provide a pessimistic default value to use when cross-compiling makes run-time tests impossible. You do this by passing the optional last argument to AC_TRY_RUN. autoconf prints a warning message when creating configure each time it encounters a call to AC_TRY_RUN with no action-if-cross-compiling argument given. You may ignore the warning, though users will not be able to configure your package for cross-compiling. A few of the macros distributed with Autoconf produce this warning message.

To configure for cross-compiling you can also choose a value for those parameters based on the canonical system name (Chapter 12). Alternatively, set up a test results cache file with the correct values for the host system (the section called “Caching Results”).

To provide a default for calls of AC_TRY_RUN that are embedded in other macros, including a few of the ones that come with Autoconf, you can call AC_PROG_CC before running them. Then, if the shell variable cross_compiling is set to yes, use an alternate method to get the results instead of calling the macros.

Guidelines for Test Programs

Test programs should not write anything to the standard output. They should return 0 if the test succeeds, nonzero otherwise, so that success can be distinguished easily from a core dump or other failure; segmentation violations and other failures produce a nonzero exit status. Test programs should exit, not return, from main, because on some systems (old Suns, at least) the argument to return in main is ignored.

Test programs can use #if or #ifdef to check the values of preprocessor macros defined by tests that have already run. For example, if you call AC_HEADER_STDC, then later on in configure.ac you can have a test program that includes an ansi C header file conditionally:

#if STDC_HEADERS
# include stdlib.h
#endif
     

If a test program needs to use or create a data file, give it a name that starts with conftest, such as conftest.data. The configure script cleans up by running rm -rf conftest* after running test programs and if the script is interrupted.

Test Functions

Function declarations in test programs should have a prototype conditionalized for C++. In practice, though, test programs rarely need functions that take arguments.

#ifdef __cplusplus
foo (int i)
#else
foo (i) int i;
#endif

Functions that test programs declare should also be conditionalized for C++, which requires extern "C" prototypes. Make sure to not include any header files containing clashing prototypes.

#ifdef __cplusplus
extern "C" void *malloc (size_t);
#else
char *malloc ();
#endif

If a test program calls a function with invalid parameters (just to see whether it exists), organize the program to ensure that it never invokes that function. You can do this by calling it in another function that is never invoked. You can't do it by putting it after a call to exit, because GCC version 2 knows that exit never returns and optimizes out any code that follows it in the same block.

If you include any header files, make sure to call the functions relevant to them with the correct number of arguments, even if they are just 0, to avoid compilation errors due to prototypes. GCC version 2 has internal prototypes for several functions that it automatically inlines; for example, memcpy. To avoid errors when checking for them, either pass them the correct number of arguments or redeclare them with a different return type (such as char).