Skip to navigation

BBC Micro Elite

Building Elite from the source

The original Elite source code for the BBC Micro Model B is split across a number of separate BBC BASIC files, each of which assembles and saves a binary file. These files are then concatenated into the final game binaries by the "Big Code File" source.

The annotated sources on this site have been organised in a couple of different ways, one of which follows this original structure (see the "Elite source code by file" section in the site menu). The accompanying GitHub repository follows a similar structure, so let's take a look at the various files involved in building Elite from the source.

I am indebted to Kieran Connell for the following, who designed this build pipeline and wrote the Python programs as part of his epic elite-beebasm project. Without his original project, none of this would have ever happened...

The Elite build pipeline
------------------------

The following files together form a build process that creates a fully playable version of Elite from the source code. This is how the source code breaks down:

  • elite-loader.asm contains the source for the game loader (see the annotated source here: Loader)
  • elite-source.asm contains the main source code for Elite (see the annotated source here: Workspaces, Text tokens, Elite A, Elite B, Elite C, Elite D, Elite E, Elite F, Elite G and Ship blueprints)
  • elite-bcfs.asm concatenates the individual binaries into one big code file (see the annotated source here: Big Code File)
  • elite-checksum.py computes checksums and applies the copy protection
  • elite-disc.asm creates the final disc image
  • crc32.py verifies the build

All these files are also available in the repository.

The build process uses a five-stage pipeline. This pipeline is based on the original build process from the source disc, but it uses the BeebAsm assembler and Python instead of BBC BASIC.

The end product is an SSD disc image file that can be loaded by a BBC Micro with DFS, or an emulator like JSBeeb or BeebEm. The code produced is identical to the released version of the game.

Each stage of the build pipeline uses one of the source files from the sources folder, so let's look at what's involved.

1. Compile the main game with elite-source.asm
----------------------------------------------

BeebAsm loads elite-source.asm and creates the following files:

  • output/ELTA.bin
  • output/ELTB.bin
  • output/ELTC.bin
  • output/ELTD.bin
  • output/ELTE.bin
  • output/ELTF.bin
  • output/ELTG.bin
  • output/PYTHON.bin
  • output/SHIPS.bin
  • output/WORDS9.bin

elite-source.asm contains the main source code for Elite. It is based on the original BASIC source files, converted to BeebAsm assembler syntax. In the original build, this is what happens:

  • ELITEA produces the ELTA binary
  • ELITEB produces the ELTB binary
  • ELITEC produces the ELTC binary
  • ELITED produces the ELTD binary
  • ELITEE produces the ELTE binary
  • ELITEF produces the ELTF binary
  • ELITEG produces the ELTG binary
  • DIALSHP contains the PYTHON binary
  • SHPPRTE produces the SHIPS binary
  • GENTOK produces the WORDS9 binary

So the BeebAsm process mirrors the original compilation steps pretty closely.

2. Concatenate the game code and compile the header with elite-bcfs.asm
-----------------------------------------------------------------------

BeebAsm then loads elite-bcfs.asm, which reads the following files:

  • output/ELTA.bin
  • output/ELTB.bin
  • output/ELTC.bin
  • output/ELTD.bin
  • output/ELTE.bin
  • output/ELTF.bin
  • output/ELTG.bin
  • output/SHIPS.bin

and creates the following:

  • output/ELTcode.unprot.bin
  • output/ELThead.bin

elite-bcfs.asm is the BeebAsm version of the BASIC source file S.BCFS, which is responsible for creating the "Big Code File" - i.e. concatenating the ELTA to ELTG binaries plus the SHIPS data into a single executable called ELTcode.

There is also a simple checksum test added to the start of the ELTcode file, but at this stage the compiled code is not encrypted, which is why it has unprot in the name. The original BASIC files contain encryption code that can't be replicated in BeebAsm, so we do this using Python in step 4 below.

3. Compile the loader with elite-loader.asm
-------------------------------------------

