PAL-11A Absolute Assembler

PAL-11A is the first assembler DEC released for the PDP-11. It reads assembly language source files, and punches out a program ready to be loaded by Absolute Loader. It optionally prints out a listing of the program on the printer, along with the locations of symbols that appear in the program.

As seen in a previous post, the SimH simulator can be used to run the Paper Tape System programs, including the ED11 editor and the PAL-11A assembler. If you want a more authentic experience, you can use ED11 to edit your PAL-11A source code. Or, you can take advantage of fifty more years of text editing technology and simply create a text file with your favorite modern editor- the SimH paper tape reader simulation can take any file as input.

PAL-11A is a fairly basic assembler. It does not have features like macros (code that can generate code) or direct support for relocatable programs. It does provide some assembly-time arithmetic, and some directives to inject raw bytes, words, and ASCII strings into the assembled output.

We can dive right in and write a simple PAL-11A program that adds two and three. We can't even start with the canonical "Hello, world" program until we understand how to actually make output appear on the teletype. We will get there soon. Here's two plus three:

        .=      1000            ; ASSEMBLE TO ADDRESS 1000
        MOV     #2,%0           ; STORE 2 IN R0
        ADD     #3,%0           ; ADD 3 TO R0
        MOV     R0,@#2000       ; STORE R0 AT 2000
        HALT                    ; HALT THE COMPUTER
        .END                    ; END OF PROGRAM

The first line is a directive that tells the assembler that the output tape should indicate that this program should be loaded at address 1000. The next four lines show the instruction mnemonics, and their sources and destinations, as well as comments that tell the person who reads them a bit more information about what they intend the program to do. The final line tells the assember that this is the end of the program- without it, the assembler will assume there is more of the program on a different tape.

Enter that program into a text file. This will be our virtual source paper tape. Later, once you learn how to load and run paper tapes, you can enter source code using a steady, unerroring hand, or use ED-11. For now, stick with your favorite editor (vim, of course) and put that program into a text file.

We can run the assembler in SimH. First fire up the PDP-11 simulator:

$ pdp11
PDP-11 simulator V4.0-0 Current        git commit id: 01234567
sim>

Enter the following commands to initialize the simulator and enter the Bootstrap Loader. First, load the Absolute Loader tape (DEC-11-L2PC-PO.ptap) into the simulated high-speed paper tape reader, then run these commands to run it. The prompts are omitted here to allow for easier copy-and-paste.

SET CPU 11/20
SET CPU 56k

SET PTP ENABLE
SET PTR ENABLE

SET DZ DISABLE
SET RK DISABLE
SET RL DISABLE
SET HK DISABLE
SET RX DISABLE
SET RP DISABLE
SET RQ DISABLE
SET TM DISABLE
SET TQ DISABLE

DEPOSIT 157744 016701
DEPOSIT 157746 000026
DEPOSIT 157750 012702
DEPOSIT 157752 000352
DEPOSIT 157754 005211
DEPOSIT 157756 105711
DEPOSIT 157760 100376
DEPOSIT 157762 116162
DEPOSIT 157764 000002
DEPOSIT 157766 157400
DEPOSIT 157770 005267
DEPOSIT 157772 177756
DEPOSIT 157774 000765
DEPOSIT 157776 177550

ATTACH PTR DEC-11-L2PC-PO.ptap

GO 157744

The Bootstrap Loader will load the Absolute Loader into memory and will halt the simulation with the prompt

HALT instruction, PC: 157500 (MOV PC,SP)
sim>

Now, we load PAL-11A with

ATTACH PTR DEC-11-ASXA-PB.ptap
DEPOSIT SR 157500
GO 157500

And PAL-11A will start, with a terse prompt

*S

SimH simulates the Teletype Model 33 ASR console with the standard input and output of SimH. Any input will be passed into the program as if it came in from the teletype keyboard. This includes control characters. SimH does listen for Control-E, so if you need to get back to the sim> prompt, press Control-E. To continue the simulation, use the CONT command (or the shorthand c). We should do that now to load the source code tape into the high-speed reader

*S ^E
sim> ATTACH PTR source.pal
sim> CONT

