Boriel’s Compiler

Tutorial by Luca Bordoni

This tutorial is oriented to ZX Spectrum enthusiasts who have experienced at least a Basic program project. It’s suggested to study the official Basic Programming manual first. Assembly knowledge is not required.

COMPILER BENEFITS

In modern times, many old-school programmers face with emulators and PC tools rather than the original classic machines, for an obvious advantage of time-saving.
Following this principle, Boriel’s ZX Basic (not to be confused with the standard Sinclair Basic) is a widely appreciated PC tool to achieve a quick conversion from a ZX Basic program to a perfectly working machine code block.
Furthermore, Boriel’s ZX Basic has another great functionality: a brand new built-in Basic syntax, which results very easy to learn for mid-experienced Basic programmers: a few minutes lesson right here in this article.
It’s possible to write our own code using a text editor and convert the text file directly through a single command line in our operative system’s prompt. We’ll talk about this step in the final chapter.

THE ZX BASIC SYNTAX

As said above, the ZX Basic must not be confused with the standard Sinclair Basic. In addition to being a compiler (which works from PC’s command-line prompt), the ZX Basic aims to be a modern Basic dialect, trying to keep many of the original Sinclair Basic features.
The ZX Basic tries to maintain compatibility as much as possible with Sinclair Basic, adding many cool new features. The point is: the standard Sinclair Basic syntax cannot be converted by the ZX Basic compiler.

Let’s see some of the most relevant differences between the two syntax:

VARIABLES DECLARATION

The first relevant difference is the variables management. Our habit was to assign a value to a variable (numeric value or string) and then handle it along the code. In ZX Basic any used variable has to be declared at the beginning of the program through the DIM instruction, while the classic LET is omitted:

10 REM Standard Sinclair Basic
20 LET a=5: LET b=40
30 LET n$=”Luke”
40 PRINT n$;” is “;a+b
REM Boriel’s ZX Basic
DIM a,b AS UBYTE
DIM n AS STRING
a=5: b=40: n=”Luke”
PRINT n;” is “;a+b

In this simple comparison, nostalgic Basic programmers can immediately note some interesting things: in the ZX Basic example, the AS UBYTE and AS STRING are new instructions, and the numeration is missing!

UBYTE and STRING represent two different variable types, clearly one for a numeric value and another for a string. Declaring the variable types is mandatory in ZX Basic. The most used variable types are:

UBYTE8bit variable, for values from 0 to 255;
UINTEGER16bit variable, for values from -32768 to 32767;
STRING16bit variable, used for strings (the $ symbol can be omitted).

About the numeration, ZX Basic treats the line numbers as labels: the classic Basic line numbers can be written without problems, but they will be ignored by ZX Basic, unless they are used as callouts, e.g. for the GOTO or GOSUB instructions.

LINE NUMBERS AND LABELS

This is a very interesting new feature. Treating a line number as a label (which can be also textual) can transform each Basic code block in a separate subroutine; the code will result very clean and every subroutine will be immediately traceable, just like it happens in modern programming languages:

10 REM Standard Sinclair Basic
20 GO SUB 60
30 PRINT “Press any key”
40 IF INKEY$=”” THEN GO TO 40
50 PRINT n$: STOP
60 LET n$=”Luke”: RETURN
REM Boriel’s ZX Basic
DIM n AS STRING  

 

GOSUB MyName

PRINT “Press any key”
10 IF INKEY=”” THEN GOTO 10
END IF
PRINT n: STOP

MyName:
n=”Luke”
RETURN

Even if the classic Basic code results more short, the readability of the ZX Basic is incomparable. Adding the advantage to use a simple text-editor, we’re now able to write a Basic program just like a normal text document! Let’s note further details:
the END IF instruction: closing an IF condition is mandatory in ZX Basic;
the missing of the $ symbol in the INKEY command: according to ZX Basic reserved words, both INKEY and INKEY$ are accepted.

GRAPHIC CHARACTERS

The ZX Spectrum has two types of graphics characters; block graphics (that is the graphic symbols which appear over the classic rubber keyboard, from key 1 to 8) and user-defined graphics (UDG, the editable 21 letters from A to U). The method for entering them into ZX Basic is the same as that found in the .bas file format created by Paul Dunn for his BASin.
UDG can be entered into the code with an escape before the letter that corresponds to the UDG. For the first UDG, for example, use \A.
Block graphics characters can be entered into code with a similar escape sequence. The \ followed by specific symbols is used to represent graphic blocks or other special characters.

Here’s a table of the most used combinations:

Block Syntax Description CHR$ Value
  \…… space, space CHR$(128)
  \…’ space, apostrophe CHR$(129)
  \’… apostrophe, space CHR$(130)
  \” apostrophe, apostrophe CHR$(131)
  \…. space, dot CHR$(132)
  \…: space, colon CHR$(133)
  \’. apostrophe, dot CHR$(134)
  \’: apostrophe, colon CHR$(135)
  \.… dot, space CHR$(136)
  \.’ dot, apostrophe CHR$(137)
  \:… colon, space CHR$(138)
  \:’ colon, apostrophe CHR$(139)
  \.. dot, dot CHR$(140)
  \.: dot, colon CHR$(141)
  \:. colon, dot CHR$(142)
  \:: colon, colon CHR$(143)
  \* asterisk CHR$(127)

EMBEDDED COLOR ATTRIBUTE CODES

ZX Spectrum programmers know that it’s possible to embed colour attributes directly into the program’s strings, instead of using the PAPER, INK, BRIGHT and FLASH commands. This practice isn’t a must, however it could strongly reduce the code length. Like the graphic codes, the ZX Basic attribute codes follow the same schema as Paul Dunn‘s BASin.
The escape sequences for control characters are as follows:
\{iN}INK colour N, where N is in the range 0 to 8;
\{pN}PAPER colour N, where N is in the range 0 to 8;
\{bN}BRIGHT N, where N is 0 or 1;
\{fN}FLASH N, where N is 0 or 1.
So, for example, an embedded control code for a bright red ink would be \{b1}\{i2}.
Note: colour value 8 is used to signify “transparent” (e.g. don’t change the ink/paper value in the square being printed).

THE COMPILER COMMAND LINE

The ZXB Compiler is the main function that will transform a ZX Basic program into a machine code block. All we have to do is to save the text file containing the ZX Basic code, and rename the extension to .bas in order to make it readable for the compiler.
The .bas file must be saved in the same ZX Basic directory where is located the zxb.exe file.

Let’s open our operative system prompt and move to the directory where both the zxb.exe and the .bas files are located.
For those who are unfamiliar with DOS commands
D: enter the local hard-drive D;
dir list directories and files from the current user position;
cd.. move backwards to the directory tree;
cd ZXB enter the directory (or subdirectory) named ZXB;
cd/ return back to the main root directory.

Here’re some ZXB command line examples to compile our .bas file:

Generates a .bin file at the memory address 30000:
zxb.exe myprogram.bas –org=30000
Generates a .tap file at the memory address 32000:
zxb.exe myprogram.bas –tap –org=32000
Generates a .tzx file at the memory address 50000:
zxb.exe myprogram.bas –tzx –org=50000

The magic is done!…

Consider that the first times it’s easy to encounter compiler errors – they’re always due to a wrong syntax in our Basic code. In that case, we have to check the Basic code in detail 🙁 This is the only “dark side” of this tool, even if the compiler error message should help to understand the specific Basic syntax problem.

Update ─ ZXB has an important parameter named heap which reserves a memory area to handle string variables. Find more useful informations in a post of mine in the ZXB Official Forum.