Example to provoke thought:
procedure fish;
var q,p:ptr_to_sometype;
begin
new(p); qp; `first
q;`
for I1 to 10 do
begin
new(p); q.linkp; p.info
____________
end;
end;
Each record is obtained from the Heap not the Stack.
Hence pointer "first" points at valid information.
If first was not set to q then the linked list would
be lost forever but intact.
--------------
| Code for | Subroutine fish
| FORTRAN | Integer I,J
| Subroutine | Do 10 I=1,20
| Fish | 10 J=J+1
-------------- Return
| | End
| I | return address
--------------
| J | & local variables
-------------- stored in static locations
|Return address|
--------------
If MAIN calls FORTRAN-66 subroutine (A) which calls (B) which
(by accident perhaps) calls (A) again then
(1) Location holding return addr to main is
overwritten by 2nd calling of A: no recursion.
(2) All local variables are (perhaps) altered from previous
values. Therefore saving of environment is in static memory.
: recursion does not work properly.
(Some microprocessors which ran Pascal did not have good stack manipulation instructions (8080,Z80) and hence could not easily use the full power of the stack. Many had to resort to the FORTRAN-66 method of storing variables and parameters. In that case it was necessary to tell the Pascal compiler that the procedure was recursive (either directly or indirectly) and in some cases how recursive it was!! This was so it could reserve enough space to hold the appropriate number of environments.)
Example to provoke more thought:
a: record
procedure fish2 info:integer;
var info2:array...;
p:ptr_to_sometype; a:sometype; end
begin
/* some code in here to set "first"
(==a global of type:ptr_to_sometype) pointing at/to
a (== a local variable on stack of some type) */
end;
In languages like Pascal, Algol 60, etc the type of result which can be
returned from a procedure or assigned to a location is
restricted so that there can be no pointers to a procedures
activation data frame when the procedure environment no longer
exists.
procedure fish_in_C; We have a pointer to something that no
var a:sometype; longer exists! This is called a
begin dangling pointer and compile time/run
global_pointer=&a time checks must be made to determine
end; /* Quite legit in C */ legality of assignment.
No procedure activation can be permitted access to a pointer
which leads to an object with a shorter lifetime than itself.
--> No pointer must lead from an older data frame to a younger.
Compile time: higher textual levels --> shorter lifetime.
Runtime: higher the data frame address on stack, the younger the data
frame and therefore shorter the lifetime.
/* Assuming stack starts at low address and grows toward high address */