Here, we're back in PAL-11A, which is waiting for a response for *S.

The *S prompt from PAL-11A is asking where the source code lives. There are three legal responses: H for the high-speed reader, L for the low- speed reader that's part of the teletype, and T for the teletype keyboard. Since PAL-11A needs to read the source more than once, a user that chooses T should be very careful to type the source code identically for each pass. (In other words, just put your source on a tape and use H.)

The next prompt is

*B

This tells the assember where the output binary should go. H means the high-speed punch, L means the low-speed punch on the teletype. Appending /3 tells the assembler to output the binary on the third pass instead of the default second pass. Appending /E to the response will print any errors to the teletype. An enter with no option tells the assembler to not output a binary. This is useful if you just want to just check for errors or print a listing of the program. We'll use H/E.

Next up,

*L

This tells the assembler where to output a code listing, that also shows the addresses where the instructions were placed. This is very useful during debugging. The options are L, the low-speed punch, H the high-speed punch, T the teletype printer, or P the line printer. An enter with no option tells the assembler to not output a listing. This is output during the third pass unless /2 is appended. We'll use H.

Finally, one more prompt:

*T

This tells the assembler where to output the symbol table, again useful for debugging. This has the same options as the *L prompt. By default the table is output during the first pass, but this can be changed by appending /2 or /3. We'll use H/3, so it ends up in the same output as the listing.

At this point, PAL-11A will read the source tape, building up an internal symbol table. When it reaches the end of the tape, it will print

END?

Here, we're ready to start the second pass. Reload the source tape into the reader, and tell the simulated punch to write the binary to a file. To do this press Control-E to get back into SimH, use the commands to load the tapes, and continue:

END? ^E
sim> ATTACH PTR source.pal
sim> ATTACH PTP binary.lda.ptap
sim> CONT

Now we're back in PAL-11A, which is expecting a response to END?. Simply hit enter, and the assembler will run its second pass, showing any errors, and will again prompt

END?

Now we're ready to start the third pass. Reload the source tape into the reader, and tell the punch to write the listing and symbol table to a file:

END? ^E
sim> ATTACH PTR source.pal
sim> ATTACH PTP listing.out
sim> CONT

Respond to END? prompt with an enter, and if all went well, you'll see

000000 NO ERRORS

*S

PAL-11A is ready to assemble another program. You can exit SimH with

*S ^E
sim> EXIT

You can run your program using the same steps as running PAL-11A. Set up the simulated PDP-11/20 as seen above, enter the Bootstrap Loader, attach the Absolute Loader tape and run the Bootstrap Loader, then attach your binary tape (called binary.lda.ptap in the example above), hit start to load your program, and use the SimH GO 1000 command to start your program.

Run the SimH commands seen above to load the Absolute Loader. When the Bootstrap Loader halts after loading Absolute Loader, enter the commands

ATTACH PTR binary.lda.ptap
DEPOSIT SR 157500
GO 157500

This loads the program. Once loaded, there will be another sim> prompt, and the program can be run, and then we can check the value at address 2000:

sim> GO 1000
HALT instruction, PC: 001016 (HALT)
sim> EXAMINE 2000
2000:   000005
sim>

Easy.

As you can see, there's a lot going on here. Fortunately, SimH lets us put these commands into a script, and that script can take arguments. Version 4 of SimH includes commands that can listen for prompts on the simulated teletype printer, and can "type" responses on the simulated teletype keyboard. I've created an enhanced assemble.do that takes filenames as command line arguments to SimH, and also automates the responses to the PAL-11A prompt. With this setup, running PAL-11A is similar to running other command line programs. An additional run.do script is used to run the assembled program.

Scripts

assemble.do: with your source in myprogram.pal, use pdp11 assemble.do myprogram

ECHO >> Setting CPU: 11/20, 28kW
SET CPU 11/20
SET CPU 56K

ECHO >> Disabling all devices
SET DZ DISABLE
SET RK DISABLE
SET RL DISABLE
SET HK DISABLE
SET RX DISABLE
SET RP DISABLE
SET RQ DISABLE
SET TM DISABLE
SET TQ DISABLE

