Path: utzoo!utgpu!news-server.csri.toronto.edu!cs.utexas.edu!sun-barr!decwrl!world!ksr!tim From: tim@ksr.com (Tim Peters) Newsgroups: comp.lang.fortran Subject: Re: FORTRAN and (un)SAVEd vars Summary: SAVEd .eq. "live on entry" Keywords: FORTRAN, SAVE Message-ID: <2419@ksr.com> Date: 2 Mar 91 05:29:18 GMT References: <112@smith.water.ca.gov> <1991Mar1.191239.28479@alchemy.chem.utoronto.ca> Sender: news@ksr.com Organization: Kendall Square Research Corp. Lines: 70 In article <1991Mar1.191239.28479@alchemy.chem.utoronto.ca> system@alchemy.chem.utoronto.ca (System Admin (Mike Peterson)) writes: > [ ... noting that on a particular compiler, avoiding -g leads to msgs > helpful in determing what should be SAVEd ...] > It seems to me that finding all such variables is an impossible task > for a routine of any complexity (e.g. containing conditional statements), > though I can see that a list of variables can be produced that do not > need to be saved under any circumstances (because they are always > defined before use in all possible paths throught the routine). Conservative approximations to the set of "live on entry" variables (variables that *may* be referenced before being defined) are routinely computed by optimizing compilers these days, and these are exactly the ones that need to be SAVEd under a compiler that can't figure this out itself. If there's no possibility that a variable can be referenced before being defined after entry, SAVE has no semantic meaning. E.g., in subroutine blah1(x) save a a = 1 print *, a end the "SAVE A" means nothing since the promise that A will retain its value between invocations of blah1 is a promise the breaking of which has no visible effect (sure, you can look at a load map, but the load map isn't visible to a standard-conforming test ). Identifying exactly which variables are *certain* to be used before being defined is in general intractable; e.g., look at subroutine blah2(x) save a if ( x.lt.0 ) a = -1 if ( x.eq.5 ) a = 0. print *, a end Flow analysis easily discovers that A *may* be used (in the PRINT) before being defined, but can't prove that it *will* be so used (good thing, too, 'cause if the user always calls blah2 with arguments less than 0, A will in fact never be referenced before being defined). Thus the SAVE may or may not mean something here, and a conservative compiler must assume that it may. A number of optimizing compilers for stack-based machines, particularly those geared toward parallel environments, now ignore SAVE statements entirely, and rely instead on this "(possibly) live on entry" criterion to decide whether it must assign a variable to some flavor of "static" storage. The original poster wanted to know if a tool was available to identify variables that "should be SAVEd". I don't know of one, but if possible they might try running their program through, e.g., Cray's CFT77 and note which variables were assigned to static (as opposed to stack) storage -- those are the variables flow analysis couldn't prove were always defined before reference, .eq. the variables (possibly) live on entry, .eq. the variables that should be SAVEd. In my experience under weaker compilers, finding the scalar variables that need to be SAVEd generally goes pretty fast 'n easy, 'cause so much breaks so bad before they're all caught . But there are usually a few subtle problems that remain with local *arrays* that should have been SAVEd -- without a flow analysis tool, patience and luck are what it takes to fix those. what-a-tangled-web-we've-weaved-ly y'rs - tim Tim Peters Kendall Square Research Corp tim@ksr.com, ksr!tim@harvard.harvard.edu