keelar
keelar

Reputation: 6026

Ensure the construction and destruction order of static variables in c++

I am trying to find a good way to ensure the construction and destruction order of static variables. As far as I know about static variables, they are constructed and destructed in the following ways:

  1. Destruction order of static objects are in the reverse order of their construction.

  2. If static variables are defined global space in different files, then their construction order is not guaranteed.

  3. However, if a static variable is defined in a function, then local static variable is constructed when the first time execution hits its declaration.

Based on the rules above, I wrote the following c++ code to ensure static variable b is always destructed before static variable a, which in my experiment ensure the construction order and destruction order:

in file A.h

class A {
 public:
  SomeClass* GetStatic() {
    static SomeClass a;
    return &a;
  }
}

in file B.h:

#include "A.h"
class B {
 public:
  AnotherClass* GetStatic() {
    A::GetStatic();  // a dummy call to force the static local variable in 
                     // A::GetStatic() get initialized before the b.
    static AnotherClass b;
    return &b;
  }
}

In the above example, I put a dummy call A::GetStatic(); right before the declaration of static AnotherClass b;. If rule 3 holds, this ensures a is initialized before b. And because of rule 1, it can be guaranteed that b is destructed before a.

And my questions are:

  1. Can I know whether what I've done is correct or might goes wrong in certain corner case?
  2. Is there a better or best way to ensure the construction or destruction order of static variables?

I also checked the isocpp.org website for the best way to ensure the construction and destruction order of static variables, but the section is still marked as TODO: WRITE THIS UP.

Upvotes: 5

Views: 2440

Answers (2)

g24l
g24l

Reputation: 3125

In your case you are using construct on first use, and none of the constructors of your classes dependent on the other. Thus the order of initialization is guaranteed A then B.

The destruction order in this case it is guaranteed to be as such B->A, as long as you have simple destructors. Here is a more elaborate answer.

Upvotes: 4

Sergei Kulik
Sergei Kulik

Reputation: 343

Sadly, but what you've done is currently a "state of the art".

Another useful techniques to google for:

#pragma init_seg(XXX) - works in MSVS and Intel C++ under Windows

__attribute__ ((init_priority(XXX)) - works in GCC and clang

Also, I have to warn you that the local static trick of yours is not thread save (at least in MSVC, Intel C++, clang and gcc) as it is implemented by checking and setting a global variable.

Upvotes: 0

Related Questions