234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
|
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
|
-
+
-
-
+
-
-
-
-
-
+
-
-
-
+
-
-
+
-
+
-
-
-
-
-
+
-
-
-
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
-
+
+
+
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
|
[ip]: http://bitsavers.org/pdf/dec/pdp8/handbooks/DEC-08-XINPA-A-D_intrPgm_75.pdf
[pl]: http://bitsavers.org/pdf/dec/pdp8/handbooks/programmingLanguages_May70.pdf
[ps8ug]: https://archive.org/details/bitsavers_decpdp8sofogrammingSystemUsersGuide_2417347
[ts8m]: http://bitsavers.org/pdf/dec/pdp8/typeset8/
[ts8p]: http://gordonbell.azurewebsites.net/digital/timeline/1968-3.htm
### <a id="ralf" name="flap"></a>RALF/FLAP
### <a id="ralf"></a>RALF
RALF is the back-end assembler for OS/8's FORTRAN IV compiler. As a result of that support role, it has a few primary advantages over PAL8:
RALF uses more or less the same statement syntax as the PAL family, but it is a very different assembler by nature. We can divide its differences into several groups.
* relocatable output code
* easy access to the floating-point processor (FPP) peripherals for the PDP-8 family
The RALF assembler has a mode switch that causes it to generate absolute-addressed code, as PAL8 does. In this mode, it is called FLAP.
RALF has the following advantages over FLAP:
#### Floating Point Processor Support
* Relocatable code
The primary advantage FLAP has over RALF is that, because it is difficult to ascribe meaning to the "page" concept in a relocatable assembler, RALF doesn't support the `PAGE` pseudo-op, while FLAP does. FLAP also supports the PAL family's zero-page and current-page literal syntaxes, while RALF does not.
RALF is the back-end assembler for OS/8's FORTRAN IV compiler, which requires use of a Floating Point Processor (FPP) peripheral, and OS/8 FORTRAN IV delegates all of the FPP handling to RALF. Indeed, Vincent Slyngstad [suggests][smal8] that you think of RALF as an assembler for the FPP rather than for the PDP-8.
RALF and FLAP share many advantages over the PAL family assemblers.
The main advantage is that these assemblers have direct support for the PDP-8 family Floating Point Processor peripherals. The first such peripheral was the [FPP-12][fpp12]. Although it was introduced with the PDP-12, it is not restricted to the PDP-12: it also works with all of the other PDP-8 family computers contemporaneous with and preceding it, going back to the original PDP-8, because it is a bus peripheral rather than a feature of the CPU proper. There was also a follow-on peripheral for the PDP-8/a called the [FPP8-A][fpp8a], which is compatible with the FPP-12. The FPP features of RALF/FLAP facilitate use of these peripherals in programs you write in those assembly languages. the FPP modes. Vincent Slyngstad [suggests][smal8] that you think of RALF and FLAP as assemblers for the FPP rather than for the PDP-8.
The first FPP from DEC was the [FPP-12][fpp12]. Although it was introduced with the PDP-12, it is not restricted to the PDP-12: it also works with all of the other PDP-8 family computers contemporaneous with and preceding it, going back to the original PDP-8, because it is a bus peripheral rather than a feature of the CPU proper. There was also a follow-on peripheral for the PDP-8/a called the [FPP8-A][fpp8a], which is compatible with the FPP-12. The FPP features of RALF facilitate use of these peripherals in programs you write in those assembly languages.
Although the basic statement syntax in RALF and FLAP is similar to that of the PAL family, these assemblers differ from PAL family assemblers in many ways:
Here is a list of FPP-related RALF features:
* Expressions:
* Multiplication is `*` rather than `^`, achieved by using the `ORG` pseudo-op to set the location counter
* Division is `/` rather than `%`, achieved by requiring whitespace before `/` used to start a comment and disallowing spaces in expressions
* There is no Boolean `AND` operator `&`
* Added FPP instructions and FPP-related psuedo-ops:
* More instructions and pseudo-ops:
* Arithmetic: `FADD`, `FADDM`, `FDIV`, `FLDA`, `FMUL`, `FMULM`, `FSTA`, `FSUB`
* Conditional jumps: `JEQ`, `JGE`, `JLE`, `JA`, `JNE`, `JGT`, `JAL`
* FPP to PDP-8 jumps: `JXN`, `TRAP3`, `TRAP4`
* Indexing: `ADDX`, `INDEX, `LDX`
* No-op: `NOP`
* Pointer moves: `JSA`, `JSR`, `SETB`, `SETX`
* Processor Operations: `FCLA`, `FEXIT`, `FNEG`, `FNORM`, `FPAUSE`, `JAC`, `STARTD`, `STARTF`
* Register manipulation: `ALN`, `ATX`, `XTA`
* Require double-precision hardware: `DPCHK`
* Use 15-bit addresses directly in FPP instructions, rather than the [PDP-8's memory model][mm8]; `BASE` psuedo-op
* Many new and changed pseudo-ops:
* `LISTOF` and `LISTON` to stop and start listing output rather than the PAL family's `XLIST` pseudo-op
* Conditional assembly additions relative to PAL8: `IFPOS`, `IFNEG`, `IFSW`, `IFNSW`, `IFFLAP`, `IFRALF`
* `IFREF` replaces `IFDEF` pseudo-op, having a superset of its functionality
* `REPEAT` pseudo-op to assemble the following line multiple times
* More ways to define constants of various sorts: , `ADDR`, `E`, `F`, `S`
* Pseudo-ops to support FORTRAN IV features: `COMMON`, `COMMZ`, `ENTRY`, `EXTERN`, `FIELD1`, `SECT`, `SECT8`
* `S n` — single-word constant with value `n` (FLAP only)
* `F n` — 3-word single FP constant with value `n`
* `E n` — 6-word extended-precision FP constant with value `n`
* Use 15-bit addresses directly in FPP instructions, rather than the [PDP-8's memory model][mm8]; `BASE` pseudo-op
If you see any of the added instructions listed above in a given assembly language program, it's a pretty good indicator that it's meant to be assembled by RALF or [FLAP](#flap).
#### Relocatable Code
RALF generates relocatable output code in `*.RL` files rather than absolute-addressed core images in `*.SV` files. This means its output files cannot be run directly by OS/8. You must use the OS/8 FORTRAN IV loader (`LOAD.SV`) to load one or more `*.RL` files into core memory, link them to any external libraries, convert relative addresses to fixed addresses, and write out a loader image (`*.LD`) which can then be loaded by the OS/8 FORTRAN IV Run Time System, `FRTS.SV`.
The compensating value for this complicated scheme is that `LOAD.SV` and `FRTS.SV` are capable of a very complicated overlay and linkage loading scheme which allows for programs up to about 300 kWords in size, nearly 10× the maximum core memory size in a standard PDP-8 family computer. It does this by loading code from disk as needed.
(Do not confuse `LOAD.SV`, the OS/8 FORTRAN IV loader — used by both RALF and OS/8 FORTRAN IV — with `LOADER.SV`, the simpler "linking loader" used by the OS/8 FORTRAN *II* compiler (`FORT.SV`) and by [SABR](#sabr). Both use the `*.RL` file name extension.)
The FPP also plays into this, because it has a 15-bit memory addressing feature which allows RALF programs to perform many memory references directly, rather than through the PDP-8's normal [complicated memory addressing scheme][mm8].
If you see any of the added instructions listed above in a given assembly language program, it's a pretty good indicator that it's meant to be assembled by RALF or FLAP.
#### Further Improvements
RALF also has many other improvements over late-generation PAL family assemblers such as PAL8 which are not directly tied to driving the FPP or to relocatable code:
**INCOMPLETE**
* Expressions:
* Multiplication is `*` rather than `^`; this is possible because RALF offers the `ORG` pseudo-op to set the location counter, where PAL family assemblers use `*`
* Division is `/` rather than `%`, achieved by requiring whitespace before `/` if used to start a comment and disallowing spaces in expressions
* There is no "and" operator `&`
* Many new and changed pseudo-ops:
* Conditional assembly additions relative to PAL8: `IFPOS`, `IFNEG`, `IFSW`, `IFNSW`, `IFFLAP`, `IFRALF`
* `IFREF`: replaces `IFDEF` pseudo-op, having a superset of its functionality
* `LISTOF`/`LISTON`: stop and start listing output rather than the PAL family's `XLIST` pseudo-op
* `REPEAT`: assemble the following line multiple times
* `ADDR`: define address constant
* `E` and `F`: define floating-point constants
* FORTRAN IV feature support: `COMMON`, `COMMZ`, `ENTRY`, `EXTERN`, `FIELD1`, `SECT`, `SECT8`
[fpp8a]: https://archive.org/details/bitsavers_decpdp8pdpUsersManDec76_996770
[fpp12]: https://archive.org/details/bitsavers_decpdp12DE_2606247
### <a id="flap"></a>FLAP
The RALF assembler has a mode switch that causes it to generate absolute-addressed code, as PAL8 does. In this mode, it is called FLAP. This section will simply describe the differences in FLAP relative to RALF. These differences aside, FLAP shares the feature set of RALF.
The primary advantage FLAP has over RALF is that, because it is difficult to ascribe meaning to the "page" concept in a relocatable assembler, RALF doesn't support the `PAGE` pseudo-op, while FLAP does. FLAP also supports the PAL family's zero-page and current-page literal syntaxes, while RALF does not.
FLAP has some pseudo-ops that RALF does not:
* `S`: define single-word integer constant
### <a id="sabr"></a>SABR
As RALF is to OS/8's FORTRAN IV compiler, so the [Symbolic Assembler for Binary Relocatable programs](http://homepage.cs.uiowa.edu/~jones/pdp8/faqs/#langs) is to OS/8's FORTRAN II compiler.
SABR is a relative assembler, unlike PAL8 or FLAP, meaning that the OS/8 linking loader (`LOADER.SV`) adjusts all of the addresses in the assembled `*.RL` output to their final values.
|