Ensure Config.H Is Included Once

ensure config.h is included once

The way I do this is indeed creating a wrapper file (which I usually call global.h) that reads like this.

#ifndef MY_PROJECT_GLOBAL_H
#define MY_PROJECT_GLOBAL_H

#include <config.h>

/* Maybe other global definitions… */

#endif

Note that the recommended way to #include the config.h file is via <config.h> not "config.h" so it works better with VPATH builds.

Then, all the source files in my project #include this global.h header as their very first #include and don't care about config.h. A header file should never #include config.h since this would lead to bad name conflicts. Actually, if you stick to this guideline, your code should also work without #include guards in the configuration header.


Update regarding OP's comment

Or: How to use configuration results in headers?

If your headers need to declare different things depending on the results of the configure script, you have a number of options, none of which is perfect.

For internal headers, there is no problem. They simply rely on the macros being #defined without #includeing anything. This works if – as is recommended – all source files #include (maybe indirectly as shown above) config.h before any other header.

If the headers are to be installed publicly, this is not such a great solution. For those of your users that use Autoconf, it wouldn't be that bad, although even those would have to remember what checks to place in their configure.ac files. For users who don't use Autoconf, it will be pretty bad. If you only have a few switches (such as Glibc's fature test macros), it is okay to ask your users to #define them before #includeing your headers but if you need many, this is not a real option. Not to mention that you'll expose a lot of implementation details to your users that way.

If all you need to do is branch depending on the platform you are building for, you could probe some of the pre-defined macros like __linux or _WIN32. There is the Boost.Predef library that aims to make these check a little more convenient by providing a higher-level abstraction. The library works with C and C++ alike but, of course, it adds an additional dependency to your project.

Finally, you could make a version of your config.h that uses a macro prefix specific to your project. There is a contribution in the Autoconf macro archive that does exactly that for you. A minimal example could look like this.


AC_PREREQ([2.69])
AC_INIT([example-project], [1.0], [bugs@example.org])
AC_CONFIG_SRCDIR([example.c])
AC_CONFIG_MACRO_DIR([m4])
AC_CONFIG_HEADERS([config.h])
AX_PREFIX_CONFIG_H([public_config.h], [EXAMPLE_PROJECT], [config.h])
AC_PROG_CC
AC_OUTPUT

Save this as configure.ac, download ax_prefix_config_h.m4 from the Autoconf macro archive and place it in the sub-directory m4 and then run autoreconf && ./configure. It will create the normal config.h and in addition public_config.h where in the latter file, all macros are prefixed with EXAMPLE_PROJECT_. The file public_config.h (which also has #include guards by the way) can be installed and #included in your project's public header files if need be.

Ensure config.h included

This is not exactly what you ask, but would you consider adding config.h into every file? You could add in your CFLAGS/CXXFLAGS the -include option in order to ensure that every file in the project includes the config.h.

See https://gcc.gnu.org/onlinedocs/gcc/Preprocessor-Options.html

-include file Process file as if #include "file" appeared as the first line of the primary source file. However, the first directory searched
for file is the preprocessor's working directory instead of the
directory containing the main source file. If not found there, it is
searched for in the remainder of the #include "..." search chain as
normal. If multiple -include options are given, the files are included
in the order they appear on the command line.

How to ensure a generated config.h file is in the include path?

There is an automatism for include directories with CMAKE_INCLUDE_CURRENT_DIR in CMake:

set(CMAKE_INCLUDE_CURRENT_DIR ON)

If this variable is enabled, CMake automatically adds CMAKE_CURRENT_SOURCE_DIR and CMAKE_CURRENT_BINARY_DIR to the include path for each directory.

So I prefer to individually have the following call on a need-by basis in my CMakeLists.txt:

include_directories("${CMAKE_CURRENT_BINARY_DIR}")

Edit: Thanks for the hint of @zaufi, if your generated header file has a target scope then you should prefer (CMake >= Version 2.8.12) to make it only visible to that target (not globally to all targets) with:

target_include_directories(MyLibrary PRIVATE "${CMAKE_CURRENT_BINARY_DIR}")

Note: For source files with relative paths CMake looks in both directories CMAKE_CURRENT_SOURCE_DIR and CMAKE_CURRENT_BINARY_DIR.

binutils/bfd.h wants config.h now?

Well, the most correct way of using the header is to use autotools in your package as well. Some people are simply stubborn and I don't think you can do much about it.

An alternative is to work-around the check, by defining the macros it is using:

#define PACKAGE 1
#define PACKAGE_VERSION 1

Of course, if you are already defining those, you may as well set them to some reasonable values like:

#define PACKAGE "your-program-name"
#define PACKAGE_VERSION "1.2.3"

and use them for your program. You'll usually going to use something like that anyway at some point to keep the versions consistent.

This should be enough if you're using a standards-compliant compiler because then the __STDC__ macro will be declared and everything will go on just fine. Well, as long as the headers you're using won't require more autoconf-generated defines.

For example, if you wanted to use plugin-api.h, you'd actually have to handle checking for stdint.h and inttypes.h...

Best practice for public C declarations depending on config.h

In the specific case of <stdbool.h>, we chose to avoid depending on config.h and to rely on the C (or C++) compiler to tell us what is OK. The code includes this header, and this header sorts out the mess. It is known to work on Mac OS X, Linux, Solaris, HP-UX, AIX, Windows. The actual header file name is not ourbool.h, but I've mangled its header guards and comments so it looks as if that is what it is called. The comments quote the C99 standard for the licence to perform as it does. Note that it also works correctly if <stdbool.h> has already been included, and it works correctly if <stdbool.h> is included after it has been included (and getting this correct was not 100% pain-free). Defining __bool_true_false_are_defined is crucial to this inter-working. (When your code is in use by other people, you can't mandate that they do not use <stdbool.h> themselves, either before or after your header is included.)

#ifndef OURBOOL_H_INCLUDED
#define OURBOOL_H_INCLUDED

/*
** Ensure that type bool with constants false = 0 and true = 1 are defined.
** C++ (ISO/IEC 14882:1998/2003/2011) has bool, true and false intrinsically.
** C (ISO/IEC 9899:1999) has bool, true and false by including <stdbool.h>
** C99 <stdbool.h> also defines __bool_true_false_are_defined when included
** MacOS X <dlfcn.h> manages to include <stdbool.h> when compiling without
** -std=c89 or -std=c99 or -std=gnu89 or -std=gnu99 (and __STDC_VERSION__
** is not then 199901L or later), so check the test macro before defining
** bool, true, false. Tested on MacOS X Lion (10.7.1) and Leopard (10.5.2)
** with both:
** #include "ourbool.h"
** #include <stdbool.h>
** and:
** #include <stdbool.h>
** #include "ourbool.h"
**
** C99 (ISO/IEC 9899:1999) says:
**
** 7.16 Boolean type and values <stdbool.h>
** 1 The header <stdbool.h> defines four macros.
** 2 The macro
** bool
** expands to _Bool.
** 3 The remaining three macros are suitable for use in #if preprocessing
** directives. They are
** true
** which expands to the integer constant 1,
** false
** which expands to the integer constant 0, and
** __bool_true_false_are_defined
** which expands to the integer constant 1.
** 4 Notwithstanding the provisions of 7.1.3, a program may undefine and
** perhaps then redefine the macros bool, true, and false.213)
**
** 213) See 'future library directions' (7.26.7).
**
** 7.26.7 Boolean type and values <stdbool.h>
** 1 The ability to undefine and perhaps then redefine the macros bool, true,
** and false is an obsolescent feature.
**
** Use 'unsigned char' instead of _Bool because the compiler does not claim
** to support _Bool. This takes advantage of the license of paragraph 4.
*/

#if !defined(__cplusplus)

#if __STDC_VERSION__ >= 199901L
#include <stdbool.h>
#elif !defined(__bool_true_false_are_defined)
#undef bool
#undef false
#undef true
#define bool unsigned char
#define false 0
#define true 1
#define __bool_true_false_are_defined 1
#endif

#endif /* !_cplusplus */

#endif /* OURBOOL_H_INCLUDED */

Clearly, if you want to allow for the possibility of HAVE_STDBOOL_H, you may, but it is not needed. You can also decide what to do if HAVE_CONFIG_H is defined, but again it is not needed.

To use this, your header would contain:

#ifndef YOURHEADER_H_INCLUDED
#define YOURHEADER_H_INCLUDED
...other #includes as needed...
#include "ourbool.h" /* Or #include "project/ourbool.h" */
...other material...

extern bool boolean_and(bool lhs, bool rhs);

...other material...
#endif /* YOURHEADER_H_INCLUDED */

The precise location of ourbool.h in yourheader.h is not critical as long as it is before you declare types, functions or (perish the thought) variables that use the bool type.

Getting full source path in config.h in autotools

You are looking for the absolute path of srcdir. It can be easily done by using:

 readlink -f $srcdir

Recall that the configure.ac file is actually a shell script with m4 macros. So virtually every standard command will be accessible:
Here is a possible way to deal with your problem:

srcdir2=`readlink -f $srcdir`
AC_DEFINE_UNQUOTED([DATA_PATH], ["$srcdir2"], [data path])

How to ensure #include doesn't recursively add (only adds unique files once)

This is a linker and header file problem, you just need to add #pragma once at the top of each header files, the compiler will add the content of each header files only one time, but you must ensure that you just declare methods in your header files and write the content of those methods in other .cpp files to prevent of linking error.

Adding a dynamic symbol name not work with AC_DEFINE_UNQUOTED from configure.ac

But the final config.h file does not contain the following definition
[...] config.h.in is generated dynamically and it does not contain the
definition too.

The latter is actually the key issue. When you use AC_CONFIG_HEADERS to request that definitions be recorded in a header file instead of being expressed via compiler command-line options, Autoconf handles it by processing one or more header templates, such as config.h.in, to produce the resulting header(s). The autoconf command does not produce these templates itself, however. You can write them by hand if you wish, but a separate program, autoheader, is available to perform this job, and autoreconf (not autoconf) automatically runs autoheader to generate a template for the first header named in the first AC_CONFIG_HEADERS call.

The behavior you describe is a longtime known issue (not accounted a bug, per se), which you can find discussed in the archives of the bug-autoconf mailing list. The resolution was a documentation change, whose result you can still see in the section of the Autoconf manual that discusses Autoheader:

In order to do its job, autoheader needs you to document all of the
symbols that you might use. Typically this is done via an AC_DEFINE
or AC_DEFINE_UNQUOTED call whose first argument is a literal
symbol
and whose third argument describes the symbol (see Defining
Symbols).

(Emphasis added.)

This indeed seems to be the technically appropriate place for those details. That is, AC_DEFINE_UNQUOTED does behave as advertised, as can be seen by disabling AC_CONFIG_HEADERS (a viable workaround under many circumstances), or by employing one of the alternatives the docs go on to suggest:

you can use AH_TEMPLATE (see Autoheader
Macros), or you can supply a suitable input file for a subsequent
configuration header file. Symbols defined by Autoconf's builtin tests
are already documented properly; you need to document only those that
you define yourself.

If you were to argue that it would have been nice for that issue to be mentioned in the AC_DEFINE_UNQUOTED docs, too, then I would fully agree with you. But I do also think that the situation is considerably different now than when the doc change was first put in, on account of the introduction and rise to prevalence of autoreconf, which hides the involvement of autoheader from most users.

In any case, I'll ignore the "supply your own template" option, which is a bit fraught, and focus on AH_TEMPLATE. To use it to support the particular case presented in the question, one would add something along these lines to configure.ac:

AH_TEMPLATE([USE_test], [Define to 1 to use test])

Perhaps you ask "What's the point then? I might as well use a regular AC_DEFINE." That's a good question, to which you should indeed give careful consideration. Note well that there is no point to defining arbitrary preprocessor macros, as only those corresponding to symbols appearing in one or more of your sources will ever be expanded. That does not necessarily make configure-time macro name generation useless, but it does mean that when maintaining configure.ac, you can and should have a complete list of all the generated macro names that need to be supported. In that case, it is indeed plausible that you might write appropriate AH_TEMPLATE invocations for all the needed cases. Under most circumstances, however, going straight to (conditional) AC_DEFINEs for each symbol is probably a better choice.



Related Topics



Leave a reply



Submit