ECHO >> Enabling High Speed Paper Tape Punch and Reader
SET PTP ENABLE
SET PTR ENABLE

ECHO >> Loading Paper Tape Bootstrap Loader @ 28kW
DEPOSIT 157744 016701
DEPOSIT 157746 000026
DEPOSIT 157750 012702
DEPOSIT 157752 000352
DEPOSIT 157754 005211
DEPOSIT 157756 105711
DEPOSIT 157760 100376
DEPOSIT 157762 116162
DEPOSIT 157764 000002
DEPOSIT 157766 157400
DEPOSIT 157770 005267
DEPOSIT 157772 177756
DEPOSIT 157774 000765
DEPOSIT 157776 177550
DEPOSIT SR 157744

ECHO >> Attaching Absolute Loader to Paper Tape Reader
ATTACH PTR DEC-11-L2PC-PO.ptap

ECHO >> Running bootstrap to load Absolute Loader
GO 157744

ECHO >> Attaching PAL-11A (8K) papertape
ATTACH PTR DEC-11-ASXA-PB.ptap

; Set up responses to PAL-11A initialization
EXPECT "*S " ECHO >> Setting PAL-11A options; SEND AFTER=20000,"H\r\n"; CONT
EXPECT "*B " SEND AFTER=20000,"H/E\r\n"; CONT
EXPECT "*L " SEND AFTER=20000,"H\r\n"; CONT
EXPECT "*T " ATTACH PTR %1.pal; SEND AFTER=20000,"H/3\r\n"; ECHO >> Running first pass; CONT
EXPECT " END ?" ATTACH PTR %1.pal; ATTACH PTP -n %1.lda.ptap; SEND AFTER=20000,"\r\n"; ECHO >> Running second pass; CONT
EXPECT " END ?" ATTACH PTR %1.pal; ATTACH PTP -n %1.out; SEND AFTER=20000,"\r\n"; ECHO >> Running third pass; CONT
EXPECT "*S " ECHO >> Done.  Exiting; EXIT

ECHO >> Start Absolute Loader to Load and Run PAL-11A (8K) paper tape
DEPOSIT SR 157500
; Absolute loader occupies xx7474 through xx7743
; start address is xx7500
GO 157500

run.do: Used to initalize and run a program with pdp11 run.do myprogram.lda.ptap

ECHO >> Setting CPU: 11/20, 28kW
SET CPU 11/20
SET CPU 56K

ECHO >> Disabling all devices
SET DZ DISABLE
SET RK DISABLE
SET RL DISABLE
SET HK DISABLE
SET RX DISABLE
SET RP DISABLE
SET RQ DISABLE
SET TM DISABLE
SET TQ DISABLE

ECHO >> Enabling High Speed Paper Tape Punch and Reader
SET PTP ENABLE
SET PTR ENABLE

ECHO >> Enabling Line Printer
SET LPT ENABLE

ECHO >> Loading Paper Tape Bootstrap Loader @ 28kW
DEPOSIT 157744 016701
DEPOSIT 157746 000026
DEPOSIT 157750 012702
DEPOSIT 157752 000352
DEPOSIT 157754 005211
DEPOSIT 157756 105711
DEPOSIT 157760 100376
DEPOSIT 157762 116162
DEPOSIT 157764 000002
DEPOSIT 157766 157400
DEPOSIT 157770 005267
DEPOSIT 157772 177756
DEPOSIT 157774 000765
DEPOSIT 157776 177550
DEPOSIT SR 157744

ECHO >> Attaching Absolute Loader to Paper Tape Reader
ATTACH PTR DEC-11-L2PC-PO.ptap

ECHO >> Running bootstrap to load Absolute Loader
GO 157744

ECHO >> Attaching %1 paper tape
ATTACH PTR %1

ECHO >> Start Absolute Loader to Load and Run %1 paper tape
DEPOSIT SR 0
; Absolute loader occupies xx7474 through xx7743
; start address is xx7500
GO 157500

ECHO >> Attach input paper tape if necessary   (ex: ATTACH PTR (file))
ECHO >> To start %1, type "GO (START ADDRESS)" (ex: GO 1000)

References