digitalmars.D - More thoughts on compile-time contracts
- Daniel Horn (59/59) Apr 29 2004 Let me preface this message by saying that the code analysis work done
- Walter (2/2) May 11 2004 I think you are on the right track. Much of what you are thinking about ...
Let me preface this message by saying that the code analysis work done by the compiler and less by the runtime, the shorter the development cycle. I think languages need radical new features to support better compile-time analysis of programs. Walter and D designers have had great ideas wrt contracts, but contracts are too late for preventing the problem at compile time. THe same holds for uninitialized values--setting them to NaN is great at run time, but what about compile time. C++ has this const notion--which is a step in the right direction, but it mucks up the typing interface and makes the programmer do unnecessary work. "If C++ can tell me that it's const why do I need to write it!"-- good point. instead we need a more powerful method of expressing const and other compile time invariants that have our compiler doing the work to check our sloppy code. for instance...const does NOT solve div/0 problems that could arise. const does NOT solve sqrt(-1) problems that could arise. but the compiler can often tell that I'm never going to have a divide by zero. Let us start with making a better contract that supercedes const, since the behavior is a lot easier and more straightforward than asserting math-ops to be true (oh but what if he does an if(0) around it... blah). So I'm back to my const_assert idea: my_class x = new my_class; const_assert(x.mymember) { x.memberfunc();//only asserts if that changes the mymember var x.mymember=0;//fails, even if mymember was an int that the compiler "knows" is zero (unassigned for instance) } so what if you take this to globals: my_class x = new my_class; const_assert(x) { my_class *[10]y; ... y[5]=x; // so far so good nothing refers to y. my_global = y;// global var gets y... the compiler could either punt here and say "uh oh, global got a pointer to my value, compile fail!" or it could put an internal const flag on that array and recheck the entire code to assure that nothing assigned to the value stored in that array. (if it was linked to externally, however it would have to punt because another lib could access the pointer) } the long and short of it is that this sort of compile time analysis could be done by propogating const to the far corners of the library being compiled (those closed source libs not being compiled would have to be trusted to have the right const_asserts around their definitions, or else print warnings to the output) does anyone think this is a useful idea? it must not stay at the const level, but I think similar ideas could be used to help me check that I'm never using a NaN for instance, or that my variables are always assigned to. Or that a particular value is never assigned to between the beginning and end of a function call. (same as a contract, but static-compile time) the language standard would have to set exactly how these assertions worked--i.e. that they traversed ALL code paths, even improbable ones (i.e. if (0) ) so that each compiler would assert at the same time. --Daniel
Apr 29 2004
I think you are on the right track. Much of what you are thinking about can be done with global data flow analysis across the entire program.
May 11 2004