Trailing-Edge
-
PDP-10 Archives
-
decuslib20-03
-
decus/20-0078/maint/tdiii.mem
There is 1 other file named tdiii.mem in the archive. Click here to see a list.
CHAPTER 1
SIMULA FOR DEC SYSTEM 10 TD, RTS
SIMULA 67 FOR DEC SYSTEM 10
THE RUN TIME SYSTEM
74-11-13 Lars Enderin
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-1
741111 Lars Enderin
III THE RUN TIME SYSTEM (RTS)
-------------------------
III.1 RTS DESCRIPTION
III.1.1 Introduction
------------
The Run Time System (RTS) is a collection of subroutines designed to
support an executing SIMULA program. The RTS consists of low segment
parts loaded on demand with the compiled program and high segment parts
loaded at run time. The debugging subsystem SIMDDT may be loaded at
program start, via REENTER after a ^C interrupt, or after program exit
for a new execution. SIMDDT is always loaded on run time errors.
III.1.2 RTS design goals and principles
-------------------------------
The RTS is designed to take advantage of the hardware characteristics of
the KI-10 CPU. The data structures have been designed with a view to
efficient operation in a paged virtual memory environment. The number
of storage allocations has been reduced by allocating most subblocks
within already existing blocks. Data referencing locality has been
improved by allocation of display vectors adjacent to their block
instances. Calling sequences and data representation have been designed
to be efficient. The most commonly occurring sequences have been
optimized.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-2
741111 Lars Enderin
III.1.4 RTS coding and naming conventions
---------------------------------
III.1.4.1 Naming conventions in the RTS
As in the compiler, a fairly rigid naming scheme has been observed to
aid in deducing the meaning of a name in the system and to simplify
consistency checks by visual inspection. Normally, the first letter
signifies the type of quantity as follows:
Q starts a compile-time constant.
S or SW signify a switch (Boolean variable) which is a 1-bit or 36-bit
field in an accumulator or storage cell.
X stands for an accumulator.
Y is a global cell or a local cell in a subroutine. Also used for
offsets in the static low segment area, based on the value in .JBOPS.
YY in some subroutine specifications is used to signify a formal
parameter.
XX is used in some routines when designating a formal parameter in an
ac.
Z starts a record field designator, defined via the DF macro (see I.6).
Record names (used in DR macros and prefixed by Q to form a record type
code) are three letters starting with Z. Record field designators
consist of a record name suffixed by 2 or 3 letters and/or digits. The
first 5 characters of a field designator should be unique since symbols
are derived from it by prefixing special characters (% and $).
Component names are two letters, e g CP (class and prefixed block
handling). Subroutine names are formed from component names followed by
two and sometimes more characters (two preferred). The symbols L1, L2,
... , L10 are preferrably used as local labels (available within BEGIN
- ENDD or PROC - EPROC), otherwise the component name is used as prefix.
Global symbols (INTERN or ENTRY) always have a dot "." as prefix to
avoid name clashes with SIMULA procedures. OPDEF's have been used in
some modules as a convenient means of coding procedure calls.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-3
741111 Lars Enderin
III.1.4.2 Register conventions
The accumulators (registers) have been given the basic mnemonics X0, X1,
..., X7, X10, ..., X17 (octal numbering). These names are used in local
contexts only.
X0
With very few exceptions, X0 is used only internally in the RTS, e g to
hold the first word (with the flags) of a dynamic record. One exception
is the mathematical subroutines, which return results in X0 and possibly
X1 (=XSAC).
X1
X1 is called XSAC and is used for various purposes, e g to pass
prototype address or the like to a RTS routine. It is used as a
parameter register chiefly when no extra code has to be executed in the
compiler, which normally compiles code using XWAC1 etc. In other words,
XSAC is used when the parameter to be passed could not be compiled to
some work ac more easily.
X2
X2 is called XTAC and is used for example to pass the number of the top
ac to standard functions.
X0 through X2 can normally be used in the RTS without being saved and
restored (except for internal subroutine interface).
X3
X3 is called XWAC1 and also XRAC. This is the first ac allocated by the
compiler and also the result ac from thunks, procedures and RTS
functions, together with XWAC2 (=XRAC1) in some cases. New object
addresses are also computed to this accumulator.
X4-X14
X4-X14 (octal) are the rest of the work accumulators, also called XWAC2,
XWAC3, ..., XWAC7, XWAC10, XWAC11, XWAC12. The upper limit is defined
by the compile-time constant QNAC which is the number of work ac's.
X15
X15 is called XCB and should always point to the nearest (current) block
with a display vector attached. XCB is the root of the run-time data
structure. From this all referenceable quantities can be found, except
for some quantities pointed to by global low segment static locations at
offsets YCSZAC, YOBJAD, YTXZTV, YSYSIN, YSYSOU, etc.
X16
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-4
741111 Lars Enderin
X16 is called XIAC,XFP, or XLOW. XIAC is used to point to some block
other than XCB when a variable is accessed. The contents of XIAC are
regarded by the compiler as lost whenever a change of control can occur
as when calling a procedure, at an explicit or implicit label, when
intermediate results may have to be saved, and when calling mathematical
subroutines. Inside the RTS, the ac can be used as XLOW to point to the
static area in the low segment. The UNIVERSAL file SIMRPA contains a
macro LOWADR which loads a specified register with this address, and
assigns the name XLOW to the register. If no parameter is given, the
default XLOW=XIAC is used. The macro SETLOW(x) assigns the name XLOW to
x (default XIAC if no parameter is given), but does not load the
register. Should be used when it is known which register contains the
address. The name XFP is used on X16 in connection with FORTRAN
subroutines, as shown in the previous section. The standard calling
sequence in FORTRAN-10 is:
MOVEI XFP,arg
PUSHJ XPDP,routine
where the argument list has the form:
XWD -number of arguments,0
arg: Z type code,address of first argument
Z type code,address of second argument
etc.
The result is returned in X0 and X1 if applicable.
X17
X17 is only referred to as XPDP and used for all PUSHJ-POPJ calls. It
refers to the run-time stack whose bottom is at YOBJRT, so named because
the return address to SIMULA code is placed there when calling a RTS
procedure.
III.1.4.3 Coding conventions
III.1.4.3.1 Preserving registers within the RTS
Inside the RTS, all work registers can be used provided any possibly
relevant registers are preserved. When some storage allocation routine
is called, the calling RTS routine is responsible for preserving the
integrity of object pointers which may exist in registers temporarily.
These registers must be saved in locations which are known to the
garbage collector as possible object references. The array YOBJAD in
the low segment is provided for that purpose. Any unused cells in
YOBJAD must be zero when not in use. Other global cells known to the
garbage collector are used for relocatable address esin the SIMULATION
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-5
741111 Lars Enderin
module (SU) and in SIMDDT. For a temporary text variable, YTXZTV should
be used in the same fashion. Registers which contain non-relocatable
values will be saved and restored by the garbage collector.
III.1.4.3.2 Addressing the low segment
The low segment is addressed through the right half of .JBOPS. As
explained above, the macros LOWADR and SETLOW are used to establish the
base register, which is always called XLOW (renamed by the macros). The
storage allocating routines in particular always use the standard
XLOW=XIAC to prevent confusion when calling them from other RTS
routines. The use of global variables is avoided when the stack can be
used equally well.
III.1.4.3.3 Saving intermediate results
The RTS procedures which are of a function nature, i e can be used
inside an expression, warrant special consideration because of the
requirement to save intermediate results over the execution of the
procedure. If the procedure involves storage allocation, an acs (ZAC)
object must be created for the intermediate results. This is done in
either of two ways.
1) The entry point .CSSA is called from compiled code in the
following way:
PUSHJ XPDP,CSSA ;via transfer vector
XWD N,ADMAP
Only the accumulators below the top ac (as given by YTAC) are saved.
This method cannot be used when the top accumulators are important.
.CSSA creates a ZAC object, saves the intermediate results and sets
YCSZAC(XLOW) to point to the acs object. YCSZAC is then used by a run
time setup routine (.CSSN, .CPNE) to set ZDRZAC of the display vector.
YCSZAC is cleared after use.
2) The "XWD N,ADMAP" word is passed as an inline parameter to some
RTS routines which may allocate storage directly or indirectly (e g
through the actions of a thunk). It is the responsibility of such a
routine to preserve any quantities which will not be saved in the acs
object, in the special locations reserved for object addresses or text
variables, then to call .CSSA. (secondary entry point to .CSSA) with a
copy of the inline parameter in XSAC, provided it is non-zero. A zero
inline parameter signifies that no intermediate results exist.
When returning from an object generator, procedure, thunk evaluation or
some run time function such as .TXCY, YCSZAC is recovered and .CSRA is
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-6
741111 Lars Enderin
entered if YCSZAC is non-zero. The result of the function is in XRAC &
XRAC+1 and is placed in the proper position on the stack by .CSRA before
restoring the intermediate quantities. The result is thus always placed
in the top accumulators.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-7
741111 780302 6 Lars Enderin
III.1.5 RTS storage allocation
----------------------
II.1.5.1 Types of records allocated by the RTS
Several types of dynamic blocks are allocated by the RTS in
response to the expressed needs of a SIMULA program. The
different block types are:
Record Function Allocated by
name
ZBI block instance SAAB (via CSSB)
(unreduced subblock)
ZBP procedure block SADB (via CSSN or CSSW
or CSSW0)
ZCL class object SADB (via CPNE)
ZPB prefixed block SADB (via CPSP)
ZTE text record SAAR (via TXBL, TXCY, IOIT)
ZTT temporary text variable SAAR (via TXDA)
ZAR array record SAAR (via CSNA or CSCA)
ZAC accumulator stack rec. CSSA
ZER eventnotice record SAAR (via SANE)
ZDR display record SADB (via CSSN, CSSW, CSSW0,
CPNE, CPSP)
ZYS "system" record SAAR
ZXB extended lookup block SAAR (via IOCF)
The block layouts are documented in TD I.5 and LH2 appendix B.
III.1.5.2 Some notes on the various block types
The ZDNTYP field in the first word of all these blocks shows
the block type. The numeric values of block type codes are
determined by an expansion of the TYPZDN macro in SIMMCR.MAC
(III.5). The symbolic names are formed from the record names
by prefixing the letter Q, e.g. QZCL is the assembly constant
for the type code of a class object record.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-8
741111 780302 6 Lars Enderin
III.1.5.2.1 Subblocks (ZBI)
ZBI (unreduced subblock instance) is the simplest type of
independent program block. The block types ZBP, ZCL and ZPB
all contain a ZBI part. A ZBI block may contain several
reduced subblocks corresponding to Algol blocks at inner block
levels.
The ZBIBNM field in the block instance indicates the innermost
currently active reduced subblock. The value in ZBIBNM is used
by the garbage collector to find the correct block map(s) (see
I.5) and by SIMDDT to find the correct symbol table segment.
Unreduced subblocks are only allocated in the following cases:
* A subblock immediately enclosed by a class instance. This
saves space for detached class objects by allowing the
subblocks to be garbage collected.
* The outermost block in a connection statement.
In all other cases, subblocks are reduced into the nearest
enclosing instance of a procedure, prefixed block or unreduced
subblock. Reduction of subblocks saves storage allocations,
reduces the size of display vectors (since several subblocks
can be addressed from the same base address) an speeds up
execution. In return, some run time procedures become more
complicated, e.g. CSGO. See III.1.6.
III.1.5.2.2 Procedure blocks (ZBP)
Procedure subblocks (ZBP) are set up by calls to CSSN, CSSW or
CSSW0. They have an attached display vector (ZDR). SADB
allocates both ZDR and ZBP at the same time as one contiguous
storage block.
SADB also fills in those fields which are common to the block
types handled (ZDR + ZBP, ZCL or ZPB), e.g. the reactivation
point (ZDRZBI,ZDRARE).
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-9
741111 780302 6 Lars Enderin
III.1.5.2.3 Class objects (ZCL), prefixed blocks (ZPB)
Class objects (ZCL) and prefixed blocks (ZPB) are allocated in
the same fashion as procedure blocks by calls to CPNE or CPSP,
which call SADB.
III.1.5.2.4 Text records (ZTE)
Text records (ZTE) are allocated by SAAR. They contain the
ASCII representation of the text contents.
III.1.5.2.5 Temporary text variables (ZTT)
ZTT records are created in connection with parameter handling.
A ZTT record contains a text variable (ZTV instance) which is
used as stand in for a text expression in certain cases. See
parameter handling.
III.1.5.2.6 Array records (ZAR)
ZAR records (arrays) are created by array declarations or when
passing array parameters by value. CSNA is used to create the
first array in an array segment. CSCA is used to create the
other arrays in the segment by copying and also when passing an
array parameter by value.
Before the array record is allocated in CSNA, its size must be
computed from the subscript bounds. The subscript bounds are
in ac's (possibly also in pseudo ac's) and are saved in a ZAC
record during evaluation. Temporarily, the array thus requires
its own space plus that needed by the ZAC record (4 + 2n words,
where n is number of subscripts).
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-10
741111 780302 6 Lars Enderin
III.1.5.2.7 Accumulator stacks (ZAC)
ZAC records (accumulator stacks) are created in situations
where intermediate results are in ac's and possibly in pseudo
ac's, and the garbage collector may be called because of
storage allocation.
Since space is always reserved at the top of the storage pool
for a ZAC record of maximal size, CSSA can create the record
and copy the ac values into it without first checking the
storage limits. If sufficient space for another ZAC is not
left then, the garbage collector is called to provide more
space. Relocation information for the saved values is provided
in the accumulator map pointed to by the ZACZAM field of the
ZAC. The ac map is a bit vector where a one in bit position
n-1 signifies that saved result n (XWACn) contains an object
address in its right half, e.g. a REF value, the first word of
a TEXT variable, an array address, a procedure dynamic address,
etc.
If pseudo ac's are used, relocation bits are found starting
with bit 18 of the map word.
The address of the ZAC object is placed by CSSA in YCSZAC(XLOW)
whence it may be copied to another location (e.g. ZDRZAC of a
display vector). YCSZAC(XLOW) will be cleared when it is no
longer needed. ZAC records may be created when the following
RTS routines are called:
CSSA (before a call to CSSN or CPNE), CSSW, PHFA, PHFV, PHFM,
PHFT, TXBL, TXCY, TXDA, IOIT, CSNA.
The other procedures call CSSA at its entry point .CSSA. .
Note that the current "top" ac's are NOT saved in the ZAC
object. Instead, they are saved by the invoked RTS routine in
global locations provided for that purpose, if pointers are
involved, or on the RTS stack for quantities which are
invariant under garbage collection.
III.1.5.2.8 Display records (ZDR)
ZDR (display) records exist for procedures, non-terminated
class objects and for prefixed blocks (including the main
program block). For classes with local classes as attributes,
the display record is kept even when terminated because it may
be needed to establish the environment of a procedure attribute
of a local class.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-11
741111 780302 6 Lars Enderin
III.1.5.2.8.1 Static display
The ZDR record contains the traditional static display known
from Algol implementations. Instead of one central display
vector, we have here one display for each active block of a
type described above. This means that several pieces of
information are duplicated in the system. Because most
subblocks are reduced, however, quite few display levels are
usually needed, and displays for terminated class object are
usually deallocated. Since the display is adjacent to the
block and addressed via the same ac (usually XCB, the current
block pointer), one instruction usually suffices to obtain the
address of any block in the static environment.
III.1.5.2.8.2 Dynamic link
In addition to the display, ZDR also contains the dynamic link
or reactivation point (ZDRZBI, ZDRARE). For a procedure or
attached class instance, the reactivation point is (address of
calling block instance, return address). For a detached class
instance, ZDRZBI normally points to its own block, and ZDRARE
points to the reactivation point within its code (program point
after call on DETACH or RESUME or after a scheduling statement
in SIMULATION). See III.1.6.3.5 Quasi-parallel Sequencing.
III.1.5.2.8.3 FOR loop returns, thunk save areas, ZAC pointer
Return addresses for FOR loops are also contained in the ZDR
record, as well as thunk save areas (see parameter handling),
and the address of a ZAC record if one was created just before
the ZDR record was created. The existence of a ZAC record for
the attached block is flagged by a bit in that block instance
to prevent execution of unnecessary instructions if a ZAC
record does not exist. This is relevant because the ZDRZAC
field is accessed from the front end of the ZDR, and the front
end address has to be calculated from the block address and
prototype information, whereas the other information in the ZDR
record is accessed conveniently via negative offsets from the
block address.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-12
741111 780302 6 Lars Enderin
III.1.5.2.9 Eventnotice record (ZER)
ZER (eventnotice) records are used in SIMULATION programs.
Each SIMULATION block has one or more ZER records allocated,
chained via the ZSUZER field in the SIMULATION block and the
ZERZER field in the ZER record. A ZER record contains a number
of event notices (ZEV).
III.1.5.2.10 Eventnotices (ZEV)
Each ZER record contains several ZEV records (eventnotices), of
which some are members of the sequencing set (SQS). The free
ZEV records form a chain via their ZEVZEV fields and the first
free record is found via the ZERZEV field in the ZER object.
For garbage collection purposes, the ZEVZER field of each ZEV
gives the address of the ZER record of which the ZEV is a part.
The ZEV also contains links to other ZEV instances in the SQS,
a pointer to the associated process (ZEVZPS) and the scheduled
simulated time for the next active phase of that process. The
process has a pointer to its associated ZEV record (ZPSZEV).
III.1.5.2.11 ZYS records
The ZYS record type is used for various blocks "behind the
scenes", i.e. not directly related to any SIMULA concept. A
ZYS block may only contain information invariant under garbage
collection, so that it can be moved freely without relocation
of internal information. ZYS blocks are used e.g. for sub-file
directories (SFD), and SIMDDT is marked as a ZYS record for
garbage collection purposes.
III.1.5.2.12 Extended lookup/enter block (ZXB)
ZXB records are used for extended lookup/enter blocks in the
SIMULA I/O subsystem. A ZXB record may contain a pointer to a
sub-file directory and is thus not invariant under garbage
collection.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-13
741111 780302 6 Lars Enderin
III.1.5.3 Garbage collector (GC)
The garbage collector (GC) can be called for three reasons.
1. The storage pool is exhausted, a new core request cannot be
honored within the allocated core (top location given by
YSALIM).
2. New buffers are to be allocated. The whole pool must be
moved upwards, leaving free space at the bottom.
3. SIMDDT calls the garbage collector when executing the
VARIABLES command in order to remove garbage data before
dumping the pool.
In the first case ac 0 (X0) contains the number of words
required above the limit given by YSALIM(XLOW). In the second
case, YSAREL(XLOW) contains the number of words needed at the
bottom of the pool, and in the third case X0 and YSAREL are
both zero, thus no more core is needed.
The action taken when GC is called (entry .SAGC in SA.MAC)
depends on the allocation strategy chosen when assembling the
RTS. If the assembly constant QSASTE is non-zero, the pool is
allocated in steps (i.e. the pool is expanded by one or more
core requests between garbage collections rather than
collecting garbage each time). If a new core chunk (step) of a
previously calculated size can be allocated without exceeding
the garbage collection limit YSAL(XLOW) calculated in an
earlier execution stage, the step is taken, otherwise a
complete garbage collection is performed. If X0 was zero on
entry, however, a complete garbage collection is always
performed (cases 2 and 3 above).
If QSASTE is zero, the whole pool given by the value in
YSAL(XLOW) is allocated initially and after each garbage
collection, and a call to SAGC will always result in a complete
garbage collection (i.e. the limits YSALIM and YSAL coincide).
This will probably be the best strategy for KA10 installations
where CORE requests are fairly expensive. QSASTE is defined in
SIMMAC.MAC and set to 1 as default. A change of the QSASTE
value only affects the SA.MAC module which must be reassembled
after assembling SIMMAC.MAC.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-14
741111 780302 6 Lars Enderin
Another algorithm has been added to take care of big programs
which may run out of real core memory and start to use virtual
memory. After calculating the optimal YSAL value, check to see
if the job would go virtual. In that case, modify the
estimated limit to a value which avoids excessive paging
overhead. This algorithm is used only when virtual memory is
available and it is currently not well tested, but it has
reduced execution time significantly for a couple of programs.
Garbage collector phases
The garbage collector works in four phases. Figure III.1.5.3
shows the interaction of GC components (subroutines and
coroutines).
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-15
741111 780302 6 Lars Enderin
Figure III.1.5.3 Subroutine and coroutine linkage in the
garbage collector.
+------+ +------+ +------+ +------+
!.SAGC1!--->!PHASE1!--->!SAGCGP!<-->!SAGCNP!
+------+ +------+ +------+ +---:--+
! ^ V
! ! +------+
! +-----!SAGCCH!
+------+ ! +------+
!SAGCDR! V
+------+<-->+------+ +------+
!SAGCSP!<-->!SAGCNP!
+------+<-->+------+ +--:---+
!SAGCFP! ^ ^ V
+------+ ! ! +------+
V +-----!SAGCCH!
+------+ +------+
+ ------------------!SACGN1!
! +------+
V
+------+ +------+ +------+ +------+
!PHASE2!--->!PHASE3!--->!SAGCGP!<-->!SAGCNP!
+------+ +------+ +------+ +---:--+
! ^ V
! ! +------+
! +-----!SAGCUP!
+------+ ! +------+
!SAGCDR! V
+------+<-->+------+ +------+
!SAGCSP!<-->!SAGCNP!
+------+<-->+------+ +--:---+
!SAGCFP! ^ ^ V
+------+ ! ! +------+
V +-----!SAGCUP!
+------+ +------+
+ ------------------!SACGN3!
V +------+
+------+ +------+
!PHASE4!<->!.SANP !
+---:--+ +------+
V
+------+
!RETURN!
+------+
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-16
741111 780302 6 Lars Enderin
III.1.5.3.1 Phase 1
The first action is to find all referenceable records in the
pool. The right half of the first word of all records in the
pool is reserved as GC working space (ZDNLNK field). During
phase 1 this field is used to chain all referenced records.
The chain starts with the outermost block instance, which can
be found provided XCB points to a record with an attached
display record. The outermost block instance is part of
generated code for the main program and is thus not placed in
the dynamic storage pool. Usually, though, the outermost block
contains pointers into the dynamic pool which may have to be
updated during garbage collection. If no display record is
attached to the XCB record, the chain starts with the XCB
record itself. All global pointers in the static area (defined
in SIMRPA, macro STATIC) which may contain pointers into the
pool are checked, and each record found via these pointers is
attached to the chain. Since a dynamic record in the pool may
contain other pointers, each record in the chain must be
searched for pointers. Phase 1 is completed when the last
record of the chain is checked without finding any new pointer.
III.1.5.3.2 Phase 2
At this stage there are two kinds of records in the pool:
* Referenced records with a link address in ZDNLNK.
* Unreferenced records with ZDNLNK = 0.
New record addresses can now be computed for all referenced
records, assuming that the records should be moved towards the
bottom of the pool in the same order by increasing addresses.
If YSAREL(XLOW) is non-zero, its value is added to the old
bottom address. Then the whole pool is scanned, placing the
new address of each referenced record in its ZDNLNK field.
Unreferenced neighbours are lumped together to look like a
single unreferenced record in the following phases.
When all referenced records have been assigned new addresses,
the new value of the first free location (the new YSATOP value)
can be determined. This plus the amount of core requested when
calling GC gives the minimal amount of core required for
continued execution of the SIMULA program. If not enough core
was reclaimed by the GC, a CORE UUO is executed for the
required core size. If that fails, execution terminates with
an error message.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-17
741111 780302 6 Lars Enderin
III.1.5.3.3 Phase 3
All pointers that were checked during phase 1 must again be
checked. This time any pointer into the pool will be updated
to point at the updated location of the record (given by its
ZDNLNK field). The same routines are used as in phase 1, but
the records are not treated in the same order. In phase 3,
referenced records are treated in the order in which they
appear in the pool, starting at the bottom. Instead of calling
SAGCCH for each record, SAGCUP is called to perform the
updating of addresses. See figure III.1.5.3.
Some dynamic records contain internal pointers. These are
relocated as soon as the next record in the pool is found by
the SAGCN3 routine. Eventnotice pointers are also treated
here. They are found in SIMULATION and PROCESS block instances
and in eventnotice records.
At this stage, however, ZEVZER and ZERZER pointers cannot be
updated since they are used to define the relocation offset for
eventnotice pointers not yet found.
III.1.5.3.4 Phase 4
Now the ZERZER chain and all ZEVZER pointers can be updated.
Each referenced record in the pool should now be moved to its
new location given in the ZDNLNK field. A complication occurs
if the bottom of the pool should be moved upwards. For some
records moved towards a higher address, the old and new area
may overlap, prohibiting the use of a BLT instruction. In that
case, the record is moved word by word starting at the high
end, and the records must be moved in reverse order. This is
simplified by first making a reverse chain of records via the
ZDNLNK fields. After all records have been moved to new
locations, the reclaimed core is cleared to zeros.
III.1.5.3.5 Determine and allocate new storage pool area
After phase 4, a new garbage collection limit and a new
allocation step size if applicable, are calculated. The
algorithms used in the calculations are given below.
Finally, a CORE request is made if necessary. The maximal
available amount is used if the request is excessive.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-18
741111 780302 6 Lars Enderin
III.1.5.3.6 Core size algorithm
The core size algorithm is designed to minimize running costs
for the SIMULA program assuming an accounting formula of the
following form:
Cost = G * (L + A) * time
where L is the storage pool size, G is a constant, and A is
explained below.
It is further assumed that the time required for a garbage
collection is proportional to the amount of active memory. The
proportionality factor B is approximated with a divided
difference over the last garbage collection. It is also
assumed that the allocation rate R is approximated by a divided
difference from the end of the last garbage collection to the
start of the current garbage collection. In the KI10
production system core is released after a garbage collection
and reclaimed when needed in constant steps, each step an
integral number of 512-word pages (see next section).
With the current accounting algorithm, A can be approximated by
5450 Q-La
A = --------- + 5 + ---- pages,
(La+Q+10) 2
where Q is the size of high segment and code and data outside
the storage pool, and La is the average size of the storage
pool or (F+L)/2, where F is the size of active memory and L is
the previous storage pool limit. The following figure shows
how A was computed:
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-19
741111 780302 6 Lars Enderin
A = dA/kA.
Cost/second
^
!
! .
! + .
! + .
! +.:
! : + : Slope of tangent =
! Accounting + : kA = G
! algorithm +: : :
! ! : + . : : :
! v + . : : :
! + :--- : : :
+ ! . : ! : : :
+ ! . : ! : : :
.! : ! : : :
. ! : dA : : :
. ! : ! : : :
. ! : ! : : :
. ! : ! : : :
---------------+-------+-------+---+------+-----> Allocation
:.......:.......: : :
Q : F : :
:...........: :
: La :
:..................:
L
The optimal storage pool limit minimises the sum of the cost to
execute between garbage collections and the cost to execute the
garbage collections. Assuming stationary program dynamics
(constant allocation rate R, constant active memory size F,
constant garbage collection time per word B and infinite
execution time) the new optimal storage pool limit is:
A
L = F * (1 + sqrt[2*B*R*(1 + -)]) (1)
F
The expected time between garbage collections is (L-F)/R, the
average store size is (L+F)/2, which yields the cost between
garbage collections:
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-20
741111 780302 6 Lars Enderin
L-F L+F
--- * (--- + A) (2)
R 2
The expected time for garbage collection is F*B, and the cost
is
F*B*(L+A) (3)
The cost rate per effective cpu second is thus
((2)+(3))/((L-F)/R), and minimisation with respect to L gives
(1).
III.1.5.3.7 Step size algorithm
Assume that the accounting algorithm can be written
COST = const * [A+W*(M+U)*M]*time
where M is accounted memory.
Assuming approximately linear memory size dependency for this
execution phase we have
COST = const * [A+(B*M+C)]*time
Assuming average time for a CORE UUO is K, allocation rate is R
and that core is expanded in the interval (C0, C1), we can
derive an approximation for the optimal step size:
A+C
S = sqrt(K*R*[2 * --- + C0 + C1])
B
Define m = W*(M+U)*M
We then have
dm
-- = 2*W*M+W*U
dM
and the linearisation yields
m = W*(2*Ma+U)*M-W*Ma^2
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-21
741111 780302 6 Lars Enderin
where Ma is the average memory size.
Thus B = W*(2*Ma+U)
and C = -W*Ma^2
Define X = 2*Ma = C0+C1
Thus B = W*(X+U)
C = -0.25*W*X^2
and the optimal step:
2*A-0.5*W*X^2
S = sqrt(K*R*[------------- + X])
W*(X+U)
The bracketed expression can be expressed as:
2*A X^2 2*A X^2
--- - --- --- - --- + X^2 + X*U
W 2 W 2
--------- + X = --------------------- =
X+U X+U
X^2 2*A 2*A U^2
--- + X*U + --- --- - ---
2 W W 2 X+U
= --------------- = --------- + --- =
X+U X+U 2
4*A
--- - U^2
1 W
= - [--------- + X+U]
2 X+U
The present values at our installation are
U = 20 [pages]
A = 1.1 [1/sec]
W = 0.0001 [1/(sec*pages^2)]
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-22
741111 780302 6 Lars Enderin
Thus
K*R 44000 - 400
S = sqrt(--- * [----------- + X+20]) [pages]
2 X+20
Expressed in words and milliseconds and assuming K = 4 ms
we will get
1.143*10^10
S = sqrt(2*R*[----------- + X+10240]) [words]
X+10240
where
R = allocation rate in words/ms
4*A
1.143*10^10 = [--- - U^2]*512^2 [words*words]
W
10240 = U * 512 [words]
III.1.5.3.8 Algorithm for virtual memory
The algorithms described above are not suitable when the job
goes virtual, i.e. when the available real core memory is not
sufficient for the job to run. If the user has virtual memory
privileges, the job will then start paging. In this case, the
assumptions on which the above algorithms are based will not be
valid. Essentially, use of virtual memory should be avoided.
An alternative allocation algorithm has been constructed for
the case where virtual memory is used. The assumptions on
which the algorithm is based may not be quite valid, but
significant cost improvements have been obtained for programs
using much virtual core.
- At start of GC, save number of niw faults in YSANWA and
number of niw faults since last GC in YSANWB. GETTAB [%VMSPF]
used. Cumulative count of niw faults updated in left half of
YSANWC. This should be job-related data, but only global
system counts are available in this way, which means that other
jobs executing at the same time may add to the counts, causing
more restrictive use of memory than necessary.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-23
741111 780302 6 Lars Enderin
- Modification of core limit if CORE fails in SANP1: If first
CORE fails, check if job is going virtual, and if it does,
subtract space (1K) for PFH. GETTAB [-1,,.GTCVL] used.
- Determination of new allocation limit for a job that runs in
virtual core:
In SANP, if the page fault handler is in core, determine number
of niw faults between last two GC:s (from YSANWB) and change
YSAL by 2K*SIGN(tgc-tswap*(nb+2*ng). Here
nb niw faults before last GC;
ng niw faults during last GC;
tswap time (ms cpu) accounted for a page swap (currently =
20.);
tgc time spent in this GC.
However, if YSAL becomes less than minimal quantity needed, the
latter is passed to SANP1. The pool is not allowed to exceed
the low segment limit (128K).
- If job is not virtual, but the new estimated optimal YSAL
value will make it virtual, make the new YSAL value so that the
job just goes virtual:
(YSAL=min(physlim+qpolmi,virtlim)-YSAHSZ-sizeofPFH).
GETTAB[-1,,.GTCVL] is used to find out virtlim.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-24
741111 780302 6 Lars Enderin
[This page intentionally left blank]
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-25
741111 780302 6 Lars Enderin
[This page intentionally left blank]
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-26
741111 780302 6 Lars Enderin
[This page intentionally left blank]
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-27
741111 780302 6 Lars Enderin
III.1.6 Execution control
-----------------
The execution of a SIMULA program is controlled on several
levels - by the user through monitor commands, by the RTS, and
by compiled code.
1) Monitor commands - START (CSTART), REENTER, CONTINUE
(CCONTINUE), ^C.
2) Overall program control by the RTS:
High segments are swapped by OCSW.
A program is set up and initialized by OCSP, OCIN, OCEI.
Errors are handled by OCUU and SIMDDT, traps by OCTR and OCUU.
SIMDDT interface is handled by OCUU, .OCRE0, .OCRE, .OCLD,
.OCRD.
OCEP terminates program execution. High segments are swapped
by OCSW.
3) Procedure calls are handled by CSSN, CSSW, CSEN, CSEP, CSES.
Class objects are created and controlled by CPNE, CSEN, CPCD,
CPCI, CPE0. Subblocks are created by CSSB and terminated by
CSEU. Reduced subblocks are initialized by CSER. Prefixed
blocks are handled by CPSP, CSEN, CPPD, CPE0, CPCI. Coroutine
sequencing and quasi-parallel systems are handled by CPDT
(detach), CPCA (call), CPRS (resume). SWITCHes and GOTO
statements are handled by CSSC, CSES, CSGO. Evaluation of a
name parameter with a thunk may cause control to go anywhere.
See III.5 (parameter handling). SIMULATION is handled by
special statements and procedures - see III.1.10.
4) Conditional expressions and statements, WHILE loops, FOR
loops and simple GOTO statements are handled entirely by
compiled code.
III.1.6.1 Monitor commands for SIMULA program control
III.1.6.1.1 START (CSTART)
A START or CSTART command causes a SIMULA program in core to
start execution at the entry point given by the right half of
.JBSA. LINK-10 sets the start address to .MAIN if a LOAD or
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-28
741111 780302 6 Lars Enderin
EXECUTE command was issued. If COMPIL recognizes the program
as a SIMULA program or the /SIMULA switch is given, a DEBUG
command causes LINK-10 to set the start address to .OCRE0,
otherwise DDT will usually be loaded and the start address will
be .MAIN. To understand what happens at the start of a SIMULA
program it is necessary to know the general layout of a SIMULA
main program, as shown below:
The first 4 or more words are copied from the source file
LOOKUP information. The interesting information is
filename.ext, date and time of file creation and last access,
and the access path:
[proj,prog] (zero if no path given) or
[proj,prog,sfd1,...] if SFD files are part of the
directory path. See Monitor Calls manual for lookup
block and SFD information.
[source file lookup info]
[text constants and any runswitches block]
[Display (ZDR) for main program block]
mainb: [Block instance (ZPB) for main program]
[constants]
.MAIN: JRST 1,.+1 ;Normal entry point
TDZA X1,X1 ;No SIMDDT address
JRST 1,.+1 ;Enter here from .OCRE0
MOVEI XCB,mainb
JSP X16,.OCSP
JFCL runswitches address ;may be zero
[compiled SIMULA statements]
PUSHJ XPDP,OCEP
[prototypes, line number tables, symbol tables]
If the program is started at .MAIN, X1 is set to zero to
indicate that SIMDDT is not in core. The program will then be
started without SIMDDT, unless this is a restart after program
exit and SIMDDT was loaded at the start of some previous
execution. In that case, the address of SIMDDT has been placed
in YOCDDT, a global location in OCSP. See REENTER command
(III.1.6.1.2). OCSP loads the initial high segment after
allocating core for the static data area and saving the ac's.
Control is then transferred to OCIN for the bulk of the
initialization - setting up the RTS stack, allocating standard
files SYSIN and SYSOUT and buffers, reading any specification
file, etc. OCIN finishes by transferring control to OCEI in the
OCEP module. If the two high segments version of SIMRTS is
used, invocation of OCEI from OCIN leads to a high segment swap
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-29
741111 780302 6 Lars Enderin
via the transfer vector and .OCSW. When the program starts, a
RESET UUO stops any active I/O and the buffer space is released
by moving .JBFF back to the value in .JBSA(LH). Any active
SIMDDT breakpoints are removed by OCSPDR.
CSTART is identical to START except that the terminal remains in
monitor mode. The program will probably wait for input or
output on the terminal unless continued via ^C-CONTINUE.
III.1.6.1.2 REENTER command
The REENTER command has different effects depending on the
current state of execution in the SIMULA program. The current
address in .JBREN governs the actions.
III.1.6.1.2.1 REENTER before program start
If issued directly after a LOAD or GET command, REENTER causes
SIMDDT to be loaded and entered before executing the statements
of the SIMULA program. REENTER starts the program at the entry
point .OCRE0 in the OCSP module. If COMPIL does not recognize
the program as a SIMULA program, a DEBUG command will cause DDT
to be loaded instead of SIMDDT. A ^C followed by REENTER will
have the same effect as REENTER after LOAD in this case. .OCRE0
reserves space for SIMDDT if not already loaded, modifies
.JBSA(LH) to keep this space over RESET, and transfers control
to the compiled program at .MAIN+2 with X1 containing the
address of the SIMDDT area. The first word of that area is set
to zero if SIMDDT was not loaded previously.
In OCSP, the assigned SIMDDT address is saved in YOCDDT for
later use (restart). When OCEI eventually gets control from
OCIN, SIMDDT is loaded if necessary and entered at the entry
point DSINI. Breakpoints may then be set before starting
execution of compiled statements via a PROCEED command.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-30
741111 780302 6 Lars Enderin
III.1.6.1.2.2 REENTER during RTS initialization
If the program is interrupted while .OCSP, .OCRE0 or OCIN is
active, a REENTER command has the same effect as a CONTINUE
command except for typing a message on the TTY. The entry point
OCRE1 is used in that program phase.
III.1.6.1.2.3 REENTER during execution of SIMULA statements
During normal SIMULA program execution, the reentry address is
.OCRE. If the program is stopped by one or two ^C characters in
this phase, a REENTER command causes .OCRE to be entered.
Depending on the value of the control variable YDSCSW(XLOW),
SIMDDT may be entered
a) directly,
b) after returning to some well-defined point in the program,
c) or the request to enter SIMDDT must be denied because the
data structures are being changed so that they are possibly
inconsistent at the time of interrupt.
In case (c), a new interrupt may be attempted after running the
program for some time. If SIMDDT was not loaded with the
program, it is loaded from the file SIMDDn.ABS (n = SIMULA
version number). Once within SIMDDT, breakpoints may be set,
variables and the operating chain may be displayed, but some
commands can not be performed, chiefly because garbage
collection may be involved.
III.1.6.1.2.3.1 Basic requirements for allowing SIMDDT to be
called
The following basic requirements must be met when SIMDDT is
executed in this mode:
a) No garbage collection allowed
Since there is no way to determine which registers and temporary
cells contain pointers into the SIMULA storage pool, garbage
collection cannot be allowed directly or as a side-effect, i e
no storage may be claimed from the pool without making sure that
no garbage collection will result.
b) The data structure must be consistent
The data structures used by SIMDDT must be consistent in order
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-31
741111 780302 6 Lars Enderin
not to get wild results or cause program interrupts. In
particular, the current block pointer, XCB, must be consistent
with the program address used by SIMDDT to pinpoint the program
state (program point and current data). XCB may not point to a
block which is partly correct, e g does not have a proper
display vector. If the interrupt was not in compiled SIMULA
code, the bottom stack level must point to a program point
consistent with XCB.
c) SIMDDT may not call non-reentrant routines which change
global data in use at the time of interrupt
This requirement is met by not permitting SIMDDT to be called
while such a routine is active.
III.1.6.1.2.3.2 Controlling the effect of REENTER
In order to conform to the basic requirements, special control
features have been implemented for determining when and if
SIMDDT can be called. For the purposes of this description, a
SIMULA program with its attendant run time system (RTS),
possibly linked with some FORTRAN or MACRO-10 subroutines, is in
one of three states:
State A (allow).
In this state, SIMDDT may be invoked directly. The data in the
pool is consistent with the program point given by XCB and the
interrupt address (usually .JBOPC). A SIMULA program is in this
state when it is at code level, i e outside any RTS routines in
code compiled by SIMULA. State A also applies to some (sections
of) RTS routines, e g mathematical subroutines. The bottom of
the stack (YOBJRT) then points into the SIMULA code.
State D (defer).
In some RTS routines, invocation of SIMDDT must be deferred to
some future instant, normally the return to user code. If such
a point can be easily identified by reference to the push-down
stack, the stack can be manipulated to effect the invocation of
SIMDDT at the proper time. Routines of this type should always
return to the point of call, or the stack must be set up to
allow for such treatment. If a proper invocation point cannot
be found easily, the state must be F.
State F (forbid).
In this state, invocation of SIMDDT is forbidden. The program
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-32
741111 780302 6 Lars Enderin
is restarted with a message that a new attempt to stop and
REENTER should be made. A SIMULA program is in this state when
the data structure could be inconsistent and/or the program
point cannot be identified, etc. State F is avoided if
possible.
III.1.6.1.2.3.3 Macros for controlling the effect of REENTER
The state information is encoded in a global cell in the static
low segment area (based on the address in .JBOPS and addressed
by XLOW, which is normally AC16). This cell is called YDSCSW
and is manipulated by the following macros:
CALLOW
This macro sets the state to A by clearing YDSCSW(XLOW).
CDEFER
Adds 1 to YDSCSW(XLOW). State A goes to state D. Any other
state is unchanged.
CENABLE
Subtracts 1 from YDSCSW(XLOW). Will give state A if
YDSCSW(XLOW) was 1, otherwise the state is unchanged. Proper
use of the macros will ensure that YDSCSW(XLOW) is not 0 when
CENABLE is executed. CDEFER and CENABLE must be properly nested
so that state A is reached when an equal number of those macros
have been executed, if the initial state was A, and state F was
not set.
CFORBID
Sets the left half of YDSCSW(XLOW) to -1. The state is thereby
set to F (YDSCSW negative).
In order for these macros to work, the global cell YDSCSW must
be addressable via the register designated XLOW (set by the
LOWADR or SETLOW macro).
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-33
741111 780302 6 Lars Enderin
III.1.6.1.2.3.4 Actions after REENTER
If the program is interrupted and subsequently REENTER-ed, the
RTS actions depend on the state as follows:
If the ordinary reentry point is not in effect, the state is
irrelevant, either because the RTS is not inintialized, or
because .OCRE is active in processing a REENTER command.
Execution merely continues with a message stating the reason.
If the ordinary reentry point is in effect (.JBREN=.OCRE), the
actions are:
All registers are saved. .JBREN is changed to an alternative
reentry point. The PC value at interrupt (.JBOPC) is stacked as
return address. If .OCRE is entered from OCRET (deferred
REENTER), .JBOPC is the address of the return to SIMULA code, i
e a faked PC value. The state is determined and governs the
actions.
III.1.6.1.2.3.4.1 Calling SIMDDT directly after REENTER
State A: Set a switch to disallow garbage collection. If
SIMDDT is not in core (loaded with program), bring it in if
possible. Start at the point DSINR of SIMDDT with XDSBAS set to
the base of SIMDDT. YDSCAD(XLOW) gives the program point of
interrupt, if possible related to compiled code. When SIMDDT
returns, the switch to disallow garbage collection is reset.
.JBREN is set to .OCRE, the registers are restored, and control
returns to the program via a "POPJ XPDP," instruction to where
.JBOPC pointed.
III.1.6.1.2.3.4.2 Preparing for deferred SIMDDT call
State D: In this state, the interrupted instruction must be in
some RTS routine, and the stack must have the return to compiled
code at the bottom. Invocation of SIMDDT should be deferred
until the return point. This is achieved by fixing up the stack
so that instead of returning to compiled code, a special RTS
routine will be entered. In some cases, the return address at
the bottom of the stack does not point to the next instruction
to be executed at return but to an inline parameter. In that
case, the inline parameter must be copied to a cell before the
start of the special reentry routine, and the cell at the stack
bottom must point to the copy. The only inline parameters used
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-34
741111 780302 6 Lars Enderin
in the present system at object code level are of the form
XWD n,m
where n is an integer whose absolute value is less than 512.
Thus, the op code part of the word is either 0 or 777 (octal),
and the word cannot be an executable instruction. The code
return address is saved in YDSCAD(XLOW), and the state is set to
F. The accumulators are restored and return is effected to
where .JBOPC points. When the special routine (OCRET) whose
address has been put into the bottom of the stack, is entered,
YDSCAD(XLOW) is copied to .JBOPC, state A is set, and .OCRE is
entered. The following actions are the same as for state A
above.
III.1.6.1.2.3.4.3 Call on SIMDDT not allowed
State F: If REENTER is attempted in this state, execution is
continued with a message. A new attempt should be made after
stopping the job again.
III.1.6.1.2.4 REENTER while processing REENTER in .OCRE or
SIMDDT
The contents of .JBREN are OCRE2 in that case. The current
SIMDDT command is suppressed if possible. If SIMDDT is
executing, ^C^C followed by REENTER can thus be used e.g. to
suppress the rest of a lengthy memory dump or source listing. A
message is typed and execution continued, or SIMDDT expects a
new command.
III.1.6.1.2.5 REENTER after program exit
This has the same effect as REENTER after LOAD or GET. When
SIMDDT signals that it is ready to accept commands, any old
breakpoint information has been reset.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-35
741111 780302 6 Lars Enderin
III.1.6.1.3 CONTINUE (CCONTINUE) command
CONTINUE has the normal effect of continuing execution where it
was stopped by a ^C or by execution of some instruction such as
EXIT 1, HALT, or by some monitor error.
CCONTINUE is identical to CONTINUE except for leaving the
terminal in monitor mode.
When CONTINUE is given after normal program exit, it has the
effect of invoking SIMDDT as if a ^C-REENTER had been given just
after the final END of the main program, but with the block
state of the main program block set to 1 to allow examination of
the global variables. A MONRT. (EXIT 1,) UUO returns the job
to monitor mode again.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-36
741111 780302 6 Lars Enderin
III.1.6.2 Overall SIMULA program control by the RTS
The modules involved in overall execution control are OCIN,
OCIO, OCEP and OCSP. OCIN and OCIO also contain some I/O code.
III.1.6.2.1 Setting up and initialization of a SIMULA program
A SIMULA program is started either directly by LINK-10 after
loading (EXECUTE or DEBUG command), or by a START or REENTER
command following a GET or LOAD command. The SIMULA program
layout shown in III.1.6.1.1 (START command) indicates the
initial actions.
III.1.6.2.1.1 Getting the high segment into core (OCSP)
OCSP (Overall Control, Start Program) is the first component of
the RTS to be called from the SIMULA program. OCSP is loaded
with the main program, normally in the low segment. Since the
low segment cannot be shared, the functions of OCSP have been
minimized, most initialization functions being deferred to the
the high segment. The main function of OCSP is to load the
initial high segment into core via a GETSEG UUO, after
allocation of a minimal amount of core for the so called STATIC
area of the low segment. If the high segment was loaded with
the program from REL files, and the main program was loaded in
the high segment, OCSP uses SETUWP to turn off write protection,
since the main program contains a data area. After getting the
high segment, OCSP transfers control to OCIN to perform the rest
of the initialization. The ac's are saved starting at offset
YACSAV in the STATIC area, after possibly getting the address of
SIMDDT from YOCDDT or from a REENTER call on .OCRE0. OCSP is
called by JSP instruction, saving the return address in an ac.
In the non-sys version, it is possible to look for the high
segment on several disk areas if the first GETSEG fails. See
module listing for further details.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-37
741111 780302 6 Lars Enderin
III.1.6.2.1.2 SIMULA program initialization (OCIN)
OCIN starts with some preliminary initializations: Clears
static area, sets standard value for LINESPERPAGE and LOWTEN,
records time-of-day and runtime at program start for later use
on program exit, sets up the run-time stack (based on XPDP),
finds any RUNSWITCHES block, initializes trap and UUO handling.
The rest of OCIN is concerned with actions related to BASICIO,
i.e. SYSIN and SYSOUT, specification of other files and
allocation of i/o buffers. This is described in III.1.7 (I/O
facilities).
III.1.6.2.1.3 End of initialization phase (OCEI)
OCIN ends by transferring control to OCEI, which opens SYSOUT,
loads SIMDDT if space was allocated and transfers control to
SIMDDT or the first explicit SIMULA statement. If SIMDDT is
first started, it transfers control to the program after its own
initializations. OCEI was introduced to define a point where
control passes from the initial high segment to the other high
segment if two segments are used.
III.1.6.2.2 Swapping of high segments (OCSW)
The high segment parts of the SIMULA RTS can be classified into
two categories:
a) Routines which are used frequently by an executing SIMULA
program, such as block creation and block entry, editing
procedures, etc.
b) Routines which are used only at the start of execution or
very seldom during the execution of a normal SIMULA program.
In order to reduce the memory space normally occupied by a
SIMULA program, the high segment routines (collectively named
SIMRTS) are grouped into two distinct high segments, SIMRn1 and
SIMRn2 (n = SIMULA version number, e.g. SIMR41 and SIMR42 for
version 4 of SIMULA). SIMRn1 contains most of the routines,
those of category a, and the other high segment contains
routines of category b and also some routines of category a
which are used by the category b routines.
The routines of category b are those concerned with program
initialization and file object creation. Communication between
the two high segments is via the transfer vector placed at the
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-38
741111 780302 6 Lars Enderin
start of the high segment and defined in the SIMRTS.MAC module
via the RTSYMBOLS macro. The transfer vector has the same size
in both high segments. The difference is in the contents of
certain vector elements. Each global subroutine in the high
segment has a fixed absolute position in the transfer vector.
For those routines that are present in the current high segment,
the transfer vector contains a JRST instruction to the actual
entry point.
A subroutine which is not present in the current high segment is
represented by a "PUSHJ XPDP,.OCSW" instruction in the transfer
vector, leading to the swapping routine.
.OCSW handles a call in the following way:
All ac's are saved starting at YUUOAC(XLOW). If the call to the
eventual RTS routine was via a PUSHJ XPDP,xxxx instruction, the
next lower level of the stack should point to the instruction
following the PUSHJ. The alleged PUSHJ instruction is saved in
the stack over the GETSEG for some checking when the new high
segment has been brought in. A GETSEG UUO brings in the other
high segment.
Since, by design, the transfer vectors and the OCSW procedure
are identically placed in their respective high segments and
exactly similar except for a few locations, GETSEG will return
to the next instruction, which is now in the OTHER high segment
(parallel worlds!!). Since channel 0 is used for GETSEG, it
must be restored if it was active for TTY I/O before the swap,
and the buffers must be relinked. The address of the called
entry in the transfer vector is retrieved from the return
address found on the stack.
If the original call was a PUSHJ to this address, OCSW must
prepare to swap the other segment back in. This is arranged by
stacking as return address the address of L6, where L6 is
defined differently in the two high segments:
1) L6: EXEC .OCSW 2) POPJ XPDP,
2) POPJ XPDP, L6: EXEC .OCSW
OCSW calls the ultimately wanted routine by jumping to the
corresponding location in the current high segment, which should
have a JRST to the actual code. If the subroutine returns to
its caller, the return will be to L6 as defined above, causing a
new swap and a final return to the caller, since the location
corresponding to L6 in one segment has a return instruction
(POPJ XPDP,) in the other segment.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-39
741111 780302 6 Lars Enderin
III.1.6.2.3 RTS error handling
A Run Time System error is normally reported via the RTSERR UUO
as defined in the UNIVERSAL parameter file SIMMCR.
Some errors are detected by other means, e.g. arithmetic traps
(III.1.6.2.4), errors in routines from FORLIB (III.1.6.2.3.4),
errors during program initialization (III.1.6.2.3.5 and
III.1.7.1).
Some errors are left for the monitor to handle, such as failure
to find a high segment via GETSEG (a HALT instruction sends
control to the monitor), push down list overflow, exceeded time
limit etc.
In some situations which should not occur in a valid SIMULA
program + RTS, a RFAI UUO (defined in SIMMCR) is issued.
III.1.6.2.3.1 "Normal" RTS errors in SIMULA (RTSERR)
An error in a running SIMULA program is usually reported by
execution of the RTSERR UUO. The error number is indicated by
the address field of the UUO (no index, no indirect address).
An alternative way of indicating the error would be to use an
ordinary subroutine linkage instruction such as PUSHJ, JSR or an
XCT applied to some globally accessible location. The
disadvantage is that another word would be needed to specify the
particular error, and since the number of possible errors is
rather large, this approach was rejected. The main disadvantage
with the UUO approach is a possible clash with other uses of the
same UUO, but since the SIMULA RTS must remain in control in any
case, that disadvantage is not felt to be great enough.
The error UUO and other UUO's are handled initially by the RTS
routine OCUU.
OCUU saves all ac's starting at YUUOAC(XLOW).
The UUO opcode is checked and the following happens if the
RTSERR UUO is recognized:
The error number is placed in YDSENR(XLOW) and the address of
the error UUO is placed in YDSEAD(XLOW). If the error did not
occur in compiled code (RTS stack not empty), a corresponding
code address is computed from the bottom element of the stack,
and that address is placed in YDSEAD instead.
If SIMDDT is not already in core, OCLD attempts to load it to
the storage pool, possibly after expanding core or collection of
garbage records.
If SIMDDT cannot be loaded, the error number is reported by an
inline error message and the program is terminated via OCEP
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-40
741111 780302 6 Lars Enderin
(closing files), otherwise SIMDDT gets control via its DSINE
entry point, writes the error message, identifies the source
line and module, then expects commands from the user. If SIMDDT
returns (via an EXIT command), the program is terminated
(closing files etc.).
For some errors, continuation is possible. Those errors are
distinguished by having a non-zero ac field in the error UUO.
The SIMDDT PROCEED command can be used to continue execution.
Error recovery is either automatic (standard action) or a new
text or integer value is requested to replace faulty data.
Extensions of this scheme are possible.
III.1.6.2.3.2 RFAI UUO
The RFAI UUO is used to signal an unusual situation in the RTS;
a situation which should not occur in a correct RTS, operating
with a correct SIMULA program (without any modules written in
other languages such as MACRO-10 or FORTRAN). An RTSERR UUO
with a special error number is simulated when the RFAI UUO is
interpreted. The ensuing treatment is described above.
III.1.6.2.3.3 Illegal UUO
If OCUU encounters an unrecognized UUO code, an error message is
again generated as for RFAI.
III.1.6.2.3.4 Errors in FORTRAN library routines
In library routines taken from the FORTRAN library (FORLIB),
e.g. SQRT, errors are reported by the following instruction
sequence:
XCT error-class, FORER.
CAI error-type, address(severity-code)
Here error-class may be ER%LIB or ER%APR, where the errors of
class ER%LIB usually have an associated ASCIZ error message
string starting at "address", and the ER%APR errors simulate
arithmetic traps, where address is where to go on recovery.
An ER%LIB error is handled by first typing the routine name in
an informative message prefixed by "ZYQEIR" then typing the
message string at "address" prefixed by "ZYQFLE". An ordinary
error message (RTSERR QFORER) is then simulated, transferring
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-41
741111 780302 6 Lars Enderin
control to OCUU.
For an ER%APR error, error-type specifies which trap (integer
overflow, floating point underflow, divide check, etc) should be
simulated. Error-type is translated to the equivalent SIMULA
error number, and an ordinary error message is again simulated.
III.1.6.2.3.5 Errors during program initialization
Some errors are detected in situations where SIMDDT cannot be
invoked because the necessary RTS environment is not yet set up.
This occurs e.g. if the core size is too small to allow program
execution, if the high segment cannot be loaded, or if SIMDDT
cannot be loaded. Any error during the initial setup of SYSIN,
SYSOUT etc in OCIN is reported directly to the terminal without
SIMDDT intervention.
III.1.6.2.3.6 Errors diagnosed by the monitor
Some errors cannot be handled easily within the RTS. Examples
are push down list overflow (presently, the stack is needed for
error handling), time limit exceeded.
Attempted execution of illegal or privileged instructions,
execution of a HALT etc, will also lead to an error on monitor
level, as will some errors in connection with file handling.
See Monitor Calls (in the Software Notebooks).
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-42
741111 780302 6 Lars Enderin
III.1.6.2.4 SIMDDT - RTS interface
SIMDDT, the interactive SIMULA debugger, is described elsewhere
in this document (section IV). The RTS is responsible for
bringing SIMDDT into core and calling it in the following
situations:
- At program start in response to a DEBUG or REENTER command.
- At program start to remove breakpoints if loaded earlier.
- At a breakpoint inserted by SIMDDT.
- Via REENTER after ^C interrupt.
- When a RTS error has occurred.
- After program exit in response to a CONTINUE or REENTER
command.
III.1.6.2.4.1 SIMDDT at program start
SIMDDT will be called (entry point DSINI) before the start of
the SIMULA statements, but after RTS initialization, if
execution starts at the entry point .OCRE0 of the RTS. This is
achieved via the DEBUG command or via the REENTER command after
a LOAD or GET or after program exit. See III.1.6.2 (REENTER
command). When invoked in this way, SIMDDT stays in core during
program execution and also over a new START or REENTER command
issued after program exit. A subsequent START command will thus
have the same effect as REENTER, i e SIMDDT cannot be bypassed
once loaded at program start. After possibly setting some
breakpoints, the user starts normal program execution with a
PROCEED command.
III.1.6.2.4.2 Removing breakpoints on restart
If the program is restarted after successful execution or after
an error, SIMDDT may have left breakpoints lying around if
invoked dynamically via ^C-REENTER. Any such breakpoints are
removed by calling OCSPDR at the start of OCSP or .OCRE0.
OCSPDR determines if SIMDDT is in core by checking the right
half of .JBOPS, and if that is non-zero, the global cell YDSBAS
based on the address in .JBOPS. If YDSBAS is non-zero, it is
assumed to be the base of SIMDDT, which is called at the entry
point DSINS to remove the breakpoints specified in its internal
table.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-43
741111 780302 6 Lars Enderin
III.1.6.2.4.3 Invoking SIMDDT at breakpoints
When a breakpoint UUO is recognized by the UUO handler OCUU,
SIMDDT is invoked at its entry point DSINR, provided SIMDDT is
available. Otherwise, an illegal UUO is indicated.
III.1.6.2.4.4 Invoking SIMDDT by ^C-REENTER
SIMDDT may be invoked at almost any program point by stopping
the program with one or two ^C commands, then issuing a REENTER
command. See III.1.6.1.2.3.
III.1.6.3 SIMULA constructs for execution control - RTS support
routines
The facilities for execution control covered by section
III.1.6.2 have no direct counterparts in the SIMULA language
definition. The present section describes those execution
control features defined in SIMULA which are not implemented by
compiled code.
III.1.6.3.1 The state of execution of a block
The state of execution of, e g, a procedure block, is defined by
the values of some items of information:
- The values of all variables in the program.
- The current program counter PC, also called program sequence
control, PSC.
- The current block CB, i e the nearest block with a display.
The accumulator designated XCB always points to the current
block.
- Possibly, the current subblock, implicitly defined by PSC and
CB.
- The reactivation point RP, consisting of a reactivation
address RA and a block instance address RBI, reactivation block
instance. In the RTS, RP=(RBI,RA) is represented in the display
record by (ZDRZBI,ZDRARE).
- The state is also characterized by the Boolean conditions
detached and terminated. A block which is not detached is said
to be attached, and a block which is not terminated is said to
be active.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-44
741111 780302 6 Lars Enderin
- In a wider sense, the state of a block is also affected by the
program environment, e g the state of I/O devices, other
programs on the machine including the monitor. These effects
are not considered in this section.
III.1.6.3.2 Procedure call, procedure exit
A procedure is invoked via a procedure statement or a function
designator. Some procedures are implemented as inline coding
sequences. These are not considered here. Other procedures are
implemented as standard procedures which give a well-defined
result and return to the caller without essentially affecting
the program state except for changing some variables. These
procedures are described in the sections on I/O handling, TEXT
handling and standard procedures respectively.
III.1.6.3.2.1 Calling a SIMULA procedure
A SIMULA procedure is set up by one of the subroutines CSSN or
CSSW. CSSN is used when setting up a "normal" procedure, i e a
procedure which is declared and statically visible from the
point of call, and which is not an attribute of an inspected
class or a match for a virtual procedure. Calling sequence:
<save ac's>
MOVEI XSAC,prototype address
PUSHJ XPDP,CSSN
<parameter transmission>
The sequence <save ac's> is only needed if intermediate results
exist in some accumulators (and possibly pseudo ac locations
.YXAi). The sequence is:
PUSHJ XPDP,CSSA
XWD n,admap
where n is the number of intermediate results starting by XWAC1
and admap is the address of a bit map specifying which ac's have
object pointers (see III.1.5.2). CSSN allocates the procedure
block and its attached display record (ZDR) by calling SADB,
then copies most of the display vector from that of CB. RP is
set to (CB,return address). The ZAC address, if any, is copied
by SADB to the display vector from YCSZAC which is then reset to
zero. If the procedure has no parameters, CSEN is entered
directly instead of returning to the calling program. On exit
from CSSN, XRAC=XWAC1 holds the address of the procedure block.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-45
741111 780302 6 Lars Enderin
The calling sequence to CSSW is
[evaluate ZDP of procedure to top ac's]
PUSHJ XPDP,CSSW
XWD n,admap
<parameter transmission>
The top ac's are XWAC1+n and XWAC2+n. If n is zero, admap is
also zero, signifying that no intermediate results exist in
ac's. CSSW allocates a procedure block and display vector via
SADB like CSSN. The ZDP information is saved in YOBJAD(XLOW)
over a possible garbage collection and relocated there if
necessary. The innermost level (furthest from the block in the
display) is the address of the procedure block itself, put there
by SADB. The next to innermost level in the display is taken
from ZDPEBI of the input dynamic procedure address, and the rest
of the display is copied from the display of ZDPZBI.
III.1.6.3.2.1.1 Code for parameter transmission
The sequence <parameter transmission> is only needed if the
procedure has parameters and has the following form:
<parameter coding>
PUSHJ XPDP,CSEN ;Enter procedure coding
If the procedure has parameters, CSSN or CSSW returns to SIMULA
code for evaluation and transmission of the actual parameters.
The coding sequence, <parameter coding>, compiled to transmit
the parameters must preserve the value of XWAC1 by using XWAC2
as top ac and causing a ZAC object to be created whenever the
garbage collector may be called. The <parameter coding>
consists of coding to evaluate and transmit a representation of
each actual parameter. The code generated for a parameter
normally consists of a straightforward expression evaluation to
one or two ac's and a store operation which places the value in
the formal location. For name parameters, a parameter
descriptor (ZFL instance) is computed and stored, and any thunk
coding is compiled inline and bypassed with a JSP instruction.
For parameters by reference or by value, the normal
representation is used for variables and expressions. For
procedure, label or switch parameters, a dynamic representation
is computed (ZDP, ZDL or ZDS instance) and stored. For a TEXT
parameter by value, the system routine COPY is called, and for
an ARRAY by value, CSCA is called. When calling a formal,
virtual or external NOCHECK MACRO-10 procedure, however, the
parameter transmission sequence following the PUSHJ to CSSW has
a special form involving a call on the RTS routine PHPT. See
parameter handling. CSEN is called directly from CSSN or CSSW
if no parameters exist, otherwise it is called after parameter
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-46
741111 780302 6 Lars Enderin
transmission to start the operations of the procedure.
III.1.6.3.2.1.2 Starting the actions of a SIMULA procedure
CSEN changes XCB and jumps to the declaration coding of the
procedure. A procedure, unlike a class object, can never be
detached. When it terminates via CSEP for a function procedure
or CSES for a pure procedure, its data area can be reclaimed
directly or by subsequent garbage collection.
III.1.6.3.2.2 Calling FORTRAN and MACRO-10 procedures
OPTIONS(/E:FORTRAN (or F40),entrypoint);
The coding sequence for calling an external FORTRAN procedure is
essentially the same as that for any SIMULA procedure, with the
restriction that REF, LABEL, SWITCH, and PROCEDURE parameters
are not allowed. A procedure block is allocated in accordance
with a special prototype generated from the specification coding
for the procedure. The special routine PHFO serves as
intermediary between the SIMULA-generated procedure block and
the FORTRAN code. See parameter handling. When the FORTRAN
code is active, XCB is saved in the global cell YFOXCB.
OPTIONS(/E:CODE,NOCHECK,entrypoint);
A NOCHECK MACRO-10 procedure is handled like a formal or virtual
SIMULA procedure, i e by a special calling sequence to CSSW,
including a call on PHPT. See parameter handling. Strict rules
must be followed by the MACRO-10 procedure in order not to
compromise the security of the SIMULA program.
OPTIONS(/E:CODE,entrypoint);
A MACRO-10 procedure with specified parameters is handled
exactly as a SIMULA procedure.
OPTIONS(/E:QUICK [,NOCHECK] ,entrypoint);
A MACRO-10 procedure which is specified as "QUICK" (not "CODE")
takes all its parameters in ac's and is called by a PUSHJ
XPDP,entrypoint instruction. The calling sequence is the same
as for e.g. MAIN, STRIP. The RTS is not involved, only compiled
code. See SIMLH2.MAN Chapter 7 and appendix E.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-47
741111 780302 6 Lars Enderin
III.1.6.3.2.3 Procedure exit
The exit from a procedure is via the final statement or possibly
via a GOTO statement. A function procedure exits via CSEP,
which restores any intermediate results and puts the function
value on top. The presence of intermediate results is signalled
by the ZDNACS bit in the object, and the saved values are
retrieved via the ZDRZAC pointer in the display record. Two
ac's are always transmitted to avoid testing for result type in
CSEP. The compiled code knows which ac(s) to use according to
the stack discipline for register allocation. A pure procedure
exits via CSES, which is similar to CSEP except that no function
value is returned. The procedure block may be deallocated if no
block which is still referenceable was allocated on top of the
procedure block. A procedure always returns to the environment
given by (ZDRZBI,ZDRARE), the dynamic link, except for a direct
or indirect GOTO statement.
III.1.6.3.3 Creation of a class object
A class object is generated by an "object generator" - NEW
<class-id> [<parameter list>]. An object generator is very
similar to a function designator and may also serve like a
procedure statement if the value is discarded. Since name mode
parameters are not allowed, the calling sequence is simpler than
a general procedure call. Calling sequence:
<save ac's>
PUSHJ XPDP,CPNE
XWD m,prototype address
<parameter transmission>
where m=offset in display of the block whose display should be
copied. Usually, the display of XCB can be copied, but in some
cases of inspection statements all relevant levels may not be
correct. CPNE works in a fashion very similar to CSSN. If the
class has local classes declared (ZCPKDP bit set in prototype),
the ZDNKDP bit in the block must be set to prevent the display
from being deallocated when the class object is terminated. The
display may be needed when calling a procedure attribute of one
of the local classes, which may again be terminated and without
a display. Any REF or ARRAY locations on the current prefix
level of the object are initialized to NONE via SADB on
allocation. CPIN is called to initialize REF and ARRAY cells in
the outer prefix levels. If parameters exist, control goes back
to SIMULA code for parameter transmission, otherwise CSEN is
called directly. Parameter transmission is done as for a
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-48
741111 780302 6 Lars Enderin
procedure but is simpler since only value and reference mode
parameters are possible and label, switch and procedure
parameters are not allowed. See III.1.6.3.2.1.1. CSEN enters
the declaration coding of the outermost prefix. CPCD transfers
control to the declaration coding at the next inner level or the
statements at the outermost level. CPCI transfers control to
the statements of the next inner prefix level at an explicit or
implicit INNER statement. At the end of the statements at the
innermost level without an explicit INNER, CPE0 is called to
terminate and detach the class object. If an explicit inner
exists for some prefix, compiled code effects the transfer
either directly or via ZCPIEA of the prefix, if the code address
is not available at compile time (external or system class).
Control returns with an object reference in the top ac either
when the class terminates or when an explicit or implicit detach
is performed. See below (quasi-parallel sequencing).
III.1.6.3.4 Entering a prefixed block
A prefixed block is set up in a way very similar to a class
object. Calling sequence:
MOVEI XSAC,prototype address
PUSHJ XPDP,CPSP
<parameter transmission>
The display is copied from the statically enclosing block,
adding the address of the prefixed block itself at the innermost
level. Initialization is done as for a class object. In order
to implement quasi-parallel sequencing as described by CBL 9.2,
an enclosing detached block must be linked dynamically to this
prefixed block. This is done by setting RP of the nearest
enclosing detached block to (address of this prefixed block, 0).
If this is the outermost prefixed block, the dynamic link is set
to point to itself. After any parameter transmission, which is
similar to that for a class, CSEN transfers control to the
declaration coding at the outermost prefix level as for a class.
Instead of the last call to CPCD, however, CPPD is called to
transfer control to the statements of the outermost prefix. The
block terminates via compound tails of prefixes and ultimately
via CPE0, which restores the XCB of the static environment
before exiting to the instruction after the prefixed block.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-49
741111 780302 6 Lars Enderin
III.1.6.3.5 Implementation of quasi-parallel systems
Quasi-parallel systems (QPS) are described in CBL 9.2. In the
present section the actual implementation of a QPS control
structure is outlined.
III.1.6.3.5.1 Information needed to define a QPS
A QPS consists of
a) A prefixed block, called the main program of the QPS.
b) Any enclosed detached class objects or prefixed blocks.
c) Any other blocks enclosed by the main program.
The COMPONENTS of the QPS are the detached instances. Blocks of
category (c) are relevant only to define "enclosed", which is
interpreted according to CBL 9.1, q v. The QPS structure is
defined by the reactivation points of its components. The
reactivation point RP = (RBI,RA) of a component is interpreted
in the following way:
If RA is zero, RBI points to an enclosed prefixed block which
contains the actual reactivation point. If RA is non-zero, it
points to the program address where execution should resume,
with XCB=RBI.
The basic means for controlling the execution of a QPS are
provided by the system procedures DETACH and RESUME, CBL 9.2.
The procedure CALL has been implemented to simplify programming
of coroutines.
III.1.6.3.5.2 DETACH statement
The detach statement works according to CBL 9.2.1. The effects
described there are implemented by the CPDT procedure in the
following way:
a) The smallest operating block instance, X, is attached, either
because it has just been generated via NEW or because it has
been reattached via CALL.
Actions: RP := (X,RA), where RA is program point after call on
detach. ZDNDET is set, and control returns to old RP (calling
block,return address).
b) X is already detached.
Actions: RP := (X,RA) as above. The main program of the
innermost enclosing QPS is then found by following static links
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-50
741111 780302 6 Lars Enderin
for detached objects, dynamic links for attached objects, until
a prefixed block is found. The static link SL of a block B is
the block address found at offset B.ZBIZPR.ZCPSBL relative to B.
RP = (BI,RA) of the main program is found. If the program
address RA is zero, the reactivation point is inside BI (an
enclosed prefixed block), and RP := BI.RP, whose program address
RA is then examined, etc until a non-zero program address is
found. This is where execution resumes, with XCB set to RP.BI
(ZDRZBI).
III.1.6.3.5.3 RESUME statement
The resume procedure has the effects described in CBL 9.2.2.
The RTS routine CPRS implements resume. Assume that the
detached object to be resumed is Y, component of a QPS called S.
Resume is called inside a currently operating component X of the
same QPS.
Actions: X, the nearest detached block instance, is found by
dynamic links starting from XCB. RTS error (RESUME operating)
if X=Y. X.RP := (CB,RA), where CB is current block, pointed to
by XCB and RA = address after resume statement. To check for
errors, all enclosing detached instances are found by following
static and dynamic chains from X as in the detach procedure (the
operating chain is followed) until the outermost block is
reached. If any of the encountered blocks is Y, we have an
error. Starting from Y, find actual reactivation point by
following RP = (BI,RA) until RA is non-zero. Resume execution
at that RP.
III.1.6.3.5.4 CALL statement
The CALL procedure (CPCA) is not part of the Common Base but is
a recommended extension. CALL essentially reverses the effect
of DETACH, as follows:
Assume the statement CALL(Y), executed within a QPS component X.
X and Y are components of the same QPS S. Y may not be
attached, terminated or operating. X is found starting from
XCB, following RP until a detached block is found. Error if
X=Y. Copy Y.RP to X.RP to set correct reactivation point. As
in CPRS, all detached blocks enclosing X are found via static
and dynamic links and checked against Y (error if identical).
Attach Y to caller by setting off the ZDNDET bit and setting RP
= (CB,RA), where CB is current block, RA is program address
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-51
741111 780302 6 Lars Enderin
after CALL statement. The reactivation point of Y is found as
in CPRS and execution resumed there.
III.1.6.3.5.4 Object termination
Ignoring any compound tails after explicit INNER statements, the
effect of passing through the final END of an object is to
detach and terminate the object. CPE0 is called. For a class
object, CPE0 sets the ZDNTER bit and transfers control to CPDT
(see detach). The same is done for a prefixed block, but since
detach has no effect, control is returned to CPE0 which restores
XCB and transfers control to the statement after the prefixed
block.
III.1.6.3.5.5 GOTO statement leading out of an object
See CBL 9.2.4.
III.1.6.3.6 INNER statement
The INNER statement is implemented by the CPCI routine, which
transfers control to the statement coding at the next inner
prefix level. Has no effect if there is no inner level.
III.1.6.3.7 GOTO statements, switches
GOTO statements are normally handled by compiled code. If the
target of the GOTO implies change of current block (CB), CSGO is
called, however. The parameter to CSGO is a dynamic label (ZDL
instance). CSGO follows the operating chain from the current
block until the target block is found or the outermost block is
reached. Class objects passed on the way are terminated and
subblock addresses eliminated from displays when passing. Since
the target must be operating, a GOTO out of a detached object is
allowed only if it leads out of the nearest enclosing prefixed
block, and a transfer to a connected label will be allowed if
and only if the inspected block is operating. A SWITCH element
is evaluated by CSSC, which takes a dynamic switch address (ZDS
instance) and a switch index as parameters and returns a dynamic
label address (ZDL). If the switch element is a statically
visible label, the static description is translated to the
dynamic form. If the switch element is a designational
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-52
741111 780302 6 Lars Enderin
expression, a dummy procedure block is set up and the switch
thunk is entered, to return later via CSES. CSES works like
CSEP except that the dynamic label is already in the top ac's.
III.1.6.4 Execution control by compiled code
Apart from calling sequences to RTS routines, the principal
means of execution control in compiled code are conditional
statements and expressions, WHILE loops, FOR loops and simple
GOTO statements. Only FOR loops are interesting from the RTS
point of view, because the return address of a FOR loop is
stored in the display vector. One word is required in the
display vector for each FOR loop nesting level in the current
block.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-53
741111 780302 6 Lars Enderin
III.1.7 I/O handling
------------
I/O handling in a SIMULA program covers the following basic
areas:
BASICIO functions, i e setting up and opening SYSIN and SYSOUT.
In DECsystem10 SIMULA, file specifications may be read and
runtime switches interpreted.
Creation and setup of file objects of the various file classes,
allocation and handling of buffers.
Implementation of the basic I/O functions OPEN, CLOSE, INIMAGE,
(BREAK)OUTIMAGE, LASTITEM, LOCATE, ENDFILE.
I/O editing functions: INCHAR, OUTCHAR, ININT etc.
III.1.7.1 BASICIO functions
The functions related to the definition of BASICIO in CBL 11 are
mostly implemented in the OCIN module of the RTS. Pointers to
the standard file objects SYSIN and SYSOUT are placed in the
static lowseg area at offsets YSYSIN and YSYSOUT respectively.
FILE prototypes are placed in the transfer vector (SIMRTS
module), whereas declaration and statement coding and symbol
tables are placed in the IO module. A special naming scheme is
adopted for quantities relating to file subclasses:
Each class is denoted by 4 letters: IOFI (FILE), IOIN (infile),
IOOU (outfile), IOPF (printfile) and IODF (directfile). SIMRPA
defines a macro for each prototype. If the class code is xxxx
(=IOIN etc), then .xxxx is the global name (prototype base
address), xxxx%S is the address of the initial statements,
xxxx%D is the start of declaration coding, D%xxxx is the name of
the macro, xxxx%I is the first address after inner in the
statement part, xxxx%M is the block map address, and xxxx%Y is
the address of the symbol table.
Before allocating SYSIN and SYSOUT, a possible specification
file defined via a compile-time /R switch is read. Encountered
switches are acted upon, buffer space is allocated, and a
specification table for files is built. This table will be
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-54
741111 780302 6 Lars Enderin
consulted whenever a file subclass is created.
When any specification file has been processed, .SAGI is called
to initialize the storage allocation system, leaving the buffers
and specification tables below the bottom of the storage pool.
Next, the SYSIN infile object is set up. Normally, SYSIN and
SYSOUT will both be the user's TTY, but the specification file
may define SYSIN and/or SYSOUT differently. In the absence of
specifications for SYSIN or SYSOUT, the logical name SYSIN or
SYSOUT is checked to find out if it has been assigned as a
device name. If so, the file named SYSIN or SYSOUT on that
device is used, otherwise the TTY is used. See OCIN for
complete algorithm. SYSIN.open(blanks(n)) is performed, where
n=80 or the width of the TTY line in the case when SYSIN is a
TTY.
The SYSOUT printfile object is then set up, and LINELENGTH is
determined as 132 or the width of the TTY line if applicable.
The actual execution of SYSOUT.open(blanks(LINELENGTH)) is left
to OCEI which is then entered.
The final actions of BASICIO, SYSIN.close and SYSOUT.close, are
performed at program end via OCEP.
III.1.7.2 File object generation, file setup, buffer allocation
The calling sequence for a file object generation is similar to
that for a SIMULA-coded class, for example:
PUSHJ XPDP,CPNE ;NEW infile("INPUT")
XWD -n,IOIN
DMOVE XWAC2,[XWD 0,-2+[ASCII/INPUT/]
XWD 5,0]
PUSHJ XPDP,TXCY
XWD 1,[1B0]
DMOVEM XWAC2,OFFSET(ZFISPC)(XWAC1)
PUSHJ XPDP,CSEN
This calling sequence, when executed, causes the following
actions:
- The file object is created via CPNE and SADB. The display is
copied from the block referenced at offset -n in the display of
the current block.
- CSEN changes XCB and sets the return information, then
transfers control to the declarations of the outermost prefix
level, IOFI%D. Neither IOFI%D nor IOIN%D, which is entered
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-55
741111 780302 6 Lars Enderin
next, contains any real declaration coding, only calls CPCD.
The statement coding part of IOFI, IOFI%S, which is then
entered, is also empty, transferring control to IOIN%S via CPCI
(inner). At IOIN%S, the real initial actions for the infile
start by setting flags and clearing certain switches, then
calling the SETUPFILE routine of the IONF module
- SETUPFILE uses the information in ZFISPC (copy of text
parameter to NEW ...) and any specification table created at
BASICIO initialization (see above) to determine the
characteristics of the file which is to be input and/or output.
If sufficient information is not available or a dialogue is
expected, the user is interrogated for the missing information.
A free software channel is claimed and OPENed. Device and file
name, number and size of buffers, etc is determined, if
necessary by consulting the user. CREATEFILE allocates and
links the buffers, performs new OPEN on the same channel as
before, and performs LOOKUP and/or ENTER.
III.1.7.3 Other basic I/O functions
Apart from the I/O functions mentioned above, the following
procedures contained in the IO module are essential: OPEN,
CLOSE, INIMAGE, (BREAK)OUTIMAGE, LASTITEM, LOCATE, ENDFILE. The
remaining procedures are merely applications of text handling
procedures. Most of the procedures conform to the definitions
in CBL chapter 11. Special information:
- OPEN (IOOP): Special actions must be done via the routine
REOPEN in IONF if the file was once opened and then closed.
Buffers must be allocated and chained, information fetched from
the specification table, an OPEN UUO must be performed etc.
These things are normally done at file creation (see above), and
the SIMULA procedure OPEN simply does what CBL specifies. For
DIRECTFILES, however, OPEN computes file record length from
image.length, allowing for <CR><LF> and rounding up to a
multiple of 5 (word alignment), and computes max LOCATION from
file size and record length.
- CLOSE (IOCL), in addition to doing what CBL prescribes, also
outputs the last image for an outfile, provided pos > 1. The
software channel is released and YIOCHTB updated. If the
channel table entry refers to two file objects representing a
bi-directional device such as a terminal, the channel is not
released until the last of the two files is closed.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-56
741111 780302 6 Lars Enderin
- INIMAGE (IOIG) has the following special properties: Carriage
returns and null characters are ignored. Line feed is taken as
end of image but is not transmitted to the image. Form feed,
vertical tab and altmode (octal 14, 13, 33) are taken as image
delimiters and are also taken as part of the image. If inimage
tries to read past the end of the file or reads an unwritten
record inside a directfile, a special end-of-file record
starting with /* and padded with blanks is transmitted to the
image.
- OUTIMAGE (IOOG). Only image.strip is moved to the buffer to
save file space and time. Carriage-return is tagged on to the
end. If the buffer is output immediately, as for a TTY file, a
line feed is added before output. Pending line feeds from the
last line, if any, are output to the buffer before the current
line is output. This is because of our interpretation of
SPACING for PRINTFILES.
- BREAKOUTIMAGE (IOBO). Works as OUTIMAGE, except that no CR-LF
is added. To enable spaces at the end to be significant, image
is not stripped shorter than image.pos-1.
- LASTITEM (IOLI) works according to CBL, except that horizontal
tab (octal 11) is treated like the space character.
- ENDFILE is implemented as an ordinary variable in the infile
or directfile object. ENDFILE is set to -1 (TRUE) when inimage
finds that the file is exhausted, i.e. when the last character
in the file was read by the previous inimage call.
- LOCATE merely checks if the argument is in range and if so,
sets off endfile flags and sets a new LOC value = argument. No
operations directed to an external device are performed here.
Special considerations for directfile:
- The images in a directfile are all of the same length, given
by the size of the text given as IMAGE when calling OPEN.
Images are buffered within disk buffers (only DSK allowed as
device), and the disk buffers are held in core as long as
possible to minimize actual I/O. When inimage or outimage is
performed on a disk block not currently in core, the block is
read first if it exists. If no outimage was performed on a
buffer, it is not rewritten on disk when replaced in core.
Close does not imply that the last image is written as for
outfiles.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-57
741111 780302 6 Lars Enderin
III.1.7.4 Editing procedures for input/output.
The editing procedures, e g INCHAR, ININT, OUTFRAC, are defined
in terms of the corresponding text attributes. The definitions
given in CBL usually cover those functions sufficiently. The
"inaccessible" function FIELD of CBL 11.3.1 is implemented as
.IOFD. Deviations from CBL:
INCHAR (IOIC) and INTEXT (IOIT) test for ENDFILE before calling
inimage. In this way characters from the end-of-file image can
be read.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-58
741111 780302 6 Lars Enderin
III.1.8 Text handling
-------------
Text handling is performed by the modules TX and TXBL which
contain a) RTS procedures and functions corresponding to the
text attributes found in section 10 of CBL, b) the non-local
procedures BLANKS and COPY. Text relations and text value
assignment are also handled by special procedures. A routine
for creating a temporary text variable (ZTT) is also part of the
TX module. Some attributes are implemented by inline coding.
The representation of text information is described in I.5, data
structures, and LH2 appendix B.
III.1.8.1 Text attributes
Most text attributes are implemented by straightforward
translation of the CBL definition. Some implementation
dependent details are outlined below.
Pos is ZTVCP+1, i e pos=1 implies ZTVCP=0 which is convenient
since it allows NOTEXT to be represented by two zero words. The
attributes LENGTH, POS and MORE are implemented by inline code.
The function attributes MAIN (TXMN), GETCHAR (TXGC), GETINT
(TXGI), GETREAL (TXGR) and GETFRAC (TXGF) are called as follows:
MOVEI XTAC,Xtop
PUSHJ XPDP,function
where Xtop and Xtop+1 contain the text reference on entry and
the returned function value on return. The other attributes:
SETPOS (TXSE), PUTCHAR (TXPC), PUTINT (TXPI), PUTREAL (TXPR),
PUTFIX (TXPX) and PUTFRAC (TXPF) are called with the text
reference in XWAC1 and XWAC2, other parameters in XWAC3, XWAC4,
etc. The additional procedure LOWTEN (TXLT) is called in the
same way.
III.1.8.2 Other text procedures
Texts are generated by COPY (TXCY), BLANKS (TXBL) and by INTEXT
(IOIT), which is part of the I/O sub-system (III.1.7). Text
assignment of the form T1 := T2 is performed by TXVA, and
comparison of text values, e g T1 < T2, is performed by TXRE.
TXRE and TXVA are called with XTAC pointing to the first ac of
the 4 consecutive ac's that contain the texts T1 and T2
respectively. The relation between T1 and T2 is coded in the
result of TXRE as -1, 0 or +1. TXCY is called with an inline
parameter specifying any intermediate results:
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-59
741111 780302 6 Lars Enderin
PUSHJ XPDP,TXCY
XWD n,admap
Thus an accumulator stack may have to be saved over storage
allocation. The parameter to TXCY is saved in YTXZTV over a
possible garbage collection. TXBL is called like TXCY. The
text procedure TXDA, called like TXCY, in certain cases creates
a ZTT object containing a dummy text variable which stands for a
text expression. The output of TXDA is the dynamic address of
this text variable i e [XWD 1,ZTT object address] and also its
absolute address in the next ac.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-60
741111 780302 6 Lars Enderin
III.1.9 Parameter handling
------------------
Since value and reference mode parameters to ordinary
procedures, classes and prefixed blocks are handled entirely by
compiled code, parameter handling in the RTS is limited to
unusual circumstances - treatment of name mode parameters,
transmission of parameters to formal, virtual, FORTRAN and
NOCHECK MACRO-10 procedures.
III.1.9.1 Access to name mode parameters
Inside a procedure, a name parameter is accessed in different
modes and contexts. The PH module contains run-time procedures
for handling name mode parameters, calling thunks, etc.
III.1.9.1.1 The value of a name mode parameter
If the value of the parameter is required, PHFV is usually
called. PHFV handles parameters of kind simple, i e not array,
procedure or switch. Label parameters are handled by PHFM, and
text parameters are handled by PHFV only in contexts where the
text descriptor will not be modified, as in T.strip.
PHFV starts by calling PHINIT (see below). The parameter does
not have a thunk if the actual parameter is a simple variable or
constant. The absence of a thunk is signalled by the ZFLNTH bit
of the formal location. In this case, the value of the
parameter is loaded directly from the ZFL instance, from a block
instance or from the literal pool. See ZFL format. In other
cases, the parameter must be computed by a thunk. This is done
via ENTERTHUNK, PROCVALUE (if actual parameter is a
parameter-less procedure) and THUNKRETURN. Since calling the
thunk implies loss of control (the only link back to PHFV is via
the return address for ENTERTHUNK), care must be taken to call
ENTERTHUNK in such a way as to retain all useful information.
If the thunk returns a dynamic address, i e the thunk is not a
value type thunk (ZFLVTD bit), the value must be retrieved via
the dynamic address. Conversion of the value is done by PHCV
(entry PHCV1) if necessary (ZFLCNV bit). PHEXIT returns to
compiled code with the value in the proper ac(s).
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-61
741111 780302 6 Lars Enderin
III.1.9.1.2 The dynamic address of a name mode parameter
The dynamic address of a parameter X is needed
a) when X is used on the left hand side of an assignment (X:=...
or X:-...). The actual parameter in this case may be a simple
variable, a value or reference mode parameter or an array
component, possibly accessed via remote referencing (<object
expression>.<attribute>). PHFA is used in this case, except for
type TEXT, which is handled by PHFV for value assignment and
PHFT for text denotes (X:-...).
PHFA works as follows: PHINIT is called. Then, if the ZFL type
for the parameter signifies a value rather than a dynamic
address, an error message is issued. If no thunk exists, the
dynamic address is computed from the ZFL, otherwise the thunk is
evaluated via ENTERTHUNK and THUNKRETURN. If the parameter type
is REF, the prototype pointer is taken from ZFLZQU before
returning to compiled code via PHEXIT.
b) when X is specified PROCEDURE, ARRAY, SWITCH or LABEL. PHFM
is used in this case. PHFM works like PHFA except that no check
for illegal assignment need be made.
c) when X is specified TEXT and used in a context where the text
descriptor may be affected as with text editing procedures like
GETCHAR, PUTINT. PHFT is used in these cases and for text
denotes (X:-...).
PHFT starts by PHINIT and works essentially like PHFA if the
parameter representation yielded via the ZFL or a thunk is a
dynamic address. In this case, the actual parameter, possibly
accessed by remote referencing, is a text variable (or parameter
by value or reference) or a text array component.
If the actual parameter is a constant, a RTS error is signalled.
This is so if ZFLVTD=1 and no thunk has been compiled. The
remaining case is when the actual parameter is a text expression
computed by a thunk. Evaluation is done as in PHFV, but before
returning to compiled code, a dummy text variable must be
created. TXDA creates a ZTT record with a copy of the
descriptor computed for the text expression. The dynamic
address of this dummy descriptor is returned from PHFT to
compiled code.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-62
741111 780302 6 Lars Enderin
III.1.9.1.3 Assignment to formal parameters by name
If X is a formal parameter by name, an assignment of the form
X:=<rhs> is carried out as follows: a) PHFA computes the
dynamic address to one or two ac's. These ac's are preserved
over the execution of <rhs>.
b) The assignment is carried out by PHFS. Assume that the
dynamic address of X is in XWACi (and possibly a qualification
in XWACi+1), and the value of <rhs> in XWACj (+XWACj+1). The
calling sequence to PHFS is:
HLLZ X0,X ;ZFL instance
PUSHJ XPDP,PHFS
XWD XWACj,XWACi
PHFS carries out qualification checking and possible conversion
before transmitting the value.
III.1.9.1.4 Accumulator handling in PH procedures
The procedures PHFA, PHFM, PHFT and PHFV interface with compiled
code via the two local subroutines PHINIT and PHEXIT. The
calling sequence to any of the procedures is
[dynamic address of X to XWAC1+n]
PUSHJ XPDP,PHFy
XWD n,admap
where y is A, M, T or V, n is the number of intermediate results
and admap is zero or the address of a relocation map for the n
results. PHINIT calls .CSSA. to save these results if n > 0,
then puts the dynamic address of X in XWAC1 (normal case). The
absolute address of X, the formal location or ZFL instance, is
loaded to XFAD, and the two ZFL words are loaded to XFL0 and
XFL1. After computing the parameter, possibly via a thunk, each
routine returns to compiled code via PHEXIT. PHEXIT modifies
the stack to skip the inline parameter. If intermediate results
were saved (YCSZAC(XLOW) nonzero), PHEXIT returns via .CSRA,
otherwise directly.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-63
741111 780302 6 Lars Enderin
III.1.9.1.5 Thunk evaluation
The execution of a thunk is started via ENTERTHUNK, which is
called by JSP XRET,PHET. Before executing the thunk code,
information must be placed in the thunk save area allocated in
the display of the block where the actual parameter belongs.
The offset of the thunk save area (ZTS) is found at the head of
the thunk as shown by the following general coding sequence
compiled for a thunk:
XWD d,0
<code to compute the actual parameter>
MOVEI XSAC,d(XCB)
JSP d+OFFSET(ZTSRAD)(XCB)
where d is the offset of the thunk save area in relation to the
end of the display vector. In the thunk save area are saved the
dynamic address of the formal location, the return address to
object code (found in XPDP stack), the return address to the
present RTS routine (value of XRET), the acs pointer (YCSZAC)
and XCB. This information is sufficient to restore the
environment on return from the thunk, provided that the save
area itself can be found, which is guaranteed by having the
thunk return its address in XSAC as seen above. The new XCB is
taken from ZFLZBI, and the thunk is entered with the ZTS address
in XSAC.
In the rare case when the value of a procedure without
parameters is required, the thunk makes an intermediate return
with the dynamic address of the procedure in XWAC1 and XWAC2.
PROCVALUE (called by JSP XRET,PHPV) checks if the procedure
should have parameters after all (error if so), and then returns
to the thunk with a new return address taken from XRET put into
the save area. X0 is stacked on entering PHPV so that SIMDDT
can get the correct code address for the error message.
When the thunk returns to the RTS, which may be after execution
of a substantial amount of code including execution of the thunk
itself recursively, THUNKRETURN uses the information in the
thunk save area based on XSAC to restore the environment where
the parameter was accessed. On exit from THUNKRETURN (PHTR),
XFAD points to the formal parameter X (ZFL instance), the return
to SIMULA code is stacked, YCSZAC points to any saved
intermediate results, XCB is restored, and XFL0 contains the
first ZFL word.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-64
741111 780302 6 Lars Enderin
III.1.9.2 Parameter transmission to formal, virtual and NOCHECK
MACRO-10 procedures
The parameters to formal, virtual and NOCHECK MACRO-10
procedures cannot be checked fully at compile time, since the
formal parameter specifications are not known. Procedures in
this category are called via CSSW. The computation and
transmission of actual parameters is carried out by the RTS
procedure PHPT, which has a very special calling sequence:
[compute dynamic address of formal or virtual
procedure to top ac's]
PUSHJ XPDP,CSSW
XWD n,admap
Z npar
PUSHJ XPDP,PHPT
[Z prototype address] ;Only for REF
ZAP1: actual parameter descriptor (ZAP) for first param.
XWD d,ZAP2
[thunk for first parameter, if any thunk is needed]
[Z prototype address] ;Only for REF
ZAP2: ZAP for second parameter
XWD d,ZAP3
[thunk for second parameter]
..
[Z prototype address] ;Only for REF
ZAPn: ZAP for n'th parameter
XWD d,ZAPEND
[thunk for n'th parameter]
ZAPEND: XWD 0,0
PUSHJ XPDP,CSEN ;enter procedure body
In the above sequence, d is the offset of the last word of the
thunk save area in the display vector, and npar is the number of
actual parameters. CSSW is informed that PHPT is to be called
by the [Z npar] instruction placed as a second inline parameter
to CSSW. In any other situation involving CSSW, this
instruction must be an executable instruction. CSSW uses the
absence of this information to give an error message if the
procedure expects parameters but has not been provided with an
actual parameter list.
The number of actual parameters is checked against the number of
formal parameters, except for a NOCHECK MACRO-10 procedure
(ZPCNCK bit set in the prototype). The parameters are treated
in sequence. Information from the ZAP or the ZFL in case of a
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-65
741111 780302 6 Lars Enderin
passed-on name mode parameter is loaded to standard registers.
In the NOCHECK case, the formal parameter type and kind are
copied from those of the actual parameter. The prototype of a
NOCHECK MACRO-10 procedure has formal parameter descriptors
(ZFP) for 31 formal parameters all specified name. This means
that ZFL instances will be computed and stored for all
parameters. The actual parameter is first checked for
compatibility. If ZAPNTH is set, the ZAP specifies the address
or value of the quantity directly (generally, by effective block
level and offset). The quantity can be loaded, possibly
converted or qualification checked, and stored in the formal
location. Note that the qualification of an actual REF
parameter is found in the word preceding the ZAP. If the formal
parameter is specified NAME, a ZFL instance is computed and
stored. A NOCHECK MACRO-10 procedure is treated as having only
name mode parameters. If a thunk has been compiled, and the
formal parameter is not of name mode, the thunk must be
evaluated to yield the value. This is done in the same way as
in PHFA or PHFV, with the additional requirement that the
current positions in the actual (ZAP) and formal (ZFP)
descriptor lists must be remembered. This is done by storing
the addresses of the ZAP and the ZFP descriptors in the formal
location until the value has been computed. Since the dynamic
address of the formal location is saved in the thunk save area,
the formal and actual descriptor positions can be recovered on
return from the thunk. The dummy ZAP of all zeros finishes the
parameter list.
III.1.9.3 Parameter transmission to FORTRAN procedures
A FORTRAN procedure is identified to the SIMULA system via the
attribute file produced by the SIMULA compiler when the
interface code is compiled. See LH2 appendix E. The prototype
of the procedure and its associated core map (ZMP) contains
information assuming a special block layout documented in the
PHFO module. The value of ZPCDEC is the address of PHFO, which
is thus entered after block allocation and parameter transfer,
which is done exactly as for a SIMULA procedure. PHFO has the
task of adapting the parameters to FORTRAN formats and calling
the actual FORTRAN procedure. If the returned parameter values
have to be converted, PHFO does this before returning to SIMULA
code. Both old (F40) FORTRAN and new FORTRAN-10 procedures can
be handled. During execution of the FORTRAN procedure, YFOXCB
in the static area has the XCB value corresponding to the
procedure block. More information is available in the PHFO
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-66
741111 780302 6 Lars Enderin
module listing.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-67
741111 780302 6 Lars Enderin
III.1.10 SIMSET and SIMULATION
---------------------
The standard classes SIMSET and SIMULATION are implemented in
the SS and the SU modules, respectively, where prototypes,
symbol tables and RTS procedures implementing the main classes
and their attributes, are found. Names for quantities referred
by the prototypes are generated in SIMRPA in the same way as for
the FILE subclasses, see III.1.7.1. The classes involved are
represented by the symbols (fixup numbers used by the compiler):
SSST (SIMSET), SSLG (LINKAGE), SSHD (HEAD), SSLK (LINK), SUSI
(SIMULATION), SUPS (PROCESS), SUMA (Main Program of SIMULATION).
D%SUSI is thus the macro for implementing the SIMULATION
prototype, SUSI%S is the statement coding (SUSI.ZCPSTA) of
SIMULATION, etc. The present RTS design places SS and SU in the
low segment to be loaded with the compiled SIMULA program.
Since some information in the class prototypes is dependent upon
the level where the SIMULA program uses SIMSET or SIMULATION as
a prefix, the SIMULA compiler must supply this level as global
symbols to be used for relocation by LINK-10 or the LOADER.
Because both the effective block level and its negation are
involved, two symbols, .SIMLV and .SIMVL, are defined. .SIMVL
defines ZPREBL of the SIMSET and SIMULATION prototype, i e the
offset from the block address where the display element pointing
to the class object itself can be found at run time. .SIMLV is
the complement of .SIMVL, i e a positive quantity, which is used
to define the display vector lengths (ZPCDLE) of the classes
involved. .SIMVL is also used as ZCPSBL (static environment
block level) for the prototypes of SIMSET and SIMULATION
attributes.
III.1.10.1 SIMSET implementation
SIMSET is defined in CBL 14.1. The implementation is a
straightforward translation of this definition. FIRST, LAST and
PREV (recommended extension) are implemented inline by the
compiler. The SIMSET prototype is SSST (entry .SSST). No
special actions are performed for declarations (SSST%D) or
initial actions (SSST%S). Coding to set up a block prefixed by
SIMSET is no different from any prefixed block setup by CPSP.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-68
741111 780302 6 Lars Enderin
III.1.10.1.1 Classes local to SIMSET
SIMSET has the class attributes LINKAGE, LINKAGE class HEAD and
LINKAGE class LINK. LINKAGE (SSLG) objects have the two links
ZLGPRE and ZLGSUC implementing the inaccessible variables SUC
and PRED defined in CBL 14.1.2. ZLGSUC and ZLGPRE share a
36-bit word. No additional data is needed for HEAD and LINK.
III.1.10.1.2 Procedure attributes of LINKAGE, HEAD and LINK
The procedure attributes are implemented in a straightforward
manner following CBL definitions. Parameters to pure procedures
are passed in XWAC1, XWAC2, etc, and parameters to functions are
passed in ac's starting with XWACn, where XTAC has the address
of XWACn.
III.1.10.2 SIMULATION
The standard class SIMULATION is defined in CBL 14.2. The SU
module contains prototypes and actions of SIMULATION, PROCESS
and MAIN PROGRAM, procedure attributes of SIMULATION and
procedures to implement the activation statement. The
sequencing set is implemented as a binary tree of EVENT NOTICES
(ZEV). Event notices are referred by process objects (and the
event notice refers back to the process) which are scheduled.
For storage management reasons, event notices are contained in
event notice records (ZER) and chained to free lists when not in
use. The event notice records are chained to the SIMULATION
block and to each other. If several SIMULATION blocks exist,
they are chained to each other for garbage collection reasons.
The SQS tree is rooted at the last eventnotice (largest
scheduled time), which is located via ZSULT of the SIMULATION
block. The current event notice (smallest scheduled time) is
found via ZSUFT. The three links ZEVZBL (upward link), ZEVZLL
(left) and ZEVZRL (right) are used to define the tree in such a
way that the EVTIME (ZEVTIM) values of the left hand subtree are
always smaller than those of the right hand subtree and thus the
path from last to first event is via left links. ZEVZBL is used
for backtracking when the left or right link does not exist.
Depending on the order of scheduling statements, several
possible trees exist for a certain sequence of events. Example:
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-69
741111 780302 6 Lars Enderin
First Last
(ZSUFT) (ZSULT) (dummy)
------ ------ ------ ------ ------ ------
[ 1 ]<--[ 2 ]<--[ 3 ]<--[ 8 ]<--[ 10 ]<--[ZZZZ]
------ ------ ------ ------ ------ ------
! !
V V
------ ------ ------- ------
[ 4 ]<--[ 6 ]<--[ 7 ] [ 9 ]
------ ------ ------- ------
!
V
------
[ 5 ]
------
where left arrows denote left links and down arrows denote right
links. ZSUFT (current) refers to the ZEV labeled 1, and the
root is the last event (10). ZZZZ stands for the largest
possible real value [3777777777777 octal] and this node is
placed in the tree to facilitate ranking of times. The tree is
manipulated at the request of scheduling statements:
ACTIVATE/REACTIVATE, HOLD, PASSIVATE, CANCEL, WAIT.
Eventnotices are allocated by SANE, which allocates a new
eventnotice record (ZER) when no more free eventnotices are
found in the current record. Special measures have to be taken
to preserve event notice addresses over a possible garbage
collection. Since the garbage collector can only relocate
addresses that point to the start of recognizable records, i e
with a ZDN part, eventnotice addresses in global locations have
to be split into two parts, ZER address + offset, before
allocating a new ZER record. The global locations that can be
used are YSUPCP and YSUSCP. See SU and SANE coding. The
address of the (current) SIMULATION block is found via the
global location YSULEV in the static area, which is set up by
the initial actions of SIMULATION to contain the instruction
MOVE XSAC,.SIMVL(XCB). The effective block level of SIMULATION
is thus found in the right half of this word. The procedure
ACTIVATE described in CBL 14.2 is implemented as SUAC. CURRENT,
IDLE, MAIN, TERMINATED and TIME are implemented inline. The
rest is straightforward translation of the CBL definition, where
the SQS is implemented as described above without referring to
the CBL definition of class EVENT NOTICE. To simplify SQS
handling, a dummy ZEV with ZEVTIM=max real value is inserted at
the start. ZEVTIM is represented in single precision floating
point format. SUAC is called with an activation mask in X0,
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-70
741111 780302 6 Lars Enderin
process reference in XWAC1, second parameter (process or time)
in XWAC2. See SU module for details.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-71
741111 780302 6 Lars Enderin
III.1.11 Standard procedures and functions
---------------------------------
The following standard procedures and functions are available in
DEC-10 SIMULA:
SIMULA name Fixup (1) Access (2) result param. call
type types (3)
ABS inline G R/L R/L
ACCUM SUAM SU - R,R,R,R (5)
ARCCOS MAAC G R R F
ARCSIN MAAS G R R F
ARCTAN MAAT G R R F
MAATD G L L F
BLANKS TXBL G T I A2
BREAKOUTIMAGE IOBO IOOU P
CALL CPCA G - O A1
CANCEL SUCA SU - SUPS P
CARDINAL SSCA SSHD I A1
CHAR inline G C I
CLEAR SSCL SSHD P
CLOSE IOCL IOFI P
COPY TXCY G T T A2
COS MACO G R R F
MACOD G L L F
COSH MACH G R R F
CURRENT inline SU SUPS
DETACH CPDT G P
DIGIT inline G B C
DISCRETE RDDI G I A,I R1
DRAW RDDR G B R,I R1
EMPTY SSEY SSHD B A1
EJECT IOEJ IOPF P
ENDFILE inline IOIN,IODF B
ENTIER inline G I L/R
EVTIME SUEV SUPS R A1
ERLANG RDER G R R,R,I R1
EXP MAEX G R R F
MAEXD G L L F
FIRST inline SSHD SSLK
FOLLOW SSFW SSLK - SSLG P
GETCHAR IOGC TEXT C A1
GETFRAC IOGF TEXT I A1
GETINT IOGI TEXT I A1
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-72
741111 780302 6 Lars Enderin
GETREAL IOGR TEXT L A1
HISTD RDHI G I A,I A1
HISTO RDHO G - A,A,R,R P
HOLD SUHO SUPS - R P
IDLE inline SUPS B
INCHAR IOII IOIN,IODF C I1
INFRAC IOIF IOIN,IODF I I1
INIMAGE IOIG IOIN,IODF I1
ININT IOIG IOIN,IODF I I1
INREAL IOIR IOIN,IODF L I1
INTEXT IOIT IOIN,IODF T I I2
INTO SSIT SSLK SSHD P
Integer to MACL G L I F
long real
LAST inline SSHD SSLK
LASTITEM IOLI IOIN,IODF B I1
LETTER inline G B I
LINEAR RDLI G R A,A,I R1
LINE inline IOPF I
LINESPERPAGE IOLP IOPF - I P
LOCATE IOLT IODF - I P
LOCATION inline IODF I
Long real to MACI G I L F
integer
LOWTEN TXLT G - C P
MAIN TXMN TEXT T T1
MOD inline G I I,I
MORE inline TEXT B
inline IOFI B
NEGEXP RDNE G R R,I R1
NEXTEV SUNE SUPS SUPS A1
NORMAL RDNO G R R,R,I R1
OPEN IOOP IOFI - T P
OUT SSOU SSLK P
OUTCHAR IOOC IOOU,IODF - C P1
OUTFIX IOOX IOOU,IODF - L,I,I P1
OUTFRAC IOOF IOOU,IODF - I,I,I P1
OUTIMAGE IOOG IOOU,IODF - P
OUTREAL IOOR IOOU,IODF - L,I,I P1
OUTTEXT IOOT IOOU,IODF - T P1
PASSIVATE SUPA SUPS - P
POISSON RDPO G I R,I R1
POS inline TEXT,IOFI I
PRECEDE SSPC SSLK - SSLG P
PRED SSPD SSLG SSLK A1
PREV inline SSLG SSLG
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-73
741111 780302 6 Lars Enderin
PUTCHAR TXPC TEXT - C T1
PUTFIX TXPX TEXT - L,I T1
PUTINT TXPI TEXT - I T1
PUTFRAC TXPF TEXT - I,I T1
PUTREAL TXPR TEXT - L,I T1
RANDINT RDRA G I I,I,I R1
RANK inline G I C
RESUME CPRS G - O P
SETPOS TXSE TEXT - I P
TXSE IOFI (6) - I P
SIGN inline G I R/L
SIN MASI G R R F
MASID G L L F
SINH MASH G R R F
SQRT MASQ G R R F
MASQD G L L F
STRIP TXST TEXT T T A1
SUB TXSU TEXT T I,I A1
SUC SSSC SSLG SSLK A1
TAN MATA G R R F
TANH MATH G R R F
TERMINATED inline SUPS B
Text assignment TXVA G - T,T T4
Text relation TXRE G B T,T T4
TIME inline SU R
UNIFORM RDUN G R R,R,I R1
WAIT SUWA SUPS - SSHD P
** (power) MARR G R R,R F
MALL G L L,L F
MARI G R R,I F
MALI G L L,I F
Notes:
Type codes used: B=Boolean, C=character, A=real array, L=long
real, I=integer, O=ref(any class), R=real. SUPS etc - see note
(2).
(1) Fixup is the identifying code given to the symbol by the
initial expansion of the RTSYMBOLS macro in SIMMCR. Values <
400000 octal are used as fixup numbers for external lowseg
references. Values > 400000 are used as absolute addresses in
the high segment, referring to the transfer vector in SIMRn0
(SIMRn1 and SIMRn2).
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-74
741111 780302 6 Lars Enderin
(2) If the access code is G, the procedure is available in any
SIMULA program and not an attribute. Procedures marked SU are
available only in SIMULATION blocks. TEXT signifies a text
attribute, and the other four-letter codes signify attributes to
the corresponding classes:
FILE (IOFI), INFILE (IOIN), OUTFILE (IOOU), DIRECTFILE (IODF),
PRINTFILE (IOPF), LINKAGE (SSLG), LINK (SSLK), HEAD (SSHD),
PROCESS (SUPS).
(3) Calling sequences:
In all cases but F (FORTRAN sequence), parameters are in
successive ac's starting with the current top of stack ac,
called Xtop. For pure procedures and for most function calls,
Xtop=XWAC1. Most procedures are optimized for this case and are
coded to place the parameters in standard ac's before processing
and restore ac's on exit. In the case of text and class
attributes, the first actual parameter (in Xtop and Xtop+1) is
the class or text reference. The result is placed in Xtop
(+Xtop+1) or where Xtop points.
A1 is used for most functions which are attributes of a class or
of TEXT:
[load address of top ac to XTAC]
[object reference in Xtop or text reference in Xtop and
Xtop+1]
PUSHJ XPDP,f
where f is the function fixup code.
A2 is used for a global function when garbage collection may
occur:
[Any arguments to Xtop, Xtop+1 etc]
PUSHJ XPDP,f
XWD n,admap
where n is Xtop-XWAC1 and admap points to a bit map showing
which ac's XWAC1 etc contain pointers. Admap is zero if n is
zero.
F is the calling sequence used for arithmetic functions taken
from the FORTRAN library and for TAN (copied from ALGLIB):
[Put the first parameter in .YFARG]
[any second parameter in .YFAR2]
MOVEI XFP,.YFADR
PUSHJ XPDP,f
(D)MOVE Xtop,X0
where XFP=X16, and .YFADR, .YFADR+1 have the addresses of
SIMULA FOR DEC SYSTEM 10 TD, RTS III.1-75
741111 780302 6 Lars Enderin
.YFARG, .YFAR2.
I1 is used for certain I/O functions:
[File ref in Xtop]
[parameters in Xtop+2, Xtop+3, ...]
MOVEI XTAC,Xtop
PUSHJ XPDP,f
Note that Xtop+1 is not used. Xtop.image.pos is affected.
I2 is similar to A2, with a file reference in Xtop, first
parameter in Xtop+1.
P is the sequence for a pure procedure statement:
[object reference or first parameter in XWAC1]
[Rest of parameters in XWAC2, ...]
PUSHJ XPDP,p
where p is the procedure address.
P1 is used for output editing procedures:
[File ref in XWAC1]
[parameters in XWAC3, XWAC4, ...]
PUSHJ XPDP,p
T1 corresponds to P1 for text editing, with XWAC1 a pointer to a
text descriptor (ZTV instance).
R1 is used for random drawing functions. As A1 except that the
last integer parameter (random stream number) must be an integer
variable (possibly value parameter).
(5) The interpretation of "NAME" for the 3 first parameters is
"address of cell".
(6) <file ref>.setpos is implemented as <file ref>.image.setpos.
CHAPTER 2
SIMULA FOR DEC SYSTEM 10 TD, RTS
III.2 RTS DECOMPOSITION
The RTS is coded as several source modules, each containing one or more
RTS subroutines or system class prototypes. The source modules, when
compiled by MACRO-10 together with the required UNIVERSAL and other
parameter files, yield REL files which are combined into:
1) SIMLIB.REL, created by FUDGE2 (or MAKLIB) from those REL files
compiled with a zero origin (relocatable) and thus meant for the low
segment, plus some chosen routines from SYS:FORLIB.
2) SIMRTS, the high segment, which may exist as SIMRn0.EXE (n = SIMULA
version number, e.g. 4) in a one high segment version, or more commonly
as
2a) SIMRn1.EXE, containing the most frequently used high segment
routines. Created by LOAD - SSAVE.
2b) SIMRn2.EXE, which contains routines for program initialization, file
creation and initialization. Created by LOAD - SSAVE. SIMRn1 and
SIMRn2 are not in core simultaneously. The transfer from one to the
other is handled by the transfer vector and the OCSW routine (see
III.1.6.2). Some routines are included both in SIMRn1 and SIMRn2.
3) SIMDDn.ABS, containing self-relocating code for the debugging
sub-system. Created by executing SUTABS.REL loaded with SIMDDT.REL.
4) SIMHGH.REL, containing the same REL files as used for creating
SIMRn0.EXE (those marked 0 or 1,2 in III.2.2). To be used for debugging
or for loading a SIMULA program (partly) in the high segment.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.2-1
III.2.1 SIMLIB components
-----------------
Module Global symbols
OCSP .OCSP
PHPT .PHPT
MA .MACI .MACL
RDDI .RDDI
RDDR .RDDR
RDER .RDER
RDHI .RDHI
RDHO .RDHO
RDLI .RDLI
RDNE .RDNE
RDPO .RDPO
RDNO .RDNO
RDRA .RDRA
RDUN .RDUN
TAN TAN.
SU .SUSI
SS .SSST
SANE .SANE
PHFO .PHFO
[The following routines are taken from SYS:FORLIB]
ACOS. ACOS.
ASIN. ASIN.
ATAN. ATAN.
SQRT. SQRT.
SINH. SINH.
COSH. COSH.
TANH. TANH.
EXP1 EXP1. EXP1.0 EXP1.2 EXP1.4 EXP1.6
EXP3 EXP3. EXP3.. EXP3.0 EXP3.2 EXP3.4 EXP3.6
EXP2 EXP2. EXP2.. EXP2.0 EXP2.2 EXP2.4 EXP2.6
EXP. EXP.
ALOG. ALG10. ALOG.
SIN. COS. COSD. SIN. SIND.
DEXP.2 DEXP.2 DEXP2.
DEXP.3 DEXP.3 DEXP3.
DEXP. DEXP.
DLOG. DLG10. DLOG.
DSQRT. DSQRT.
DSIN. DCOS. DSIN.
DATAN DATAN.
FORXIT EXIT
SIMULA FOR DEC SYSTEM 10 TD, RTS III.2-2
CFRXIT CEXIT.
EXIDOT EXIT.
OCSP is loaded with all SIMULA main programs, the others on demand by
library search. OCSP loads the initial high segment.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.2-3
III.2.2 SIMRTS components
-----------------
The following is contained in SIMRTS:
Module Segment Global symbols
SIMRTS 0 .IODF .IOFI .IOIN .IOOU
.IOPF .PDERR
SIMRT1 1 .IODF .IOFI .IOIN .IOOU
.IOPF .OCSW .PDERR
SIMRT2 2 .IODF .IOFI .IOIN .IOOU
.IOPF .OCSW .PDERR
CS 1 .CSCA .CSEN .CSEP .CSER
.CSES .CSEU .CSGO .CSNA
.CSQU .CSRA .CSSA .CSSA.
.CSSB .CSSC .CSSN .CSSW
.CSSW0
CSSADM 2 .CSRA .CSSA.
CP 1 .CPCA .CPCD .CPCI .CPDT
.CPE0 .CPNE .CPPD .CPRS
.CPSP
IO 1 IODF%D IODF%I IODF%M IODF%S
IODF%Y IOFI%D IOFI%I IOFI%M
IOFI%S IOFI%Y IOIN%D IOIN%I
IOIN%M IOIN%S IOIN%Y IOOU%D
IOOU%I IOOU%M IOOU%S IOOU%Y
IOPF%D IOPF%I IOPF%M IOPF%S
IOPF%Y .IOBO .IOCS .IOCL
.IOCLA .IOCS .IOEJ .IOFD
.IOIG .IOLI .IOLN .IOLP
.IOLT .IONB .IOOG .IOOP
.IORB .IOSP
IOED 1 IOTXR .IOIC .IOIF .IOII
.IOIR .IOIT .IOOC .IOOF
.IOOI .IOOR .IOOT .IOOX
IONF 2 .IOCF .IOCOM .IOENT .IOLOK
.OCINE .OCINK
PH 1 .PHCV .PHFA .PHFM .PHFS
.PHFT .PHFV
SA 1,2 .SAAB .SAAR .SACL .SADB
.SADE .SAGC .SAGI .SAIN
.SANP
TX 1 .TXCY .TXDA .TXGC .TXGF
.TXGI .TXGR .TXLT .TXMN
.TXPC .TXPF .TXPI .TXPR
SIMULA FOR DEC SYSTEM 10 TD, RTS III.2-4
.TXPX .TXRE .TXSE
TXBL 1,2 .TXBL .TXST .TXSU .TXVA
OCIN 2 YOCSWL .OCIN .OCIN4 .OCIN5
.OCIN6 .OCIN7 .OCINB .OCINF
.OCINI .OCINJ .OCINY .OCINZ
OCIO 1,2 .IOERF .IOFER .IOTYS .OC8T
.OCDT .OCIN1 .OCIN2 .OCIN8
.OCIN9 .OCINC .OCIND .OCING
.OCINH .OCLA .OCOO
OCEP 1 .FORER .FOREX .OCEI .OCEP
.OCLD .OCTR .OCUU
REL:HELPER.REL 2 .HELPR
Modules marked 0 are only used in the one high segment version
SIMRn0.EXE. Those marked 1 are used in SIMRn1.EXE, those marked 2 in
SIMRn2.EXE. All modules except CSSADM.REL, SIMRT1.REL and SIMRT2.REL
are used in SIMRn0.EXE.
CHAPTER 3
SIMULA FOR DEC SYSTEM 10 TD, RTS
III.3 LOW SEGMENT ORGANIZATION
Normally (1), the low segment of an executing SIMULA program contains:
1) The compiled code of the SIMULA main program.
2) Code for any external classes or procedures, possibly compiled by
MACRO-10 (or an equivalent processor, e g BLISS) or FORTRAN.
3) RTS routines loaded from SIMLIB by library search. OCSP is loaded
with all SIMULA programs, the other routines are loaded as needed.
4) If SIMDDT is loaded directly at the start of execution (DEBUG or LOAD
- REENTER), it occupies the space directly following the last routine
loaded by LINK-10 or LOADER.
5) The so-called STATIC area is allocated next. See SIMRPA. The static
area is addressed by loading the right half of .JBOPS to a register,
usually called XLOW (default XLOW=X16) and using the symbols declared
via the STATIC macro in SIMRPA as offsets. The RTS stack based on XPDP
is part of the static area.
6) The dynamic low segment area starts with
6a) an area for buffers and buffer headers,
6b) the IOSPEC table,
6c) more buffers if needed.
See IO.MAC for table layouts and record definitions.
--------------
(1) Part or all of the program can also be loaded in the high segment if
a shared SIMULA program is desired or if the program is very big and
more space in the low segment is needed for data. See SIMHGH.HLP. Also
useful for debugging the RTS.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.3-1
7) The storage pool for dynamically allocated objects is at the end of
the low segment. SIMDDT and its work areas may be allocated in the pool
if not loaded at program start.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.3-2
III.3.1 Low segment layout
------------------
------------------------- <--- 0
! JOBDAT area !
!-----------------------! <--- 140 (octal)
! main !
! program !
!-----------------------!
! external procedures !
! and classes !
!-----------------------! <--- OCSP
! RTS !
! routines !
!-----------------------! <--- YOCDDT if non-zero
. (SIMDDT if loaded) .
:-----------------------: <--- .JBSA, .JBOPS
! Static area !
!-----------------------! <--- YOCBST
! Initial buffer !
! area !
!-----------------------! <--- YIOSPC
! IOSPEC table !
!-----------------------!
! Buffer area !
! continued !
!-----------------------! <--- YSABOT
! Storage pool !
! for SIMULA !
! objects !
! - - - - - - - - - - - ! <--- YSATOP
! Unused part of !
! pool !
!- - - - - - -! <--- YSALIM
! Space for a ZAC obj. !
------------------------- <--- .JBREL
CHAPTER 4
SIMULA FOR DEC SYSTEM 10 TD, RTS
III.4 RTS INTERFACE
The RTS interfaces with a) the user, b) the monitor and file system, c)
the compiled program. Within the RTS, there are interfaces d) between
low and high segment, e) between SIMDDT and the rest of the RTS.
III.4.1 RTS interface with the user
---------------------------
The user communicates with the RTS by the following means:
- The user TTY, which is used by the RTS for error messages and other
diagnostics, for the file initialization dialogue if specified
(III.1.7), to receive SIMDDT commands, etc. The TTY is used both as
SYSIN and as SYSOUT if no other specification has been given.
- A specification file may be read if the /R switch is given at
compile-time. See III.1.7.
III.4.2 RTS interface with monitor and file system
------------------------------------------
This is described mainly in III.1.6 and III.1.7.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.4-1
III.4.3 RTS interface with compiled program and internally
--------------------------------------------------
SIMRTS, the high segment of RTS, interfaces with the compiled program
via the transfer vector and the static area. The low segment of the RTS
interfaces with compiled program via global symbols and the static area.
III.4.3.1 Low segment - high segment interface
Since the high segment (SIMRTS) is created independently of any low
segment that is present at run time, communication between the segments
must go through fixed addresses or via a base register and fixed
offsets. Both methods are used, as explained below.
III.4.3.1.1 References to high segment from low segment
High segment routines are called via a transfer vector, consisting of
JRST and PUSHJ instructions. The transfer vector is created by
expansion of the RTSYMBOLS macro, with a suitable definition of the
macro which is called for each entry. No global variables are placed in
the high segment.
III.4.3.2 References from the high segment to the low segment
The (static) area for global variables and tables is placed at the
initial .JBFF location. .OCSP saves the address of the global area in
.JBOPS, right half. When referring from either the high or the low
segment to those global locations, a base register must be used, which
is loaded by a HRRZ instruction from .JBOPS when needed. The symbolic
name of that register should always be XLOW. The actual value of XLOW
may change throughout the run time system, but usually XLOW=XFP is used.
The global variables are thus always indexed by XLOW.
Some low segment data must be loaded together with the SIMULA program.
These are:
* Pseudo or extended accumulators which are global locations
defined at load time, with the names .YXA1, .YXA2, etc. The compiler
refers to those locations by consecutive fixup numbers, which are
translated to external references. In order to have access to those
locations also from the high segment, the address of .YXA1 must be
placed in the static area based on XLOW. YXACAD(XLOW) contains that
address.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.4-2
* Address and value list for communication with FORTRAN library
subroutines, e g SIN, COS, and the exponentiation routines. The address
list consists of two words at address .YFADR. Those words have the
addresses of the two doublewords .YFARG and .YFAR2. When calling, e g,
the SQRT function, the argument is placed in .YFARG and XFP is made to
point to .YFADR, before executing the PUSHJ. As an example, the
following calling sequence is generated for the statement y:=sqrt(x):
MOVE XWAC1,x
MOVEM XWAC1,.YFARG
MOVEI XFP,.YFADR
PUSHJ XPDP,SQRT. (fixup MASQ in RTSYMBOLS)
MOVE XWAC1,0
MOVEM XWAC1,y
III.4.3.3 References from the RTS to the compiled program
SIMDDT uses the main line number table address to find line number and
symbol tables for the main program and any external procedures or
classes. The RTS stack, starting at YOBJRT of the static area, is used
for referring to compiled code in several RTS routines and in SIMDDT.
.JBSA points either to .MAIN or .OCRE0 (DEBUG command). The data area
for the outer program block and its display vector are placed in
compiled code. Program objects (subblocks, procedures, classes,
prefixed blocks) refer to compiled code via the prototype pointer.
Other blocks may also contain references to compiled code. The
SIMULATION or SIMSET block level is defined by global symbols (see
III.10).
III.4.3.4 Access to SYSIN, SYSOUT objects, to SIMULATION block
The SYSIN file object address is found at offset YSYSIN in the static
area. Code is compiled to load an ac from .JBOPS before accessing
SYSIN. Access to SYSOUT is via YSYSOUT. In a SIMULATION program,
YSULEV contains information (MOVE XSAC,offset of simulation block
address in current display) to find the SIMULATION block. Since these
three offsets are used by compiled code, they must not be changed unless
absolutely necessary (old SIMULA rel files will be useless).
CHAPTER 5
SIMULA FOR DEC SYSTEM 10 TD, RTS
III.5 COMMON MACRO PARAMETER FILES
MACRO-10 modules in the RTS refer to the UNIVERSAL files SIMMAC.UNV,
SIMMCR.UNV and SIMRPA.UNV, created from the corresponding .MAC files.
SIMMAC is described elsewhere (I.6). SIMMCR contains information used
at code generation, chiefly record definitions for static and dynamic
records used at run time. SIMRPA contains additional definitions used
mostly at run time but also for code generation in some cases.
III.5.1 UNIVERSAL SIMMCR
----------------
SIMMCR contains the following:
- Definitions of register names XIAC, XFP, XCB, XSAC, XTAC, XRAC, XRAC1.
- TYPZDN macro, used to define the constants for run-time dynamic record
discrimination (ZDNTYP field) and also in the garbage collector to
define a jump table for record processing. The last tag value used,
QZDNTM, is defined.
- RTS error codes used at compile time.
- Parameter descriptor codes used in ZFL and ZAP records.
- Record definitions (DR, DF) for dynamic records ZDN, ZBI, ZBP, ZCL,
ZPB, ZTE, ZTT, ZAR, ZAC, ZER, ZDR, ZYS, ZXB, ZTV, ZDV, ZDS, ZLD, ZDL,
ZDA, ZRV, ZDP, ZFL, ZSU, ZEV, ZLG, ZPS, static records ZPR, ZPC, ZCP,
ZMP, ZSL, ZSR, ZTD, ZPD, ZFP, ZFR, ZAP, ZLN, ZSD, ZSM, ZTH and
miscellaneous definitions: ZTS (thunk save area), YFOFAD, YFOAAD,
YFOPAD.
- The RTSYMBOLS macro, which gives values to most symbols used to access
RTS routines and system class prototypes. The entries in the RTSYMBOLS
macro are calls of an X macro, used for procedure entries, and a Y
macro, used for prototypes. The X macro is invoked:
X(ROUT,SEG,SIM,N)
SIMULA FOR DEC SYSTEM 10 TD, RTS III.5-1
ROUT is the mnemonic used for the entry. SEG is L (low segment), 1
(SIMRn1), 2 (SIMRn2) or 3 (both SIMRn1 and SIMRn2). An empty second
parameter stands for 1. SIM is the letter S if the symbol has a SIMULA
name (exists in initial symbol table), empty otherwise. N, if present,
gives the global name to be used for the entry point to the routine,
otherwise the global name is formed by prefixing ROUT with a dot.
The Y macro is invoked:
Y(PROT,SEG,SIM,F)
PROT corresponds to ROUT. If SEG is 1,2 or 3, the prototype will be
expanded in the transfer vector directly to be accessible to compiled
code via PROT. The initial expansion reserves space for the prototype
to get the correct values of the following entries. F, if present,
shows the size of the variable part of the prototype (after the fixed
ZPC part, i e parameter descriptors for formal parameters). RTSYMBOLS,
when expanded with the initial definitions of X and Y, defines fixed
high segment addresses if SEG=1,2 or 3, consecutive fixup numbers
starting with 1 if SEG=L. The high segment addresses are used directly
in compiled code as entry addresses to RTS procedures and prototypes.
The fixup numbers are coupled with an external symbol table defined in
PASS 3 of the compiler by another expansion of RTSYMBOLS (with X and Y
redefined). In the SIMRTS module used to produce SIMRTS.REL, SIMRT1.REL
or SIMRT2.REL, another expansion of RTSYMBOLS produces the transfer
vector used at run time. RTSYMBOLS also defines fixup numbers for
pseudo ac's and the FORTRAN subroutine interface cell - .YFADR, .YFARG,
.YFAR2. A readable representation of RTSYMBOLS is produced by
compilation (with listing) of the following MACRO-10 code:
TITLE RTSYMBOL VALUES
SEARCH SIMMAC,SIMMCR
IF2,<END>
DEFINE XX(NA,VAL,S1,EN)<
PRINTX NA VAL S1 EN
>
DEFINE X(ROUT,S,DUM,N)<
IFNB <N>,<XX(ROUT,\ROUT,S,N)>
IFB <N>,<XX(ROUT,\ROUT,S,.'ROUT)>
>
DEFINE Y(PROT,SEG,S,F)<
XX(PROT,\PROT,SEG,.'PROT)
>
PRINTX SYMBOL VALUE SEG ENTRY
PRINTX ------------------------------
RTSYMBOLS
END
SIMULA FOR DEC SYSTEM 10 TD, RTS III.5-2
III.5.2 UNIVERSAL SIMRPA
----------------
SIMRPA contains definitions needed mostly in the RTS and in some
compiler modules.
III.5.2.1 SIMRPA macros
The following macros are defined:
LOWADR(X) - defines XLOW=X and loads XLOW from .JBOPS.
SETLOW(X) - defines XLOW=X, does not change X.
IFNONE(X) - skips if X==NONE.
TRIMSTACK - removes top of XPDP stack.
ERRMAC(A) - defines the error message macro to be used in component A
(A'ERR).
RIGHTHALF(A) - compile time message if A is not a right half field,
where A is a field designator.
SAVEALLACS - All ac's are saved at offset YUUOAC of the static area.
CALLOW, CDEFER, CENABLE, CFORBID - control ^C-REENTER SIMDDT interface
(see III.1.6.2.3.3).
TEXT(T), RTEXT(T), RRTEXT(T) - used for garbage collector debugging.
ERRCODE(N0,A) - Defines the initial error number used in module A,
Q'A'ENO=N0.
RTSMODULE(M,M1,SEG) - Defines TITLE, ERRMAC(M), high or low segment
relocation.
PROCINIT(A) - Defines declarations for IO, OCIO, OCIN modules when
expanded. A is module name.
RDINIT(e) - Defines macros and initial info for submodule RD'e of RD.MAC
(submodules are separated by PRGEND).
DCLASS(NAM,...) - Defines D%'NAM (prototype macro) for the standard
class with index code NAM, e g IOFI (FILE).
SIMULA FOR DEC SYSTEM 10 TD, RTS III.5-3
DSZCML - Defines symbol table record (ZSM) for a standard class.
DZSD - Defines symbol table entry for local quantity.
SYSCLASS - Used to define codes QCLPB, QSUSI, QSSLG, QSUPS, QIOFI for
the ZCPGCI field in the prototype. Used by garbage collector to
indicate special relocation. SYSCLASS is used there to define a jump
table.
III.5.2.2 Constants defined in SIMRPA
Alternative ac names are defined. Compile time constants like QIOLP
(default LINESPERPAGE value). Entry point offsets for SIMDDT.
Constants referring to monitor tables, FORTRAN error codes, interrupt
conditions.
The offsets in the STATIC area are defined via the STATIC macro. These
offsets begin with the letter Y.
III.5.2.3 Record definitions in SIMRPA
The following records are defined:
ZFS, ZFI, ZIF, ZOF, ZPF, ZDF, ZBH, ZSW, ZBU, ZYS as SFD block, ZXB, ZFD.
III.5.2.4 Switch definitions in SIMRPA
Switches used in OC, IO and SA modules are defined.
CHAPTER 6
SIMULA FOR DEC SYSTEM 10 TD, RTS
III.6 TESTING
Special debugging tools have been developed for the I/O subsystem (see
I.10, test standard), and the garbage collector (SAGC, III.6.2). For
the rest of the RTS, the standard debugging tool, DDT has been used.
SIMDDT can also be used (in conjunction with DDT). At present (version
4 of SIMULA) the debugging tools for SAGC cannot be used, however.
III.6.1 Debugging with DDT
------------------
III.6.1.1 Debugging using rel files for all RTS components
DDT debugging is simplified if all REL files both for low and high
segment are available. In this case the required files are loaded
directly and possibly saved as an EXE file. SIMLIB may be used in
library search mode. Note that local symbols are not available for
routines in SIMLIB. If all required rel files are loaded directly with
DDT via a DEBUG command, breakpoints may be set anywhere before starting
the program. The following command sequence may be used:
.DEBUG SIMPRO.SIM,/REL REL:SIMHGH.REL,REL:HELPER.REL
[set breakpoints]
^[G (or .OCRE0^[G if SIMDDT start is wanted)
[execution]
where ^[ stands for <altmode> and SIMHGH.REL contains the modules
SIMRTS, CS, CP, IO, IOED, OCIN, OCIO, PH, SA, TX, OCEP. The REL files
from SIMHGH.REL may also be loaded separately. SIMRTS.REL (the
one-segment version) must always be the first module in the high
segment. If possible, REL files compiled with QDEBUG=1 and QSYS=0
should be used (see implementation guide). For complete garbage
collector debugging, SADEB.REL must be included. See III.6.2. If
SIMULA FOR DEC SYSTEM 10 TD, RTS III.6-1
execution is made to start in SIMDDT, DDT may be entered by typing ^C
when a command is expected, then issuing the DDT command. Control is
returned to SIMDDT by executing "JRST 2,@.JBOPC^[X" and then typing a
SIMDDT command. Note that SIMDDT may be used to force a garbage
collection via the VARIABLES command. This is useful when a garbage
collection error is expected. See III.6.2 for ways to dump SIMULA
objects and to trace garbage collector actions.
III.6.1.2 Debugging the SYS version of the RTS
Debugging the SYS version of the RTS high segment is rather difficult.
If possible, the rel files should be used as described in III.6.1.1.
With DDT, breakpoints can be set in the low segments without difficulty,
but breakpoints cannot be set in the high segment at all if the SHR
files from SYS are used at user level. One possible way is to GET and
SAVE SIMRn1 and SIMRn2 from SYS, creating unsharable EXE files on the
user area, then load the program with DDT (DEBUG/D SIMPRO) and SAVE it,
then ASSIGN DSK SYS (after setting the SYS switch via SETSRC). If
breakpoints must be placed in SIMRn1, set a breakpoint at .MAIN+6, then
set the required high segment breakpoints after stopping at .MAIN+6. It
is also possible to start in SIMDDT and enter DDT at a breakpoint as
shown above. If breakpoints in SIMRn2 are needed, set a breakpoint at
.OCSP+73 (may be changed, check for JRST 400047) and start. SIMRn2 is
then in core. If you need to set breakpoints at other invocations of
SIMRn1 or SIMRn2 than the first one, patches must be made in the high
segment. It is possible e g to place "EXIT 1,", which works as ^C, in a
high segment location, noting the replaced instruction. If the replaced
instruction is is HRRZ 16,.JBOPS (LOWADR), it may be redundant,
otherwise the replaced instruction has to be executed in DDT explicitly
(^[X command) before returning via .JBOPC as shown above. This
debugging mode should not be used unless it is necessary to reproduce an
error. If the error can be shown to occur when all rel files are
loaded, debugging should be done as in III.6.1. If the SYS version has
only one high segment, debugging is somewhat simplified.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.6-2
III.6.2 Testing facilities in the garbage collector
-------------------------------------------
WARNING
The testing facilities are currently
(version 4) not usable.
In the test version (QDEBUG=1, QSYS=0), the garbage collector (SAGC,
shortened as GC) processing can be traced. The global cell at offset
YSASW in the static area contains 5 switches to determine the amount of
test output produced. The switches are:
Switch bit no Meaning
SAGCPE 0 1 if no output on nnnGCP.TMP
SWGCTE 1 1 for test output from GC
SWGCT2 2 1 for test output on TTY
SWGCT3 3 1 for test output on SYSOUT
SWGCT4 4 1 if GC runtime and low seg limit
should be logged.
If SAGCPE is off, the GC parameters used in the storage allocation
algorithms are output in append mode on the file nnnGCP.TMP after each
garbage collection, where nnn is job number. The data on this file can
be analysed by the utility program SUTGCA (see chapter V). SAGCPE is
set off by default if QDEBUG=1. Initialization is done by .SAGI, which
opens the file. SAGCPE is set off if I/O errors occur on the file.
If SWGCTE is on, the test version logs GC actions. In PHASE1 the start
addresses of all chained records are output. In PHASE2 all referenced
records in the pool are logged with old address, new address, record
length given. In PHASE3 all updated pointers are given with old and new
values. Finally, in PHASE4, the old address, new address, and length
for each moved record are output. SWGCTE is off by default.
SWGCT2 and SWGCT3 specify the output destination for test output.
Default is TTY (SWGCT2 and NOT SWGCT3).
If SWGCT4 is set a short log message is given on each GC execution.
SIMULA FOR DEC SYSTEM 10 TD, RTS III.6-3
The default switch settings can be changed by patching the .SAGI
routine. The appropriate bits in the first instruction compiled for
SETON SWGCT2(XLOW) can be set. The bits may also be changed in
YSASW(XLOW) at a DDT breakpoint.
The SADEB.MAC module contains a number of dump routines to be used for
GC testing as well as the output routines for logging as specified
above.
.SAPD dumps the whole object pool.
SAPDRE dumps a single record in the pool.
.SQSDU dumps the sequencing set of SIMULATION (SQS).
The routines are invoked by the ^[X command in SIMDDT, executing a PUSHJ
17,r instruction, where r is the appropriate routine.
When calling SAPDRE, XCUR==X6 must contain the start address of the
record. For easier handling of the dump routines, note that the DDT
command "PUSHJ 17,.SAPD<PD:", for example, defines PD as PUSHJ 17,.SAPD.
Thus PD^[X may be used to get a pool dump.
CHAPTER 7
SIMULA FOR DEC SYSTEM 10 TD, RTS
III.7 SAMPLE PROGRAM
As an illustration of what happens at run time, the execution of the
following SIMULA program is analysed in some detail, referring to line
numbers as allocated by the compiler:
B1 1 BEGIN
2 CLASS pb1;;
B2 3 pb1 BEGIN
4 CLASS c1;
B3 5 BEGIN
6 CLASS c2;
B4 7 BEGIN
8 detach;
9 rc3:-NEW c3;
10 resume(rc3);
E4 11 END c2;
12 CLASS c3;
B5 13 BEGIN
14 detach;
E5 15 END c3;
16 REF(c2)rc2;
17 REF(c3)rc3;
18 CLASS pb2;;
19 rc2:-NEW c2;
20 detach;
B6 21 pb2 BEGIN
22 CLASS pb3;;
B7 23 pb3 BEGIN
24 resume(rc2);
E7 25 END pb3;
SIMULA FOR DEC SYSTEM 10 TD, RTS III.7-1
E6 26 END pb2;
E3 27 END c1;
28 REF(c1)rc1;
29 rc1:-NEW c1;
30 resume(rc1);
31 resume(rc1);
E2 32 END pb1;
E1 33 END program;
Tracing with SIMDDT gives the following execution order by source line
number: 3, 2, 29, 19, 8, 20, 30, 21, 18, 23, 22, 24, 9, 14, 10, 15, 31,
25, 26, 27, 32.
This is explained as follows:
Start before line 1 at the entry point .MAIN given by .JBSA. Call OCSP,
which swaps in SIMRn2, transfers control to OCIN for initialization
(SYSIN and SYSOUT setup etc). OCIN transfers control to .OCEI via the
transfer vector in SIMRn2, swapping in SIMRn1 to replace SIMRn2 (.OCSW).
OCEI returns to compiled code.
CSER is called to initialize the reduced subblock starting at line 1,
using .SAIN to initialize data according to subblock map.
At line 3, CPSP, using SADB and .SAIN, sets up the prefixed block with
its display vector and dynamic link. CSEN is called to start
declarations in the prefix (ZPCDEC of the pb1 prototype) then via CPCD
to ZPCDEC of the prefixed block, then via CPPD to line 2 (statements of
the prefix), continuing via CPCI (implicit inner) to ZCPSTA of the block
(line 29).
At 29 a c1 object is generated and entered: CPNE [SADB [.SAIN] CSEN] -
ZPCDEC - CPCD - ZCPSTA (line 19).
At 19, create c2 like c1, ending up at line 8.
At line 8, detach (CPDT) detaches c2 and returns the reference to the
caller, continuing at line 20, where c1 is detached, returning to line
30.
At line 30, resume (CPRS) of c1 leads to the reactivation point at line
21.
At line 21 a prefixed block again starts via CPSP, CSEN, prefix class
(line 18), continuing at line 23, where a new prefixed block is started
SIMULA FOR DEC SYSTEM 10 TD, RTS III.7-2
(lines 22, 24).
At line 24 c2 is resumed at its reactivation point line 9. C3 is
resumed (line 14) and detaches to line 10.
At line 10, c2 terminates via CPE0. CPE0 calls CPDT, leading to the QPS
reactivation point at line 15, where c3 terminates, detaching to line 31
of the surrounding prefixed block. The resume (CPRS) at line 31 leads
to line 25 in the innermost prefixed block via operating chain and back
down via dynamic links.
The prefixed blocks terminate in turn via CPE0 and ZCPIEA links: lines
25, 26. C1 terminates via CPE0 and CPDT, leading to line 32, where the
pb1 prefixed block terminates via CPE0 and ZCPIEA.
OCEP terminates program execution, closing files via .IOCLA and .IOCL.
Returns to monitor level via EXIT 1,.