Search code examples
c++c-preprocessortranslation-unit

Can a define be made across all translation units?


Can a #define or similar pre-processor definition be made across all translation units?

Header implementations are useful for really small libraries since all the code can be contained and distributed with a single header with the following structure:

// library.h

void libFunc(); // forward decl

#ifdef IMPLEMENT_LIBRARY
int libState;
volatile int libVolState; // library state exposed to external processes
void libFunc(){
    // definition
}
#endif

This structure however requires the user to define IMPLEMENT_LIBRARY before the header's inclusion in only one of their translation units, meaning it can't be put in the user's header files, and might be a little confusing to someone who isn't wholely familiar with C++'s compilation rules.

If there were a way to define IMPLEMENT_LIBRARY across all TU, this could be done automatically with

#ifndef IMPLEMENT_LIBRARY
#defineToAllUnits IMPLEMENT_LIBRARY
// library state
// definitions
#endif

Does such a mechanism exist, or is the current single-header system as good as it's gonna get?


Solution

  • Some compilation units could very well have been compiled before the one which would contain a #defineToAllUnits, so that is not possible.

    In practice your problem is often solved by using the build system to pass a -DIMPLEMENTAT_LIBRARY option to compiler (or equivalent syntax). Another possibility, common when trying to achieve a wide portability with several defines, is to have a configuration header like config.h included everywhere. That header can be autogenerated at configuration time.

    You can also avoid infringing the ODR by using inline functions and variables.