From: Gordon Sande on 5 Jul 2010 09:03 On 2010-07-05 00:03:46 -0300, "Lynn McGuire" <lmc(a)winsim.com> said: >> Something I recommended a while back is to find a compiler that >> allows default initializations to arbitrary bit patterns. Then you >> can set all variables that are otherwise not initialized the right >> way (i.e. with save statements, data statements, and normal >> assignments) to various values (large positive or negative values >> for integers, signaling/quiet NaNs or positive or negative HUGE() >> for floating point) and watch where the program errs. You can work >> through your program one routine at a time or in blocks of routines >> as appropriate. Hopefully, the bad code is limited and localized. > > I think that I want to stay with our current compiler until we get everything > to working without /save. That way we have a baseline and can run two > debug sessions, one with /save and one without. You may also run into the situation where the progrmmer assumed (incorrectly) that the zero initialization would happen on each entry but instead the values are those left over from the previous entry. So you have been living with a (hopefully minor) bug for all this time. Fixing things to assign to zero will change things. Your problem will be to figure out which is right. Simply keeping things the same as they were may involve preserving some number of bugs! The thing to worry about is the bug that has been producing plausible answers that have become the accepted answers. >> Perhaps you can identify it as mostly being written by a single bad >> programmer, and track it down that way. When your code is finally > > Over 100 programmers wrote our software. Maybe 200 over the 40+ > years. > > Thanks, > Lynn
From: mecej4 on 5 Jul 2010 10:17 Lynn McGuire wrote: > As many have advised on this board, we are looking to remove the /save > compiler option from our compiles. The /save option initializes all local > variable to zero and saves their values between subroutine calls. Does > anyone have experience doing this and have any advice ? We have about > 600,000 lines of code and 100,000 local variables to initialize. > > I was wondering what would be the best procedure for doing this: > 1. initialize all local variables to zero in a data statement > 2. initialize all local variables to zero in a statement at the beginning > of the > subroutine (my favorite) > 3. something else ? > > Thanks, > Lynn Lynn: given the size of the task facing you, it is more important that you start out with a full understanding of the implications of choosing each of the alternatives that you have listed, instead of adopting one of them on the basis of recommendations alone. Here is an example that illustrates my point: -------------------------------- program undefvar integer :: ivar call sub ivar=-100 ! diversion call sub write(*,'(/,I4)')ivar ! diversion end program undefvar subroutine sub() integer :: iv ! should have been initialized to -10 and 'save'd if(iv < 0)iv=-iv iv=iv+10 write(*,*)iv return end subroutine sub -------------------------------- Let us assume that the original programmer's intention was to initialize iv to -10 in the subroutine, and have iv retain its value from one subroutine call to the next. The bugs consist of not doing the initialization and not specifying the 'save' attribute. The programmer's expected results from the program: 20 30 -100 If you use your alternatives 1 or 2, you will be deceiving yourself. Try your alternatives on this silly test program. The program may run, but not as intended. The results may be wrong, but it may evade you to recognize that they are faulty. Likewise, if you use a compiler's option to do zero-initialization using a compiler switch, or add the 'save' attribute to the variable iv, the modified program will still not function correctly, since the intended initialization to -10 has not been implemented. Beyond the common "initialize to zero" feature, no compiler can read the programmer's intentions. Along the same lines, what are proper initial values for LOGICAL and CHARACTER variables, for which "initialize to zero" makes no sense? Now, for your big application, consider that, instead of the integer iv, the ideal-gas constant R is the one that is not initialized wherever it is needed, and imagine the consequences. What recourse is there left? I recommend that you use a compiler that will most effectively help you hunt down instances of uninitialized variables. Lahey/Fujitsu, NAG and, on Windows, Salford/Silverfrost compilers have good capabilities of this sort. NAG is especially good in pinpointing bugs with respect to INTENT(OUT) variables. Compilers that set out to produce fast executables are not necessarily suited for the task before you. HTH. -- mecej4
From: Lynn McGuire on 5 Jul 2010 18:56 > Now there are cases where choice 2 is superior. But they are all cases > where the code does not need SAVE. In particular, if you have code that > assumes zero initialialization, does not need SAVE, and might get > converted to being invoked multiple times in a single program, then > choice 2 does the needed zero initialization for each invocation. > Parallelization is a prime area where this could be relevant. I think that our code needs zeroing upon EACH entry of our subroutines. I have been trying this out and have gotten several benchmark files to run to completion now by adding the zeroing of a few key variables (the indexes for the arrays variables have been killers). I doubt that we have very many actual variables to be SAVEd that have not already been marked as such. Thanks, Lynn
From: Lynn McGuire on 5 Jul 2010 18:58 > You may also run into the situation where the progrmmer assumed (incorrectly) > that the zero initialization would happen on each entry but instead the > values are those left over from the previous entry. So you have been living > with a (hopefully minor) bug for all this time. Fixing things to assign to > zero will change things. Your problem will be to figure out which is right. > Simply keeping things the same as they were may involve preserving some number > of bugs! > > The thing to worry about is the bug that has been producing plausible > answers that have become the accepted answers. That is where our engineering expertise comes in and we can tell the change is for the better or for the worse. Thanks, Lynn
From: dpb on 5 Jul 2010 19:16
Lynn McGuire wrote: .... > I think that our code needs zeroing upon EACH entry of our subroutines. > I have been trying this out and have gotten several benchmark files to run > to completion now by adding the zeroing of a few key variables (the indexes > for the arrays variables have been killers). .... If that's the case, it's been wrong w/ the /SAVE option because it does _NOT_ do that at all. >> type wat.for program wat x = 1.0 call foo(x) call foo(x) end Subroutine foo(x) x = x+1. print *, y y = y+1.0 End C:\Temp> wfl386 /save wat.for Watcom F77/32 Compile and Link Utility Version 11.0 Copyright by Sybase, Inc., and its subsidiaries, 1990, 1997. All rights reserved. Watcom is a trademark of Sybase, Inc. wfc386 wat.for /save Watcom FORTRAN 77/32 Optimizing Compiler Version 11.0 2010/07/05 18:15:38 Copyright by Sybase, Inc., and its subsidiaries, 1984, 1997. All rights reserved. Watcom is a trademark of Sybase, Inc. wat.for: 11 statements, 72 bytes, 1 extensions, 0 warnings, 0 errors WATCOM Linker Version 11.0 Copyright by Sybase, Inc., and its subsidiaries, 1985, 1997. All rights reserved. Watcom is a trademark of Sybase, Inc. loading object files searching libraries creating a Windows NT character-mode executable C:\Temp> wat 0.0000000 1.0000000 C:\Temp> -- |