PL/65 USER'S MANUAL Rockwell International (C)Rockwell International Corporation, 1978 $10.00 All Rights Reserved Document No. 29650 N37 Printed in U.S.A. November 1978 *************************************************************************** TABLE OF CONTENTS SECTION TITLE PAGE 1 INTRODUCTION 1-1 2 STRUCTURE OF PL/65 PROGRAMS 2-1 3 STATEMENT TYPES IN PL/65 3-1 3.1 Declarations 3-2 3.2 Assignment 3-3 3.3 Imperative 3-5 3.4 Specification 3-6 3.5 Conditional 3-6 3.6 Branching 3-7 3.7 Looping 3-8 3.8 Compiler Generated Labels 3-9 3.9 Page Zero Utilization 3-9 4 INSTALLATION AND OPERATION 4-1 4.1 Loading the PL/65 Compiler 4-1 4.2 Operating the PL/65 Compiler 4-2 4.3 Loading the PL/65 Optimizer 4-3 4.4 Operating the PL/65 Optimizer 4-3 4.5 PL/65 Test Program 4-4 APPENDIX A STATEMENT FORMATS A-1 A.1 ASSIGNMENT A-2 A.2 BLOCK A-4 A.3 CALL A-5 A.4 CASE A-5 A.5 CLEAR A-6 A.6 CODE A-6 A.7 COMMENT A-7 A.8 DATA A-7 A.9 DEC A-8 A.10 DECLARE A-9 A.11 DEFINE A-9 A.12 ENTRY A-10 A.13 EXIT A-10 A.14 FOR-TO-BY A-11 A.15 GO TO A-12 i *************************************************************************** TABLE OF CONTENTS (Cont.) SECTION TITLE PAGE A.16 HALT A-12 A.17 IF-THEN-ELSE A-13 A.18 IFF-THEN A-14 A.19 INC A-15 A.20 PULSE A-16 A.21 RETURN A-17 A.22 ROTATE A-17 A.23 RTI A-18 A.24 SET A-18 A.25 SHIFT A-19 A.26 STACK A-20 A.27 TAB A-20 A.28 UNSTACK A-20 A.29 WAIT A-21 A.30 WHILE A-21 APPENDIX B ABBREVIATIONS B-1 APPENDIX C ASSEMBLER EQUIVALENTS C-1 APPENDIX D SAMPLE PL/65 PROGRAMS A-1 D.1 "SORT" COMPILER INPUT D-1 D.2 "SORT" COMPILER OUTPUT D-2 D.3 "TOGGLE TEST" COMPILER INPUT D-4 D.4 "TOGGLE TEST" COMPILER OUTPUT D-5 D.5 "MONITOR SEGMENT" COMPILER INPUT D-8 D.6 "MONITOR SEGMENT" COMPILER OUTPUT D-9 APPENDIX E PL/65 TEST PROGRAM E-1 ii *************************************************************************** INDEX TITLE PAGE == statement 3-5 ACCUMULATOR B-1 AND B-1 ARRAYS 3-2, 3-4 ASSEMBLER EQUIVALENTS C-1 ASSIGNMENT 3-1, 3-3 BEGIN-END blocks 3-7 BINARY 3-2, B-1 Binary 3-5 BINARY Constants 3-3 BIT B-1 BLOCK 3-3, A-4 BRANCHING 3-1, 3-7, 3-8 Bubble sort 2-1 CALL A-5 CARRY B-1 CASE 3-7, A-5 CHARACTER A-9 CLEAR 3-5, A-6, B-1 CODE A-6 COMMENT 3-3, A-7 Compiler generated labels 3-9 Computed GO TO 3-7 CONDITIONAL 3-1, 3-6 DATA 3-2, A-7, A-8 DATAW A-8 DEC A-9 DECIMAL B-1 DECLARATIONS 3-1, 3-2 DECLARE 3-3 DECW A-8, A-9 DEFINE 3-2, A-9 ENTRY 3-6, A-10 EXCLUSIVE OR B-1 EXIT 3-6, A-10 EXPRESSIONS 3-2, 3-3 FOR-TO-BY 3-8, A-11 iii *************************************************************************** INDEX (Cont.) TITLE PAGE GO TO 3-8, A-12 HALT A-12 HEXADECIMAL 3-3, B-1 HEXADECIMAL Constants 3-4 IFF-THEN-ELSE 3-6, A-13 IFF-THEN A-14 IMPERATIVE 3-1, 3-5 INC A-15, A-16 INCW A-15, A-16 INDEX X B-1 INDEX Y B-1 Indirect GO TO A-12 INITIAL A-9, B-1 INSTALLATION 1-1 INTEGER 3-3 INTERRUPT B-1 INTRODUCTION 1-1 LABEL 3-3 Logical operators 3-3 LOOPING 3-1, 3-8 NAME 3-3 NEGATIVE B-1 OR B-1 OVERFLOW B-1 Page zero utilization 3-9 Parenthetical expressions 3-3, 3-4 PROCESSOR STATUS B-1 PROGRAM STRUCTURE 2-1 PULSE A-16 Quantifier 3-3 REGISTERS A-14 Relational operator in IF 3-6 RETURN A-17 ROL A-17 iv *************************************************************************** INDEX (Cont.) TITLE PAGE ROR A-17 ROTATE 3-1, 3-5, A18 RTI A-18 SET 3-5, A-18, A-19 SHIFT 3-1, 3-5, A-19 SHL A-19 SHR A-19 SPECIFICATION 3-1, 3-6 STACK 3-6, A-20 STACK POINTER B-1 STATEMENT FORMATS A-1 STATEMENT TYPES 3-1 Subscripts 3-4, 3-5 SUBSCRIPTS 3-3 TAB A-20 UNSTACK 3-6, A-20 VARIABLE 3-3 WAIT 3-5, A-21 WAIT ON 3-6 WHILE 3-6, A-21, A-22 ZERO B-1 v *************************************************************************** SECTION 1 INTRODUCTION A high level systems implementation language, PL/65, has been developed for use on the Rockwell SYSTEM 65 Microcomputer Development System. This document describes an implementation of that language for the R6500 family of microprocessors. The language resembles PL/1 and Algol in general form, but a large number of simplifying assumptions have been made to avoid unnecessary complexity and to ease compiler implementation. The result is a mid-level language which has the power and flexibility of Assembler and the structuring potential of a high-level language. All language features are aimed at improving the productivity of the systems programmer by simplifying the writing of systems normally written in Assembler. PL/65 compilers produce assembler code rather than object code. Thus, symbol table manipulation in the compiler is avoided. Furthermore, this allows the systems programmer to enhance or debug at the assembler language level if necessary. In fact the programmer may revert to assembler language whenever it is expedient to do so. In spite of the simplicity of the language, the systems programmer is able to structure programs for readability and logical organization without sacrificing run-time efficiency. Program logic essentially becomes self- documenting. Control structures for conditional and iterative looping and the IF-THEN-ELSE conditional coupled with a simplified block structure add greatly to the language potential for highly structured programs. This document describes the language features of PL/65. Consult Section 4 for PL/65 installation and operating instructions on SYSTEM 65. This PL/65 Language Reference Manual assumes user familiarity with pro- gramming in a high-level language. 1-1 *************************************************************************** SECTION 2 STRUCTURE OF PL/65 PROGRAMS A PL/65 program is a collection of PL/65 statements. The compiler does not impose an ordering of the program, hence the systems programmer bears the responsibility for correctly formed programs. The general structure of PL/65 programs is illustrated in the following ascending order bubble sort routine. _________________________________________________ | | | PAGE '**SORT**'; | | ; | | "ASCENDING ORDER SORT"; | | ; | | DECLARE F, I, TMP; | | ENTRY $200; | | ; | | N=N-2; "SET TERMINAL VALUE FOR LOOP"; | | F = 1; "SET FLAG"; | | WHILE F = 1 | | DO; | | F = 0; | | FOR I = 0 TO N | | BEGIN; | | IF B[I] > B[I+1] THEN | | BEGIN; | | F = 1; | | TMP = B[I]; | | B[I]=B[I+1]; | | B[I+1]=TMP; | | END; | | END; | | END; | | N: DATA 10; "N IS NUMBER OF SORT ELEMENTS"; | | B: DATA 23,55,36,28,54,39,99,86,21,67; | | ; | | EXIT; | |_________________________________________________| Example 1. ASCENDING ORDER BUBBLE SORT Programs normally start with an ENTRY statement; and terminate with an EXIT; statement. Their use is explained in later sections. The sample sort routine above shows program structures common to many high 2-1 *************************************************************************** level languages. Particular structures shown are: assignment, integer arithmetic, conditional looping (WHILE-DO), iterative looping (FOR), conditional execution (IF-THEN), collective execution (BEGIN-END), linear array manipulation, data area declaration (DECLARE), and array initializa- tion (DATA). Statements are separated by semi-colons and optional com- ments. Comments are delimited by double quotes and terminated by semi- colons. The compiler is not column sensitive so statements can be indented for readability. TABS can also be used. The following routine is design- ed for execution on an R6500. A transistor switch and relay are assumed to be connected to pin 1 of an R6522 Port B Data Register. The program cycles through an array T for a switch position (1 = on, 0 = off) and a time delay (in seconds). ___________________________________________________ | | | PAGE 'TOGGLE SWITCH'; | | ; | | DEF DRB=$A000, DDRB = $A002 | | DEF T1CL=$A004, T1CH = $A005 | | DEF ACR=$A00B, PCR = $A00C | | DEF IFR=$A00D | | DEFINE *=$10; | | DCL J,K,L; | | DCL TIME; | | ENTRY; | | UDDRB=$FF; | | ST: CLEAR ,CARRY; | | T1CL=$50 | | T1CH=$C3 | | FOR J=0 TO 10 BY 2 | | BEGIN; | | DRB=T[J]; | | TIME=T[J+1]; | | CALL DELAY; | | END; | | GO TO ST; | | ; | | DELAY: FOR K=1 TO TIME | | BEGIN; | | "FOLLOWING IS A 1 SECOND DELAY"; | | FOR L=1 TO 20 | | BEGIN; | | WHILE BIT [6] OF IFR ^=0; | | END; | | RETURN; | | ; | | "FOLLOWING IS SWITCH POSITION AND TIME DELAY"; | | DATA 1,5,0,10,1,5,0,15,1,5,0,2; | | EXIT; | |___________________________________________________| Example 2. SWITCHING WITH TIME DELAY 2-2 *************************************************************************** Assembly language generated by the compiler for the above routines is given in Appendix D. These routines were selected specifically to show some of the commonality between PL/65 and other languages. The following routine illustrates some of the features which make PL/65 unique. _____________________________________ | | | PAGE '*MONITOR SEGMENT'; | | ; | | "SEGMENT OF A MONITOR PROGRAM"; | | RST: .X=$FF; | | .S=.X; | | SPUSER=.X; | | CALL INITS; | | DETCPS: CNTN30=$FF; | | .A=$01; | | DET1: IFF BIT[SAD] THEN START; | | IFF .N THEN DET1; | | .A=$FC ; | | DET3: CLEAR .CARRY; | | .A+$01; | | IFF ^.C THEN DET2; | | CNTH30+1; | | DET2: .Y=SAD; | | IFF ^.N THEN DET3; | | CNTL30=.A; | | .X= $08; | | CALL GETS; | |_____________________________________| Example 3. SEGMENT OF A MONITOR PROGRAM This example shows some of the extended features of PL/65 using named bits and named registers. Also shown is a special form of the IF-THEN conditional statement. These features are explained in detail in later sections. 2-3 *************************************************************************** SECTION 3 STATEMENT TYPES IN PL/65 Statements in PL/65 can be grouped into seven classes: * Declaration DECLARE DEFINE DATA comment * Assignment byte move multiple byte move * Imperative SHIFT ROTATE CLEAR SET CODE HALT WAIT STACK UNSTACK INC INCW DEC DECW PULSE * Specification ENTRY EXIT * Conditional IF-THEN-ELSE IFF-THEN CASE * Branching GOTO CALL RETURN RTI BREAK 3-1 *************************************************************************** * Looping FOR-TO-BY WHILE Sections 3.1 through 3.7 provide a very general description of PL/65 statement types and their function. A more formal definition and detailed examples are given in Appendix A. In the descriptions to follow, VARIABLE refers to either a name (label) or an integer. An integer may be decimal, hexadecimal (number preceded with a '$'), or binary (number preceded with a '%'). EXPRESSION means vari- ables connected with arithmetic or logical operators. In an expression, the first term may normally be subscripted and sometimes may be indirect if that mode is not explicitly restricted. SUBSCRIPT refers to a variable or expression (which is non-indirect and non-subscripted) which reduces to a one byte value. STATEMENT is a single PL/65 statement and BLOCK refers to a group of PL/65 statements delimited with the words DO;-END; or BEGIN;-END;. 3.1 DECLARATIONS The only data types in PL/65 are bytes and linear arrays of bytes. The compiler does not verify data type and there are no implicit type conver- sions. The sole purposes of the DECLARE command are to reserve and initialize data storage. The statement DECLARE ALPHA; reserves a byte (8 bits) of storage which can be referenced symbolically by ALPHA. The statement DECLARE GAMMA BYTE INITIAL[13]; reserves a byte (8 bits) and initializes that byte to decimal 13. Areas for byte arrays and character arrays can be reserved and initialized. Sample array declaration and character array initialization are shown by the following: DECLARE IOTA[40]; DCL R CHARACTER['RAIN']; In the above example IOTA is an array of 40 bytes and there is no init- ialization. The symbol R references the first character of the string 'RAIN'. Pairs of bytes (words) can also be reserved; DCL SUB WORD[30]; reserves 30 pairs of bytes. Words can also be initialized as shown by: DCL D WORD INIT[5]; ("INIT" stands for "INITIAL".) The DEFINE statement is equivalent to an assembly language equate. The statement DEFINE J=32; defines the symbol J to have the value decimal 32. Virtually no syntax checking is done by the compiler on the DEFINE expres- sion; any string of symbols is accepted by the compiler without error. Errors in expression formation are noted at assembly time rather than at translate time. Note that the PL/65 compiler produces assembly code rather than machine code. 3-2 *************************************************************************** Arrays can be initialized with a DATA statement as in the example: MT: DATA 24, 36, 27, 54; Here, a 4 byte array named MT is defined and initialized. All arrays are zero origin. Hence, MT[0] is 24 and MT[3] is 54. Except for the facility to initialize arrays, the DATA statement serves the same purpose as DECLARE. Word arrays can be initialized with the DATAW statement. Comments in PL/65 are strings of characters delimited by double quotes as in "SET MAX VALUE TO 5";. Comments require terminating semicolons as do all other statement types. Comments may be freely used wherever state- ments can occur, but comments cannot be inserted between syntactic ele- ments of statements. Spacing of the listing may be accomplished with lines that contain only a semicolon (null statement). 3.2 ASSIGNMENT The data movement instruction in PL/65 is the assignment statement which has been enhanced to make data movement more convenient. The statement B = C; means move the byte at location C to location B. Also, B.1 = C; means move the byte at location C to location B, and B.3 = C; means move 3 consecutive bytes starting at location C. The more general form B.K = C; specifies movement of K bytes. A variable name with decimal point is said to be "quantified" and the expression to the right of the decimal point is the quantifier. In the absence of a quantifier, single byte operations are implied. The quanti- fier can be a PL/65 arithmetic expression, or simply a variable name or constant. An expression is an operand followed by an arbitrary number of operator- operand pairs. The operands can be variable names of integers. A typical expression in PL/65 is B + 3 - C which is evaluated as if it were (B + 3) - C. Similarly D - E - F is evaluated as (D - E) - F. Thus, the state- ment B.K - 3 + J = C; will cause (K-3)+J bytes to be moved from byte locations starting at C to consecutive locations starting at B. ________________________________________________ | | | NOTE: | | ----- | | | | Since the symbols 'A', 'X', 'Y', 'S', and 'P' | | have special meaning in R6500 Assembler they | | should not be used as variable names in PL/65. | |________________________________________________| The right side of an assignment can be a PL/65 expression, as in: B = C + D - E + 24; 3-3 *************************************************************************** Expressions are evaluated left to right, in the order in which operators are encountered. Parentheses are allowed in assignment statements. The major restriction is that the right side of an assignment statement must not begin with a left parenthesis. Thus B = (C + (D -5)); is invalid. Note that parenthetical groups lower code efficiency and should be used with appropriate care. Byte arrays and words, character strings, and quantified variables can be used in arithmetic expressions. The operators are permitted +, -, .AND [logical AND], .OR [logical OR], and .EOR or .XOR [exclusive OR]. Operands follow assembly language conventions: a prefix $ indicates a hexadecimal constant, % indicates binary, and # signifies that the address of the symbol is to be used rather than the value. As noted, arrays of bytes are always zero origin. The statement B[0] = C[0]; has the same effect as B = C; Further, B[0].1 = C; has the same effect as B.1 = C; However, byte assignments should not be so quantified or reduced code efficiency will result. Subscripts can be integers, variable names, or expressions. Thus, the most general form of byte assignment is B[exp1].exp2 = C[exp3]; or B[exp1].exp2 = C operator D; Note that only one subscripted variable is allowed on the right side of the '=' and, if present, it must be the only variable. The statement B[exp1] = C[exp2] is a single byte assignment. Unlike code generated by some compilers there is no subscript range checking for arrays. Thus, an errant array reference could refer to executable code as data. Since only byte arithmetic is used, the largest value a subscript may have is 255. Indirect single byte assignments are permitted with the operators '@' or '&'. '&' means that the variable is already in page zero. '@' means that the variable is not in page zero and will be moved to a temporary page zero location before being used. The most general form of indirect assignment is: @Variable[sub] = @variable+[sub] or @variable[sub] = @variable+expression; where either '@' may be replaced with '&' if appropriate. Subscripts 3-4 *************************************************************************** in indirect assignments will always generate code corresponding to the INDIRECT Y form in the Assembler. For example: @B[5] addresses the fifth byte after the location pointed to by B. If location B contains $1000 (stored as $00, $10), @B[5] refers to location $1005. For word assignments, the alternate form '==' may be used for the '.2' quantifier. Thus: WORD1.2 = WORD2; WORD1 == WORD2; are equivalent statements. 3.3 IMPERATIVE Each computer model has its own unique instruction set and format. However, certain functions are common to a broad spectrum of machines. That set has been included in the PL/65 language as a convenience to the programmer. Bit manipulation is performed with the instructions SHIFT, ROTATE, CLEAR, and SET, which operate on single bytes. The instruction SHL B.3; is a shift left of 3 bit positions with zero fill. ROL B.2; is an end-around shift left 2 bit positions. The default quantifier is 1. Bits of a byte can be cleared or set by providing a mask for the variable name as in SET BITS[203] OF B; which will set bit positions corresponding to ones in the binary repre- sentation of the value 203 decimal (i.e., 11001011). The CODE statement allows the user to specify assembler code directly. Any information in single quotes is copied directly to the output file without any processing. Hence, assembler code can be inserted in single quotes. The keyword CODE is optional. Blocks of assembler code may be passed between two lines which have an '*' in the first column. The HALT; command is a termination of program execution. For the R6500 processor the code generated is a jump to self [JMP *]. A WAIT instruction is included in PL/65 to help handle asynchronous interrupts. A WAIT is a conditional delay for an asynchronous event. The form is WAIT ON BITS[100] OF T; In this case, T would normally be some register which can be affected by external events. As soon as any of the specified mask bits of T are '1' the wait is terminated and execution continues. At times a delay may be required until all of the bits speci- fied are set. Also, it is sometimes necessary to wait until the bits are clear (i.e., 0). Four options with the WAIT statement are shown in the examples below. Note that default options are "ALL" and "SET". 3-5 *************************************************************************** WAIT ON ANY BITS[ALPHA] SET OF BETA; WAIT ON ANY BITS[ALPHA] CLEAR OF BETA; WAIT ON ALL BITS[ALPHA] SET OF BETA; WAIT ON ALL BITS[ALPHA] CLEAR OF BETA; Two stack manipulation instructions are present in PL/65 and they are extremely useful for saving and restoring register values on entry or exit from subroutines. Examples are: STACK R0, R1, R2; STACK WORD R1; STACK R2, R1, R0; UNSTACK R0,R1,R2 ; UNSTACK WORD R1; 3.4 SPECIFICATION Normally the first statement of a PL/65 program is ENTRY. Actions performed correspond to initialization functions. For the R6500 the ENTRY statement initializes the instruction counter to $0200 (page 2), clears decimal mode, and initializes the stack pointer to $FF. If pro- grams are to be assembled at a location other than $0200 the address can be specified as for example: ENTRY $0300;. The EXIT statement generates an assembler ".END" instruction. 3.5 CONDITIONAL The decision structure common to many high-level languages such as Algol and PL/1 is the IF-THEN-ELSE conditional. Here is one form of the condi- tional for single byte tests: IF B greater than >= greater than or equal to = equal to ^= not equal to Multiple byte comparisons may be made on direct values only (i.e., indirection is not allowed) and the comparison must be chosen from: = equal to ^= not equal to Conditionals can be nested to any depth as illustrated by: IF P > B + C THEN IF C < 5 THEN IF E - 4 = F THEN P = E + F .EOR G; Collective conditional execution is accomplished by using BEGIN-END blocks. IF N < MAX THEN BEGIN; SUM = SUM + P; N = N + 1; P = B[N]; END; An alternate form of conditional execution based on a computed value is provided as a form of CASE statement. An example is: CASE [N] [LB1, LB2, LB3]; In this example a branch is made to label LB1, LB2, or LB3, depending on whether N is 1, or 2. The value of the expression must reduce to an integer for which there is a label in the list. There is no range checking on the computed value and random execution errors will occur if the range is improper. Any number of labels is permitted and the condi- tional value can be an expression. The PL/65 CASE statement is analagous to a computed GO TO in FORTRAN; in fact, the keywords "GO TO" may be used in place of "CASE". 3.6 BRANCHING Statements may be labeled with a name of 1 to 6 alphanumeric characters followed by a colon. Multiple labels are not permitted. An unconditional branch to a specific statement can be made with a GO TO, e.g., GO TO 3-7 *************************************************************************** START;. Indirect branches are supported, e.g., GOTO @START;. The uncon- ditional branch should be avoided when possible since it often obscures the logic of the program. Subroutine calls are supported with the commands CALL and RETURN. ... CALL SUB1; ... B1: ... RETURN ; The CALL executes a Jump to Subroutine (JSR) and acts as an absolute branch to the specified label. The RETURN executes a Return from Sub- routine (RTS) and causes execution to resume at the statement following the call. Since all variables are global to the main program and all subroutines, there is no need or provision for parameter passing. An RTI (return from interrupt) instruction is available, also. 3.7 LOOPING Two forms of looping constructs are implemented in PL/65. An example of the iterative form is: FOR I = 1 TO 13 BY 2 BEGIN; C[I]; SUM = SUM + B; END; The general form is: FOR name = exp1 TO variable BY variable statement [or block] where exp1 is the initial value for the variable name, exp2 is a test or terminal value and exp3 is the value of the variable incremented each iteration. As in PL/1, the test is made prior to first execution of the statement and hence there are cases where the statement may not be executed at all as in the example: FOR J = 5 TO 4 ... ; The BY clause is optional; an increment of 1 is assumed if it is omitted. FOR-LOOPS may be nested to any depth. The loop is executed until the value of the loop variable exceeds the value of the terminal expression. Thus, FOR J = 1 TO 1 ... 3-8 *************************************************************************** is a non-terminating loop with exit from the loop by a direct GOTO state- ment presumably. The second form of looping has no iteration and is shown by: WHILE B < C + D DO ; B = B + 1; C = C - 2; END; The loop block is executed as long as the conditional expression is true. As in the FOR-LOOP the test is made prior to first execution and hence the block may be bypassed with no execution. The general form is: WHILE variable relopr variable DO; Statement[s] END; The relopr (relational operator) and variables are as defined earlier. 3.8 COMPILER GENERATED LABELS Note that the compiler generates labels which are of the form 'ZZ' followed by a number. Therefore, it is strongly recommended that any labels generated by the programmer are of a different form. 3.9 PAGE ZERO UTILIZATION PL/65 imposes certain minor restrictions on the use of page zero: The first is that locations $0 through $5 are used as temporary locations by the compiler. It is recommended that programs start their page zero locations at $10. This may be easily done with the DEF *=$10; statement. The second restriction applies to PL/65 on the SYSTEM 65, but is a good programming practice on any machine. Since the compiler uses page zero when it is running, the program must not generate values into page zero by using the INIT option of the DECLARE statement or any other statement which cause corruption of page zero. Thus, the general rule is that the program should initialize page zero when it is started, and not when it is compiled. 3-9 *************************************************************************** SECTION 4 INSTALLATION AND OPERATION The PL/65 Compiler is provided in object code form on mini-floppy diskette for direct installation on SYSTEM 65. Also included on the diskette is the object code for a PL/65 Optimizer program and a PL/65 Test program. The files are identified as: FILE NAME FILE DESCRIPTION PL65Vn PL/65 Object Code OPTVn Optimizer Object Code TEST PL/65 Test Program 4.1 LOADING THE PL/65 COMPILER 1. Install the PL/65 Compiler diskette into one of the two SYSTEM 65 disk drives. __________________________________________________________ | | | CAUTION: | | -------- | | | | The PL/65 Compiler object code occupies 14K bytes of | | RAM -- from address $0200 to $3700. Be sure to save | | any data required within this address range before | | loading the PL/65 compiler. | |__________________________________________________________| 2. Type L after display of the Monitor prompt. SYSTEM 65 will respond with: IN= 3. Respond to the input prompts: IN= F FILE= PL65Vn DISK=1 SYSTEM 65 will load the PL/65 Compiler object code into RAM and will display the Monitor prompt at the end of the load (after approxi- mately one minute): < 4-1 *************************************************************************** 4. The PL/65 Compiler disk may be removed from the SYSTEM 65 disk drive until subsequent load of the compiler or optimizer is re- quired. 4.2 OPERATING THE PL/65 COMPILER 1. If the PL/65 application source program is contained on diskette, install the diskette in one of the SYSTEM 65 disk drives. 2. Enter PL/65 Compiler by typing 7. SYSTEM 65 will respond with: <7> PL/65 [VX] IN= _____________________________________ | | | NOTE: | | ----- | | | | X will be a version number. | |_____________________________________| 3. Enter the code of the input device containing the PL/65 application source program. For example, if a source program with file name PLSRC is contained on a diskette and is mounted in SYSTEM 65 disk drive 1, type in this data in response to SYSTEM 65 prompts: IN=F FILE=PLSRC DISK=1 OUT= 4. Enter the code of the output device where the formatted PL/65 source program listing is to be directed. For example, if the output is to be printed, type P. SYSTEM 65 will respond with: IN= F FILE=PLSRC DISK= 1 OUT=P SYSTEM 65 will proceed to list the formatted PL/65 source code. 5. At the completion of listing the formatted source program, PL/65 will display the error count in decimal and ask for an output device code. ERRORS= NN where NN= 00 TO 99 OUT= 6. Enter the code of the output device that the PL/65 compiler output (R6500 Assembler Source Statements) is to be directed. For example, if the output is to be directed to a diskette on SYSTEM 65 disk drive 4-2 *************************************************************************** 2 with file name ALSRC, type in this data in response to SYSTEM 65 prompts: OUT=F FILE= ALSRC DISK=2. PL/65 will then compile the PL/65 application source program into R6500 assembly statements and at the end of the compilation, will display a disassembled instruction and the Monitor prompt: =XXXX 4C 00 02 JMP $0200 < If it is desired to optimize the assembler source code, follow the procedure described in Sections 4.3 and 4.4. Otherwise, the PL/65 compiler output assembler statements may be assembled in accordance with the SYSTEM 65 operating procedure (see Section 9 of the SYSTEM 65 User's Manual). 4.3 LOADING THE PL/65 OPTIMIZER 1. Ensure that the PL/65 Compiler diskette is installed into one of the two SYSTEM 65 disk drives. 2. Type L after display of the Monitor prompt: IN= 3. Respond to the input prompts: IN=F FILE=OPTVn DISK=[1,2] SYSTEM 65 will load the PL/65 Optimizer object code into RAM and will display the Monitor prompt at the end of the load: ^ 4. The PL/65 Compiler diskette may be removed from the SYSTEM 65 disk drive until subsequent load of the PL/65 Compiler or Optimizer object code is required. 4.4 OPERATING THE PL/65 OPTIMIZER 1. If the PL/65 compiler output assembler statements are contained on diskette, install the diskette in one of the SYSTEM 65 disk drives. 4-3 *************************************************************************** 2. Enter the optimizer by typing 7. SYSTEM 65 will respond with: <7>IN= 3. Enter the code of the input device containing the input assembler source program. For example, if the source program with a file name of ALSRC is contained on a diskette mounted in SYSTEM 65 disk drive 1, type in this data in response to SYSTEM 65 prompts: <7>IN=F FILE=ALSRC DISK=1 OUT= 4. Enter the code of the output device which is to receive the optimized assembler source program. For example, if the output is to be stored on a diskette mounted in drive 1 with file name ALSRC', type in this data in response to SYSTEM 65 prompts: <7>IN=F FILE=ALSRC DISK=1 OUT=F FILE=ALSRC' DISK=1 5. SYSTEM 65 will proceed to optimize the input assembler source pro- gram. At the end of the optimization process, SYSTEM 65 will respond with a decimal count of the number of instructions deleted: COUNT = NN Where NN = 00 TO 99. =XXXX 4C 00 02 JMP 0200 The optimized assembly source statements may now be assembled in accordance with the SYSTEM 65 Assembler instructions (see Section 9 of the SYSTEM 65 User's Manual). 4.5 PL/65 TEST PROGRAM The source code of the PL/65 Test Program may be used as a test file to become familiar with the PL/65 Compiler processing. Use this file as the PL/65 Compiler application source program in Section 4.2. 4-4 *************************************************************************** APPENDIX A STATEMENT FORMATS This section describes the format possibilities for the various types of statements. Examples are given to show most format types. The descriptions are alphabetized according to statement type. Brackets < > denote the field is optional and a slash / indicates that a choice is to be made from the alternatives given. Descriptions are in the following order: ASSIGNMENT A.1 BLOCK A.2 CALL A.3 CASE A.4 CLEAR A.5 CODE A.6 COMMENT A.7 DATA A.8 DEC A.9 DECLARE A.10 DEFINE A.11 ENTRY A.12 EXIT A.13 FOR-TO-BY A.14 GO TO A.15 HALT A.16 IF-THEN-ELSE A.17 IFF-THEN A.18 INC A.19 PULSE A.20 RETURN A.21 ROTATE A.22 RTI A.23 SET A.24 SHIFT A.25 STACK A.26 TAB A.27 UNSTACK A.28 WAIT A.29 WHILE A.30 A-1 *************************************************************************** A.1 ASSIGNMENT The assignment statement is probably the most powerful and useful state- ment type in PL/65. This does not mean that it is also the hardest one to understand. There are certain restrictions on the types of assignment statements which are legal. These restrictions may, at first, seem to be arbitrary but are fairly easy to understand if you look at the code generated for a particular statement. In general, the restrictions are caused by the availability of only two index registers on the R6500 processor or the size of the index registers (8 bits). The examples below attempt to illustrate the types of statements which are legal but a few general rules may be stated: 1. The left term may always be subscripted. One subscripted term may appear on the right side. If present, it must be the first term and must be the only term in a multiple byte assignment. Subscripts must fall in the range 0 to 255. 2. Indirect operators are '@' which means the term is not located in page zero but will be moved to a page zero temporary location before being used. '&' means the term is already in page zero. This form results in greater code efficiency than does the first form. 3. Indirect terms may occur on either side of the statement and may be subscripted. They may only occur in single byte statements. As mentioned earlier, subscripted indirect statements generate code which uses the INDIRECT Y Mode. If an indirect term is used on the right side, it must be the first term. 4. Multiple byte statements may only have two terms on the right side. If a multiple byte expression is subscripted on the right side, only that term may appear. 5. The '==' form may be used to signify a two byte move. It generates exactly the same code that '.2=' would generate. 6. If a character string appears on the right side, it must be the only term. 7. Single byte assignments (the only form which allows more than two terms on the right side) may contain parenthetical groupings with the '(' and ')' operators subject to the restriction that '(' must always be preceded with a arithmetic or logical operator. This is the only place that parenthetical expressions are allowed. A-2 *************************************************************************** 8. The value of an address may be assigned with the '##' operator as shown below. A single byte value may be assigned with the '#' operator. 9. Note that parenthetical groupings and indirect terms on the right side lower code efficiency due to the necessity of saving intermed- iate results. 10. The abbreviated form: ALPHA+n; or ALPHA-n; may only be used on non-subscripted, non-indirect variables. _______________________________________________ | | | <[sub]> expression / | | name =array element/; | | <.expr> 'characters' | |_______________________________________________| Examples: B = C; "SIMPLE BYTE TRANSFER"; @B = C; "BYTE TRANSFER INDIRECT DESTINATION"; B= @C; "INDIRECT SOURCE"; B= #C; "VALUE OF SYMBOL TO LOCATION B"; B = ##C; "ADDRESS ASSIGNMENT": B= D + F; "SIMPLE ARITHMETIC AND ASSIGNMENT"; B= G[4]; "BYTE TRANSFER FROM ARRAY G ELEMENT 4"; B[J] = C; "TRANSFER TO ARRAY B ELEMENT J"; B.K = C; "TRANSFER OF K BYTES STARTING AT C"; B[J+5] = C; "MOVE BYTE AT C TO ARRAY B ELEMENT J+5"; B[J] = 'X'; "TRANSFER OF LITERAL BYTE 'X' TO B"; B[J+1].K-1 = 'ABCDEF'; "MOVEMENT OF K-1 LITERAL BYTES"; " LOGICAL OPERATORS "; C = D .AND F; C = D .OR F; C = D .XOR F; C = D .AND F .OR 2 .XOR $55; B .AND 1; B .OR 2; B .EOR 2; B+1; B-1; B+5; B+J ; A-3 *************************************************************************** B-J; B+J-K+5; B.K = C-D; "ONLY TWO TERMS ON MULTI BYTE"; B.K = C[J]; "ONLY ONE TERM IF SUBSCRIPTED IN MULTI BYTE"; B[J].15 = C[J]; "ALSO LEGAL"; B.K = 5; "SET K BYTES ALL EQUAL TO 5"; @B = @C; &B = &C; &B = @C; @B = &C; @B[5] = @C[J]; &B[5] = &C[J]; @B[K] = C[5] +D -F; &B[5] = C[5] +D -F; &B = C[R]=D-6 .AND 3; &B[G-3] = C[N]+D-6; &B[3] = C[4] - (F-D+3); B[5] = @C+D-(F-N+3); B[5] = @C; B[N] = &C; A.2 BLOCK A block is a collection of statements (one or more) to be treated as a single group. _______________________________________________ | | | BEGIN;/ | | statements END; | | DO; | |_______________________________________________| No distinction is made between keywords BEGIN and DO and either may be used. Nothing more than logical grouping is implied by blocks. Examples: FOR J = 1 TO 5 DO ; B[J] = J; B[J] = J-1; END; IF ALPHA = 0 THEN BEGIN; BB = $21; "NOTE HEX CONSTANT"; BC = 17; "NOTE DECIMAL CONSTANT"; BC = %1011; "NOTE BINARY CONSTANT"; END; A-4 *************************************************************************** A.3 CALL Labeled blocks may be called as subroutines. ______________________________________ | | |