Next, BeebAsm loads elite-loader.asm, which reads the following files:

  • images/DIALS.bin
  • images/P.ELITE.bin
  • images/P.A-SOFT.bin
  • images/P.(C)ASFT.bin
  • output/WORDS9.bin
  • output/PYTHON.bin

and creates the following:

  • output/ELITE.unprot.bin

This is the BeebAsm version of the BASIC source file ELITES, which creates the executable Elite loader ELITE. This is responsible for displaying the title screen and planet, loading the dashboard image, setting up interrupt routines, configuring a number of operating system settings, relocating code to lower memory (below PAGE), and finally loading and running the main game.

The loader incorporates four image binaries from the images folder that, together with the code to draw the Saturn backdrop, make up the loading screen. It also incorporates the WORDS9 and PYTHON data files that contains the game's text and the Python ship blueprint.

There are also a number of checksum and protection routines that EOR the code and data with other parts of memory in an attempt to obfuscate and protect the game from tampering. This can't be done in BeebAsm, so we do this using Python in the next step.

4. Calculate checksums and add encryption with elite-checksum.py
----------------------------------------------------------------

Next, the pipeline runs the Python script elite-checksum.py, which reads the following files:

  • output/ELTA.bin
  • output/ELTB.bin
  • output/ELTC.bin
  • output/ELTD.bin
  • output/ELTE.bin
  • output/ELTF.bin
  • output/ELTG.bin
  • output/ELThead.bin
  • output/SHIPS.bin
  • output/ELITE.unprot.bin

and creates the following:

  • output/ELTcode.bin
  • output/ELITE.bin

There are a number of checksum and simple EOR encryption routines that form part of the Elite build process. These were trivial to interleave with the assembly process in the original BASIC source files, but they've been converted into Python so they can run on modern machines (as not too many modern computers support BBC BASIC out of the box). Kieran Connell is the genius behind all this Python magic, so many thanks to him for cracking the code.

The script has two parts. The first part generates an encrypted version of the ELTcode binary, based on the code in the original S.BCFS BASIC source program:

  • Concatenate all the compiled binaries
  • Compute the checksum for the commander data
  • Poke the checksum value into the binary
  • Compute the checksum for all the game code except the header
  • Poke the checksum value into the binary
  • Encrypt all the game code except the header using a cycling EOR value (0-255)
  • Compute the final checksum for the game code
  • Output the encrypted ELTcode binary

The second part implements the checksum and encryption functions from the ELITES BASIC source program to generate an encrypted ELITE binary:

  • Reverse the bytes for a block of code that is placed on the stack
  • Compute the checksum for MAINSUM
  • Poke the checksum value into the binary
  • Compute the checksum for CHECKbyt
  • Poke the checksum value into the binary
  • Encrypt a block of code by EOR'ing with the code to be placed on the stack
  • Encrypt the code destined for lower RAM by EOR'ing with the loader boot code
  • Encrypt binary data (dashboard etc.) by EOR'ing with the loader boot code
  • Output the encrypted ELITE binary

At the end of all this we have two encrypted binaries, one for the loader and another for the main game.

5. Assemble a bootable disc image with elite-disc.asm
-----------------------------------------------------

Finally, BeebAsm loads elite-disc.asm, which reads the following files:

  • output/ELTcode.bin
  • output/ELITE.bin

and creates the following:

  • elite.ssd

This script builds the final disc image. It copies the assembled ELITE and ELTcode binary files from the output folder to the disc image, and is passed as an argument to BeebAsm by the Makefile when it creates the disc image. The BeebAsm command is configured to add a !Boot file that *RUNs the ELITE binary, so the result is a bootable BBC Micro disc image that runs the cassette version of Elite.

The disc image is called elite.ssd, and you can load it into an emulator, or into a real BBC Micro using a device like a Gotek.

Doing the above on a modern computer
------------------------------------

For more details on how to run this process on a modern computer, and for all the source and build files you need to run this on your PC, Mac or Linux box, see the accompanying GitHub repository.