init code in header-only library

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • Christof Warlich

    init code in header-only library

    Hi,

    I'm working on a (template) library that is up to now entirely
    implemented in header-files. This makes the library quite convenient to
    use as no extra object code needs to be linked when using the library.
    But now, the library needs to run some initialization code at system
    startup. Usually, this initialization code would be called from a .cc
    file once at system startup, e.g. by assigning the init function to a
    global variable:

    // init.cc
    #include <stdio.h>
    inline int init() {
    // whatever needs to be initialized goes here
    printf("initial izing\n");
    return 0;
    }
    static int dummy = init();

    With this simple approach, calling init() cannot be done from a header
    file, as it will be called as often as it will be included by .cc files.
    Thus, it is required to link the application with the object derived
    from init.cc now.

    To avoid this, I replaced the above with the following code, now having
    everything defined in a header file:

    // init.h
    #include <stdio.h>
    inline int init() {
    // whatever needs to be initialized goes here
    printf("initial izing\n");
    return 0;
    }
    // ensure that init is called exactly once
    inline int initialize(void ) {
    static int dummy = init();
    return 0;
    }
    static int dummy = initialize();

    This works as desired: With the two sample application files one.cc and
    two.cc:

    // one.cc
    #include "init.h"
    int main(void) {
    return 0;
    }

    // two.cc
    #include "init.h"

    and compilation:

    $ g++ -I. one.cc two.cc

    the init() function is only called once:

    $ ./a.out
    initializing

    The only concern is that a new global dummy variable will be created for
    every application file that includes init.h. Any ideas to avoid this?

    Christof
  • Victor Bazarov

    #2
    Re: init code in header-only library

    Christof Warlich wrote:
    Hi,
    >
    I'm working on a (template) library that is up to now entirely
    implemented in header-files. This makes the library quite convenient
    to use as no extra object code needs to be linked when using the
    library. But now, the library needs to run some initialization code
    at system startup. Usually, this initialization code would be called
    from a .cc file once at system startup, e.g. by assigning the init
    function to a global variable:
    >
    // init.cc
    #include <stdio.h>
    inline int init() {
    // whatever needs to be initialized goes here
    printf("initial izing\n");
    return 0;
    }
    static int dummy = init();
    >
    With this simple approach, calling init() cannot be done from a header
    file, as it will be called as often as it will be included by .cc
    files. Thus, it is required to link the application with the object
    derived from init.cc now.
    >
    To avoid this, I replaced the above with the following code, now
    having everything defined in a header file:
    >
    // init.h
    #include <stdio.h>
    inline int init() {
    // whatever needs to be initialized goes here
    printf("initial izing\n");
    return 0;
    }
    // ensure that init is called exactly once
    inline int initialize(void ) {
    static int dummy = init();
    return 0;
    }
    static int dummy = initialize();
    >
    This works as desired: With the two sample application files one.cc
    and two.cc:
    >
    // one.cc
    #include "init.h"
    int main(void) {
    return 0;
    }
    >
    // two.cc
    #include "init.h"
    >
    and compilation:
    >
    $ g++ -I. one.cc two.cc
    >
    the init() function is only called once:
    >
    $ ./a.out
    initializing
    >
    The only concern is that a new global dummy variable will be created
    for every application file that includes init.h. Any ideas to avoid
    this?
    No offence, but you're trying to avoid using object modules in your
    library and still want to have a feature that is only possible to
    have *if* your library has at least one object module. It's like
    you want to have your cake and eat it too (although I don't really
    like that expression).

    You can, if you want, just *document* that your library needs to
    be initialised by calling your initialisation function. If the user
    needs to use your library before 'main' is called, they would need
    to define a single static variable somewhere in their code, and use
    that variable's initialisation to call your function. If they don't
    care about initialising your library before 'main', they could just
    call your initialisation function at the beginning of 'main'. No
    problem. Let the user decide.

    V
    --
    Please remove capital 'A's when replying by e-mail
    I do not respond to top-posted replies, please don't ask


    Comment

    • Christof Warlich

      #3
      Re: init code in header-only library

      Victor Bazarov schrieb:
      >To avoid this, I replaced the above with the following code, now
      > having everything defined in a header file:
      >>
      >// init.h
      >#include <stdio.h>
      >inline int init() {
      > // whatever needs to be initialized goes here
      > printf("initial izing\n");
      > return 0;
      >}
      >// ensure that init is called exactly once
      >inline int initialize(void ) {
      > static int dummy = init();
      > return 0;
      >}
      >static int dummy = initialize();
      >>
      >This works as desired: With the two sample application files one.cc
      >and two.cc:
      >>
      >// one.cc
      >#include "init.h"
      >int main(void) {
      > return 0;
      >}
      >>
      >// two.cc
      >#include "init.h"
      >>
      >and compilation:
      >>
      >$ g++ -I. one.cc two.cc
      >>
      >the init() function is only called once:
      >>
      >$ ./a.out
      >initializing
      >>
      >The only concern is that a new global dummy variable will be created
      >for every application file that includes init.h. Any ideas to avoid
      >this?
      >
      No offence, but you're trying to avoid using object modules in your
      library and still want to have a feature that is only possible to
      have *if* your library has at least one object module.
      Please have a closer look at the code example above: It shows that it
      _is_ possible to execute initialization code exactly once before main()
      _without_ the need of a dedicated library object module. The files
      one.cc and two.cc are examples for application code that is _using_ the
      library, hence including the library's interface definition, i.e. init.h
      in the example above. Sorry that I haven't made that clear enough.

      So why did I post, you may ask. Generally, I'm quite happy with this
      solution, but it comes at the cost of needing the space of an integer
      per application object file that uses the library (due to the global
      dummy variable). Thus, I'm asking for ideas if this could be avoided or
      at least be minimized. All I could think of so far was to make dummy a
      char instead of an int to reduce the amount of memory being occupied.

      Comment

      Working...