www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - Static initialization order

reply Justin Johansson <no spam.com> writes:
I'm sure many of you are across this problem.

Sorry if this post is about a topic that has been
dealt with conclusively before on this NG.

May I ask, what are the best solutions for C++ (my current
dilemma) and what steps will be taken in D2 to zap it.

Cheers

-- Justin Johansson
Feb 03 2010
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Justin Johansson wrote:
 May I ask, what are the best solutions for C++ (my current
 dilemma) and what steps will be taken in D2 to zap it.

Within a module, static initialization is done in lexical order. Across modules, static initialization is performed so that imported modules are initialized before the importer. This is true in D1 as well as D2.
Feb 03 2010
parent reply Justin Johansson <no spam.com> writes:
Walter Bright wrote:
 Justin Johansson wrote:
 May I ask, what are the best solutions for C++ (my current
 dilemma) and what steps will be taken in D2 to zap it.

Within a module, static initialization is done in lexical order. Across modules, static initialization is performed so that imported modules are initialized before the importer. This is true in D1 as well as D2.

Thanks for the clarification for both D1 and D2. Certainly D's approach beats the hit-and-miss approach in C++.
Feb 03 2010
parent reply =?UTF-8?B?QWxpIMOHZWhyZWxp?= <acehreli yahoo.com> writes:
Justin Johansson wrote:
 Walter Bright wrote:
 Justin Johansson wrote:
 May I ask, what are the best solutions for C++ (my current
 dilemma) and what steps will be taken in D2 to zap it.

Within a module, static initialization is done in lexical order. Across modules, static initialization is performed so that imported modules are initialized before the importer. This is true in D1 as well as D2.

Thanks for the clarification for both D1 and D2. Certainly D's approach beats the hit-and-miss approach in C++.

That's unfortunate and has been many causes of bugs for C++ programs. C++ follows C's model of separate compilation. The C++ compiler never sees more than one translation unit (a source file after all preprocessor magic applied to it) at a time. The best C++ could do was to define the order in that single translation unit; and that is the same order as D's. Ali
Feb 07 2010
parent reply Justin Johansson <no spam.com> writes:
Ali Çehreli wrote:
 Justin Johansson wrote:
  > Walter Bright wrote:
  >> Justin Johansson wrote:
  >>> May I ask, what are the best solutions for C++ (my current
  >>> dilemma) and what steps will be taken in D2 to zap it.
  >>
  >> Within a module, static initialization is done in lexical order.
  >>
  >> Across modules, static initialization is performed so that imported
  >> modules are initialized before the importer.
  >>
  >> This is true in D1 as well as D2.
  >
  > Thanks for the clarification for both D1 and D2.  Certainly D's approach
  > beats the hit-and-miss approach in C++.
 
 That's unfortunate and has been many causes of bugs for C++ programs.
 
 C++ follows C's model of separate compilation. The C++ compiler never 
 sees more than one translation unit (a source file after all 
 preprocessor magic applied to it) at a time.
 
 The best C++ could do was to define the order in that single translation 
 unit; and that is the same order as D's.
 
 Ali

Thanks for your comment, Ali. Yes, well, that unfortunately is what I'm doing in my C++ project .. putting implementation of all the static class declarations in one big file. It's a bit of a pain because that makes for another file to maintain rather having the static init source code in the respective class .cpp file. On the other hand, at least I can see all the static inits in one place and that turns out to be a small benefit. The only other idea, of dubious worth, is to create a "proxy" initialization class which is parameterized with a init-order priority attribute. Concept is that all these proxies would collated and sorted according to their priority. Upon entering main() each static init is fired off in the priority-ordered init order. D1 isn't completely without its warts though. When I was trying to implement this particular project in D1, I had all sorts of circular reference problems, either compiling or linking code (can't remember which), to do with static objects and so I still had to resort to collating some disparate code into a single file. Like I say, I cannot remember the full details of the workaround but there was something on D.help which addressed the issue. Cheers Justin
Feb 07 2010
parent reply BCS <none anon.com> writes:
Hello Justin,
 Yes, well, that unfortunately is what I'm doing in my C++ project ..
 putting implementation of all the static class declarations in one
 big file.

could you do that same sort of things that you do with .h files? void SomeStaticInitFunction() { static bool once = false, done = false; if(once) { assert(done); return; } once = true; // call the StaticInitFunctions that you depend on: done = true; // do other stuff. } and then call the StaticInitFunctions whenever and wherever you want. -- <IXOYE><
Feb 07 2010
parent reply Justin Johansson <no spam.com> writes:
BCS wrote:
 Hello Justin,
 Yes, well, that unfortunately is what I'm doing in my C++ project ..
 putting implementation of all the static class declarations in one
 big file.

could you do that same sort of things that you do with .h files?

Sorry, I'm not sure I understand your question. For my problem, .h files are not the issue; the issue is about establishing the correct order for statically constructed objects which exist in .cpp files. Hence the reason for one big .cpp file.
 void SomeStaticInitFunction()
 {
   static bool once = false, done = false;
   if(once) { assert(done); return; }
   once = true;
 
   // call the StaticInitFunctions that you depend on:
 
   done = true;
 
   // do other stuff.  }
 
 and then call the StaticInitFunctions whenever and wherever you want.
 
 -- 
 <IXOYE><

Feb 09 2010
parent BCS <none anon.com> writes:
Hello Justin,

 BCS wrote:
 
 Hello Justin,
 
 Yes, well, that unfortunately is what I'm doing in my C++ project ..
 putting implementation of all the static class declarations in one
 big file.
 


files are not the issue; the issue is about establishing the correct order for statically constructed objects which exist in .cpp files. Hence the reason for one big .cpp file.

I'm suggesting that a variation on the idea of scope guards be used: if static initializer A depends on static initializer B having been run, than at the top of A, it calls B. Then to prevent both of them from being called more than once, you put in a short-circuit return at the top based on a function-local static bool and (optionally) a check to see if the function is getting called in a loop. Than you make shure that every static inilizer gets called at least once and the order sort's its self out. I don't remember exactly how static initializers are setup in C++ so you might have to put the above in extra functions that get called from the static initializers. -- <IXOYE><
Feb 09 2010