开发者

Automatic initialization routine in C++ library?

If i have a header file foo.h and a source file foo.cpp, and foo.cpp contains something along the lines of:

#ifdef WIN32
class asdf {
   asdf() { startup_code(); }
   ~asdf() { cleanup_code(); }
};
asdf __STARTUP_HANDLE__
#else
//unix does not require startup or cleanup code in this case
#endif

but foo.h does not define class asdf, say i have an application bar.cpp:

#include "foo.h"
//link in foo.lib, foo.dll, foo.so, etc
int main() {
   //do stuff
   return 0;
}

If bar.cpp is c开发者_如何学JAVAompiled on a WIN32 platform, will the asdf() and ~asdf() be called at the appropriate times (before main() and at program exit, respectively) even though class asdf is not defined in foo.h, but is linked in through foo.cpp?


Yes -- but be very careful. The order in which static objects (like your asdf object) are initialized is undefined. So it is undefined behavior if any other object tries to reference your object before main().

Also, __STARTUP_HANDLE__ is not a valid identifier. Double-underscores are not allowed in any identifier (even macros), and a single-underscore followed by a capital letter is also not allowed.


If it ain't broke, don't fix it. Look out for the static initialization order issue, as the other answers say. But you really should fix that reserved identifier.

__STARTUP_HANDLE__ does work similar to a runtime library, and runtime libraries use names like that, but it's not part of the runtime library so that name isn't allowed.

#ifdef WIN32
namespace { // anonymous namespace - no outside access
class asdf {
   asdf() { startup_code(); }
   ~asdf() { cleanup_code(); }
} x; // to create an instance
}


As long as the objects (foo.o) themselves are linked into the executable, this will work (assuming the static initialization order fiasco doesn't hit you). If you're pulling it in from a library (foo.lib), though, it won't unless you explicitly mark the object as an "active object," but I don't remember how to do that in MSVC.


On Windows and with DLL's you have the possibility to use the function DllMain that will be called at load etc

BOOL WINAPI DllMain(HINSTANCE hinstDLL,
                    DWORD fdwReason,
                    LPVOID lpvReserved) {  

  switch (fdwReason) {

  case DLL_PROCESS_ATTACH:    
    break;

  case DLL_THREAD_ATTACH:
    break;

  case DLL_THREAD_DETACH:
    break;

  case DLL_PROCESS_DETACH:
    break;

  default:
    break;
  }

  return TRUE;
}
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