Index | PAL Intro | Commands | Registers | Indices | Stack | Macros | Classes | Attributes | Errors
reg/load() - Iterate a data table
Synopsis
Description
Indirect Addressing
Error Handling
Examples
See Also
Author
reg/load write, (#table)
reg/load write, (readtab)
reg/load write, (readtab, #index)reg/load write, (#table, #index)
When a PROSE binary is generated by the prism assembler, a number of data tables are stored inside the binary file (see pal_intro(5)).
Two of these tables can be read using the reg/load indirect addressing functionality. These tables are:
To iterate a data table, first a data table read structure is initialised. Then successive calls can be made to read consecutive data values or specific index positions. Finally use reg/clr to clear the read structure and release memory associated with it.
Code Addresses Identified by a table argument of #0, the code addresses table contains a list of addresses that are associated with code labels. The first code label defined or referenced in the PAL source file will be the first address in this table (index 0). Use reg/index to convert a code label of choice to an index number. Data Xref Table Identified by a table argument of #1, the data cross-reference table contains a list of data segment addresses that are associated with data labels. The first data label defined or referenced in the PAL source file will be the first address in this table (index 0). Use reg/index to convert a data label of choice to an index number. In the first synopsis form above a data table read structure is initialised. This structure describes the position within a data table and is stored in the write argument (type PSUNIT_TYPE_READTAB).
In the second synopsis form, returns in the write argument the next data item in the table (a code pointer if table was 0 and a data segment pointer if table was 1). The readtab argument is a pointer to an initialised data table read structure.
In the third synopsis form, a specific data table value can be requested using the raw index number index. The first data item in the table is identified by #0, the next is #1 and so on. The index position requested is located using a mathematical operation and therefore data table values can be read in any order without any loss of efficiency (as opposed to reading data segments for example, which require seeking).
In the fourth synopsis form an index is supplied with a table identifier. No data table read structure is required, instead a single lookup is performed. This form is more efficient than the previous forms and also matches the syntax used by local/jsr and local/jmp with indirect addressing (see local_jmp(5)). However it always requires a specific index to lookup.
If an attempt is made to read beyond the end of a data table, a NULL value is returned in the write argument.
Using parentheses ( ) with the reg/load instruction invokes the indirect addressing behaviour described above when the initialisation command is provided with a raw index (the table argument).
See the reg_load(5) manual page for a description of other functionality available with this command.
A runtime error is generated if a table argument is not #0 (for code addresses) or #1 (for data segments).
The following example uses the code address table to call a number of local routines in order:
See local_jmp(5) for an even more efficient version of the above code.
.sub1 obj/dump [Running .sub1] local/rtn
.sub2 obj/dump [Running .sub2] local/rtn
.sub3 obj/dump [Running .sub3] local/rtn
.main % Read index position for .sub1 in code table reg/index PUSH, &[.sub1]
% Open the code addresses table reg/load P0, (#0)
% Read item from table using index obtained for .sub1 % and call the pointer returned reg/load P1, (P0, PULL) local/jsr P1
% Read the next item from the same table reg/load P1, (P0) local/jsr P1
% And read the next one too ... reg/load P1, (P0) local/jsr P1
% Tidy up and exit reg/clr P0 func/rtnA more efficient version of the above code uses the fourth synopsis form and requires no data table read structure. However, knowledge that .sub1 is index #0 has been hard-coded. Normally use of reg/index to obtain the correct index number would be the preferred approach. .sub1 obj/dump [Running .sub1] local/rtn
.sub2 obj/dump [Running .sub2] local/rtn
.sub3 obj/dump [Running .sub3] local/rtn
.main % Read address for .sub1 and call reg/load P0, (#0, #0) local/jsr P0
% Read next address and call reg/load P0, (#0, #1) local/jsr P0
% And read the next one too ... reg/load P0, (#0, #2) local/jsr P0 func/rtn
prism(1), pal_commands(5), pal_registers(5), pal_indices(5), reg_load(5), reg_clr(5), reg_index(5), local_jmp(5),
PROSE Assembly Language at prose.sourceforge.net.
Copyright (c) 2002-2008 Mark R. Bannister <cambridge@users.sourceforge.net>.
This is free software and can be downloaded from prose.sourceforge.net; see the source for copying conditions. There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
PAL 1.0 | reg_load_table (5) | 1 December 2008 |