Hi! On Thu, 6 Jan 2005, Chris Dams wrote:
Chris, I'm afraid you introduced a new static initialization order problem when you sent us your integral.cpp file. You cannot initialize static ex integral::relative_integration_error like you do in integral.cpp:206.
Hmmm... Wait a minute... If I understand correctly, this means that initialization of integral::relative_integration_error occurs before the initialization of the library_init of the same file integral.o as well as before the initialization of all other library_init objects in all GiNaCs other object files. Isn't this a bit strange???
Now that you mention it...
I mean, can't the runtime environment (or whatever it is called) just initialize static objects in the same order as they are defined in the preprocessed C++-code???
Sure. The language guarantees exactly that.
If the order of static initialization were the same as the order of definition were the same, there would not be a problem, right?
Right. But wait a minute! The problem comes from ex::is_zero() const in ex.h:208: There we have the inline member function bool is_zero() const { extern const ex _ex0; return is_equal(_ex0); } But have a look at utils.cpp. Initialization jumps from all the modules that include ex.h into the ctor of library_init and there all the numeric objects are initialized. But _ex0 is declared above that ctor and it is not initialized until the module utils.o is initialized itself! Just the jumps into that ctor do not as a by-product initialize all the static objects. If that analysis is correct there appears to be a loophole in the initialization order scheme. I wonder how that can be fixed without creating a big mess in utils.cpp...
Would you please be so kind and sent a patch to this list for my review?
I would suggest the change in the attached patch, since the functions that are used in this patch do not seem to involve any static variables. Unfortunately I do not know how to test this, because at my place no crash occured in the first place. Do you think this is sufficient to avoid a crash in all cases?
Your patch seems to work, thanks a lot! The patch below seems to fix the problem just as well. By virtue of ex::construct_from_double(double) it should be equivalent to your patch. If you have no objections, I'll commit it. diff -a -u -r1.2 integral.cpp --- integral.cpp 14 Oct 2004 15:36:45 -0000 1.2 +++ integral.cpp 6 Jan 2005 21:31:23 -0000 @@ -203,7 +203,7 @@ } int integral::max_integration_level = 15; -ex integral::relative_integration_error = power(10,-8).evalf(); +ex integral::relative_integration_error = 1e-8; ex subsvalue(const ex & var, const ex & value, const ex & fun) { Best wishes -richy. -- Richard B. Kreckel <http://www.ginac.de/~kreckel/>