Intel® Fortran Compiler
Build applications that can scale for the future with optimized code designed for Intel® Xeon® and compatible processors.

De-Scoping at Entry Statement?

Dogbite
Beginner
388 Views
I am migrating my code from CVF to IVF, and am going through the usual routine of discovering what no longer works.

Several of the program's subroutines have secondary entry points (located below a RETURN stmt) used to initialize local variables with values read from a parameter file, as in the fragment below:


SUBROUTINE APLVM(IVT,FFS,FFSUP)

INTEGER IVT
REAL ARVMAX(7)

[ do fascinating stuff ]

RETURN

ENTRY APLVMI()
READ(32,'(///,3(F5.1,1X))') (ARVMAX(IVT),IVT=1,3)
RETURN
END


When executing, I get error 157 - access violation, pointing at the READ line. Aopparently (uder IVF) the code at APLVMI no longer has access to the variables defined earlier in the subroutine. The Language Reference is basiclly mute on the subject, and the .asm file lacks a symbol table to shed further light.

Is the IVF compiler designed to prevent code from referencing variables defined above an entry statement?
0 Kudos
8 Replies
Steven_L_Intel1
Employee
388 Views
Wow - have not seen that one in a while. If you managed to get this to "work" in CVF you are very lucky. (Or maybe not.)

This code is VERY illegal and ought not to work at all. The rule in Fortran is that when you come in through an entry point, you must not access any variables not in the dummy argument list you entered through. There is NO concept of "remembering"variables from calls to other entry points. DEC Fortran (and CVF which came from it) did not store entry variables in static storage, which some F77 compilers did.

You'll have to fix the code.
0 Kudos
Dogbite
Beginner
388 Views
Steve, thanks for your prompt reply, and glad to be able to contribute to your daily Wow quotient.

The code was originally written in the late 80's by a succession of Russian emigres, which may (or not) have some relevance. Since I got the code in the early 90's it's moved smoothly through Lahey Fortran to CVF without objection to this structure, or any suspicion of bad calculations.

The CVF code did operate with the "Variables default to Automatic" box unchecked, which seems to mean that variables are assigned memory and not allocated on the stack -- I don't know what the corresponding IVF setting is.

Steve, if the code following an Entry stmt is restricted to variables in the call line (as you have said), is it possible to have that rule explicitly noted in the compiler documentation (it isn't now)? And perhaps also have the compiler generate a message, rather than have the error show up at runtime?

Thanks again.
0 Kudos
Steven_L_Intel1
Employee
388 Views
The compiler really can't tell, at compile time, what path you'll take through the code. Whether you'll get an error at run-time really depends on how addresses work out.

Regarding documentation, I don't see how it could be any clearer than this:

"Dummy arguments can be referred to only in executable statements that follow the first SUBROUTINE, FUNCTION, or ENTRY statement in which the dummy argument is specified. If a dummy argument is not currently associated with an actual argument, the dummy argument is undefined and cannot be referenced. Arguments do not retain their association from one reference of a subprogram to another."


0 Kudos
Dogbite
Beginner
388 Views

Steve,

Ah, I see that you are looking my code fragment and identifying IVT as the culprit, where I am looking at the code and thinking the problem is with access to ARVMAX. (This is why I find the documentation you cited to be lacking: it doesn't address the usage of ARVMAX at all.)

Of course, at APLVMI the code is not dependent on any previous value of IVT, as it's using IVT as a loop variable. It appears that the previous compilers either weren't as rigorous in applying the "currently associated" criteria, or were able to recognize the usage of IVT as value-defining. Anyway, defining an additional integer variable for use in the loop variable should solve this.

When I drag myself into the office, I'll need to check whether the compiler setting for allocating local variables to memory is set -- I don't think I've found that one yet on IVF. Obviously, this code depends on ARVMAX maintaining its value across invocations, and a number of other routines also store run-specific parameter values.

So let me ask, what are the trade-offs between stack and memory allocation? And are there special considerations when the code is running in an OMP environment (as I'll be modifying this program to do)?

Thanks again for shedding light.
0 Kudos
Steven_L_Intel1
Employee
388 Views
Right - ARVMAX is fine. The problem is the reference to IVT.

As for stack, etc. - if you go OpenMP you'll need to use stack allocation for local variables (this will happen automatically when you enable OpenMP.) Stack allocation is fast but has size limits. Dynamic allocation has some overhead at allocation and deallocation, but if the work done is a lot then it is not noticeable.
0 Kudos
Jugoslav_Dujic
Valued Contributor II
388 Views
Right - ARVMAX is fine. The problem is the reference to IVT.


Hm, hm. Hold on. The line in question reads:

ENTRY APLVMI()
READ(32,'(///,3(F5.1,1X))') (ARVMAX(IVT),IVT=1,3)

This might be as well a hole in Fortran standard, because:

1) According to the standard, IVT within the implied DO-loop, as above, has its own very local scope. In other words,
INTEGER IVT
...
IVT=42
READ(32,'(///,3(F5.1,1X))') (ARVMAX(IVT),IVT=1,3)
PRINT(*,*) IVT

should yield "42", because IVT within the READ statement has limited scope/lifetime. It's more a syntactic element than a real variable.

2) According to the same standard, and IVF manual, "Dummy arguments can be referred to only in executable statements that follow the first SUBROUTINE, FUNCTION, or ENTRY statement in which the dummy argument is specified"

So, according to my interpretation of those, IVT simultaneously may and may not be referred as the implied DO-loop index.

I'd rather cross-post this to comp.lang.fortran for wider input...
0 Kudos
Steven_L_Intel1
Employee
388 Views
Jugoslav, you're thinking of implied-do in DATA, constructors and the like. "io-implied-do" is different and the do-variable is an ordinary variable without a special scope. In particular, there are rules that prevent you from modifying the do-variable during the I/O which would not apply if it were "special".
0 Kudos
Jugoslav_Dujic
Valued Contributor II
388 Views
Jugoslav, you're thinking of implied-do in DATA, constructors and the like. "io-implied-do" is different and the do-variable is an ordinary variable without a special scope. In particular, there are rules that prevent you from modifying the do-variable during the I/O which would not apply if it were "special".

Ah OK, thanks, I mixed it up. The standard does discern "data-implied-do" and "ac-implied-do" (ac=array constructor) into (mostly) one category, and "io-implied do" into another.

F2k final draft, 9.5.2 Data transfer input/output list,

"20 For an io-implied-do, the loop initialization and execution is the same as for a DO construct (8.1.6.4)." (emphasis mine).
0 Kudos
Reply