]> www.ginac.de Git - cln.git/commitdiff
Replace CL_REQUIRE/CL_PROVIDE(cl_FF_globals) with portable code.
authorAlexei Sheplyakov <varg@theor.jinr.ru>
Thu, 21 Aug 2008 11:46:16 +0000 (15:46 +0400)
committerAlexei Sheplyakov <varg@theor.jinr.ru>
Wed, 27 Aug 2008 04:41:04 +0000 (08:41 +0400)
The order of initialization of non-local objects in different compilation units
is not specified in C++. Hence special care should be taken to avoid static
initialization order fiasco. CLN solved the problem with some evil (GCC
specific, and even GCC-version-specific) hack. Replace it with a technique
similar to one used in STL to initialize std::cout and friends.

include/cln/ffloat_class.h
src/float/ffloat/elem/cl_FF_globals.cc

index f53b7fd512e165983943573fd02b28df0a35b1f6..b1c54e2f011c564bb27e430c4576b759c961da06 100644 (file)
@@ -62,7 +62,14 @@ inline cl_FF::operator struct cl_heap_ffloat * () const
 extern const cl_FF cl_FF_0;
 inline cl_FF::cl_FF ()
        : cl_F ((cl_private_thing) (struct cl_heap_ffloat *) cl_FF_0) {}
-CL_REQUIRE(cl_FF_globals)
+class cl_FF_globals_init_helper
+{
+       static int count;
+public:
+       cl_FF_globals_init_helper();
+       ~cl_FF_globals_init_helper();
+};
+static cl_FF_globals_init_helper cl_FF_globals_init_helper_instance;
 #if 0 // see cl_FF.h
 inline cl_FF::cl_FF (struct cl_heap_ffloat * ptr)
        : cl_F ((cl_private_thing) ptr) {}
index 68c7eebcb8e04f47bf2edc1eaf0d434d6008f5d9..7c98cf6b340179477b1191c4470db3994e914ced 100644 (file)
@@ -3,9 +3,8 @@
 // General includes.
 #include "cl_sysdep.h"
 
-CL_PROVIDE(cl_FF_globals)
-
 // Specification.
+#include "cln/ffloat_class.h"
 #include "cl_FF.h"
 
 
@@ -15,14 +14,30 @@ namespace cln {
 
 #if !defined(CL_WIDE_POINTERS)
 
-const cl_FF cl_FF_0 = allocate_ffloat(0); // 0.0f0
+const cl_FF cl_FF_0 = cl_FF_0; // 0.0f0
+
+const cl_FF cl_FF_1 = cl_FF_1; // 1.0f0
+
+const cl_FF cl_FF_minus1 = cl_FF_minus1; // -1.0f0
 
-const cl_FF cl_FF_1 = encode_FF(0,1,bit(FF_mant_len)); // 1.0f0
+int cl_FF_globals_init_helper::count = 0;
 
-const cl_FF cl_FF_minus1 = encode_FF(-1,1,bit(FF_mant_len)); // -1.0f0
+cl_FF_globals_init_helper::cl_FF_globals_init_helper()
+{
+       if (count++ == 0) {
+               new ((void *)&cl_FF_0) cl_FF(allocate_ffloat(0)); // 0.0f0
+               new ((void *)&cl_FF_1) cl_FF(encode_FF(0,1,bit(FF_mant_len))); // 1.0f0
+               new ((void *)&cl_FF_minus1) cl_FF(encode_FF(-1,1,bit(FF_mant_len))); // -1.0f0
+       }
+}
 
+cl_FF_globals_init_helper::~cl_FF_globals_init_helper()
+{
+       if (--count == 0) {
+               // Nothing to clean up
+       }
+}
 #endif
 
 }  // namespace cln
 
-CL_PROVIDE_END(cl_FF_globals)