Inside OS: BBC Micro ROM Routines

The following article was written by Roger Cullis, and published in PRACTICAL COMPUTING February 1985, Pages 122- 125.

[This text was OCR’ed from the pages of the original article. Unfortunately, the font of the original table of OS entry points was impossible to OCR accuratlely. In the extremely limited time I have for this project, I have done my best to clean up the text by hand. Undoubtedly, many errors remain.]

[The original article was accompanied by the following notice]


This article summarises the operation of the BBC Micro and where the routines are to be found, and is intended to help users to write programs which interact fully with the built-in software. But you shduld remember that the source code and object code of ROM routines are the subject of copyright and may not be used without the copyright owner’s permission. Although you may freely call them from programs running on the computer, you cannot extract or copy them for your own software.

[The main text of the article was as follows]

Inside Os: Roger Cullis dissects the BBC Micro’s operating-system ROM routines.

IN ORDER to write software which makes full use of the facilities provided by a computer, it is vitally important to understand the computer’s components and how they are controlled. The BBC Micro is a complex machine which not only drives a wide variety of peripheral devices through built-in interfaces but can also be connected to an increasing number of second processors to enhance its computing power. In many cases these resources can only be exploited by direct access to the utilities and routines which are an integral part of the languages and operating system provided in the machine’s firmware.

The BBC Micro is built round the Mostek 6502 eight-bit microprocessor. In its standard form it has 32K of ROM and either 16K of RAM as the model A, or 32K as the model B. It was designed as an expandable system and so is primarily an I/O device. It can service a variety of peripheral devices such as serial and parallel printers, local area networks, disc drives and speech synthesisers. For this reason blocks of memory hake to be reserved for specific applications. For example, in order to provide buffers for transfer of data between the computer and the floppy-disc controller, nearly 3K of read/write memory is required. Adding Econet takes another 0.5K, and speech
synthesis a further 1K.

Memory map

The 6502 microprocessor has a 16-bit address bus, which means that it can access a 216 or 64K memory bank. Of this, 32K is ROM and memory-mapped I/O and, on the model B, 32K is RAM — 16K on the model A. The arrangement of memory is shown in figure 1. RAM occupies the lower 32K addresses from &0000-7FFF and ROM occupies two 16K blocks from &8000-BFFF and &C000-FFFF. The lower ROM block is allocated to utilities, including Basic, the disc filing system, word processors such as View, or graphics extensions.

Up to 16 different 16K ROMs can be connected to this address space, although only one may be active at a given time. The machine operating system or a control program ensures that the appropriate page ROM is switched in when it is required. This operating system, which controls the running of the computer, occupies the upper ROM block. &C000-FFFF.

Most of the memory space contains operating code, but part of the address allocation is devoted to memory-mapped I/O. If an instruction is written to one of these addresses, it is not stored but passed directly to the peripheral device to which the address is allocated.

The OS, the paged ROMs and I/O devices all require read/write memory to store data during operation. This memory may be set aside exclusively for the purpose, as is the case with the soft-key buffer, &0B00-0BFF, which holds the strings called up by the user-definable keys. Alternatively, it may be shared among several chips, as with the paged ROMs’ public workspace or the filing system zero-page locations, or it may be allocated dynamically during the operation of a program. An example of this dynamic allocation is found in the Basic stack, which acts as a temporary store, and expands and contracts according to the needs of the program.

The screen buffer where the computer stores what is currently displayed on the screen occupies the highest region of RAM. Its size depends on the mode which is being displayed. Mode 7, Teletext mode, occupies only 1K, whole mode 0 requires 20K.

Page 0, addresses &0000-00FF, is used for dynamic storage during operation, and page 1, &0100-01FF, is allocated to the 6502 stack. The operating system takes pages 2 and 3; pages 4 to 7 are given to the current language ROM, or to interfacing routines if a second processor is active. Pages 8 to C, addresses &0800-0CFF, are devoted to operating system buffers for input and output and for storage of soft- key definitions and sound envelopes. Page D, addresses &0D00-0DFF, contains the non-maskable interrupt routines and parameters such as the current paged ROM status and extended vectors.

The operating system ROM contains the routines to start up the computer when it is switched on or reset by pressing the Break key. It also supervises the chips which control the peripheral devices and handles the flow of data to and from them.

The BBC Micro can have a variety of different filing systems, such as disc, Econet and Telesoft, for data storage and retrieval. Mostly these are in the form of separate paged ROMs, but the two simplest are built into the OS ROM. They are the ROM filing system, which can be used for data retrieval only, and the cassette filing system, which only implements a limited subset of the full filing- system operations.


OS routines

There have been several versions of the OS, commencing with version 0.1. Each successive version has implemented more features, culminating in the current OS 1.2 which has remained unchanged for some time. The general layout of the operating system is shown in the memory map. There are several well-defined features which serve quite independent functions.

The computer is able to control a wide variety of peripheral devices by using dedicated peripheral controller chips. For instance, disc storage is controlled by an Intel 8271 floppy-disc controller chip, Econet by a Motorola 6854 advanced data link controller, and the VDU by a Motorola 6845 cathode-ray tube controller. These chips each have several registers which need to be initialised, and they expect instructions in a pre-defined format.

The look-up tables and control routines to meet these needs are stored in the operating-system ROM or, in the case of filing systems, in a separate paged ROM. The first part of the OS is devoted to look- up tables of parameters required to set up and run the visual display, starting with the character fount look-up table at &C000-C0BF.

Text characters are displayed on an eight by eight matrix. The fount for each character is stored in ascending ASCII order as an eight-byte block, each byte representing one line of the matrix. In each byte, a bit set to I represents a dot that is to be displayed. For example, the symbol +, ASCiI code 2B, held in ROM at &C058-C05F, is displayed as shown in table 1.


&C300 contains an unconditional jump to VDU initialisation routines, and at &C303 there are the BRK embedded messages. &C31F-C332 contains the byte mask look-up tables used in processing pixels for graphics display.

&C333-C353 and &C354-C374 contain the two-byte address of the entry point of the VDU routines, indexed by VDU code. The high byte held in &C354-C374, is modified so that the number of associated parameters can be derived from it. The parameters are then assembled in a VDU queue. The low byte is held in &C333-&C353.

&C375-C3E6 holds the *640 and *40 multiplication tables, which determine the number of characters from the origin in text display modes. &C3E7-C3F6 holds look-up tables for default text window size, indexed by screen mode.

&C3F7-C447 contains look-up tables for various display parameters. Several of these tables overlap one another, and some serve a dual purpose. &C441-C444 holds the sound pitch offset. If more than one channel is programmed to output the same frequency, it is not possible to distinguish by ear that a second or third channel is active. To avoid this effect, the pitch of channels 2 and 3 is offset slightly in the same way that piano strings are slightly detuned. &C447-C458 holds the screen buffer size and location look-up tables. &C463-C468 holds the character position determination look-up tables. &C469-C4A9 holds the initial register settings for 6845 CRTC chip.

&C4AA-C4B5 holds the look-up tables for alternative entry points and branch loops in VDU processing routines. &C4B6-C4B9 holds the character definitions for the non-standard ASCII codes used in mode 7. The soft-character RAM allocation is done by &C4BA-C4BF.

The VDU routines are held in &C4CO-&D93F, starting with the VDU command handler. Current VDU status is stored as a series of flag bits at zero-page location &D0. On input of a VDU command, permissible action is checked against VDU status and the entry point of the associated routine ascertained from a look-up table.

The value of the status bit may be determined with Osbyte 75. The significance of the bits is
0 — enable printer
1 — disable scrolling
2 — enable paged mode
3 — enable software scrolling
5 — enable text at graphics cursor
6 — enable cursor editing
7 — disable VDU

The command is processed and converted into instructions which are stored in corresponding registers of the 6845 CRTC to modify the display. Parameters associated with a VDU command, such as VDU25,k,X,Y are stored as a VDU queue and processed in sequence.

Graphics display is controlled by manipulation of graphics co-ordinates. A region of low RAM is set aside as graphics co-ordinate workspace. Values such as the previous position of the graphics cursor are stored here. It is also used, for example, as a co-ordinate store in the Plot and Fill routines.

Colour processing is controlled by a palette which stores the relationships between logical and physical colours. It is located in the video ULA chip.

The page 2 setup default values, held at &D940-D9CC, are copied by the Reset routine to page 2.

This article forms part of a book to be published by Losco Ltd, P0 Box 4, Cranleigh, Surrey GU6 8BQ, price £11.95 plus £1.50 post and packing. A further instalment will appear in next month’s Practical Computing.

[Unfortunately, I do not have a copy of the follow-up article. I believe this book to have been “Within the BBC Microcomputer” published in 1985. ISBN:0948203005.]

[The article was accompanied by the following table]

VDU display setup parameters and routines.
C000 C2FF character font lookup table
C300 initialise system
C303 ‘BBC Computer’ embedded message
C312 ‘16K + BELL’ embedded message
C317 ‘32K + DELL’ embedded message
C31F C32E 4-colour MODE byte mask lookup table
C32F C332 16-colour MODE byte mask lookup table
C333 C353 VDU entry point lo lookup table
C354 C374 VDU entry point hi parameter lookup table
C375 C383 *640 multiplication table (40-,80-column MODEs)
C385 C3E5 *40 multiplication table (teletext MODE)
C3E7 C3EE text window – bottom row lookup table
C3EF C3F6 text window – right-hand column lookup table
C3F7 C3FE video ULA control register setting
C3FF C406 number of bytes per character for each display MODE
C407 C408 mask table for 2-colour MODEs
C409 C40C mask table for 4-colour MODEs
C40D C414 mask table for 2-colour MODEs, font flag mask table
C4l4 C41B number of colours minus one for each MODE
C418 C425 6COL PLOT options processing lookup table
C424 C425 2-colour MODE colour parameter lookup table
C426 C429 4-colour MODE colour parameter lookup table
C42A C439 16-colour MODE colour parameter lookup table
C430 C44l display MODE pixels/byte -l lookup table
C440 C447 screen display memory index lookup table
C44l C444 sound pitch offset by channel lookup table
C44B C44E CRTC setup parameter
C44F C453 CRTC setup parameter
C447 C458 VDU section control numbers
C459 C4SD MSB of memory occupied by screen buffer
C45E C462 MSB of first location occupied by screen buffer
C463 C465 number of bytes/row
C466 C468 row multiplications table pointer lo lookup table
C469 C46D CRTC cursor end register setting lookup table
C46E C479 6845 registers 0-11 for MODEs 0-2
C47A C485 6845 registers 0-11 for MODE 3
C486 C49l 6845 registers 0-11 for MODEs 4-5
C492 C49D 6845 registers 0-11 for MODE 6
C4A93 C4A9 6845 registers 0-11 for MODE 7
C4AA C4AD VDU routine vector addresses
C4AE C4B1 VDU routine branch vector address lo
C4B2 C4B5 VDU routine branch vector address hi
C4B6 C4B9 teletext character conversion table
C4BA C4BF soft character RAM allocation
VDU routines.
C4C0 check VDU command, if normal character, PRINT it
C511 VDU 00 – do nothing
C511 VDU 06 – enable VDU drivers
C511 YDU 27 – do nothing
C53B VDU 01 – send next character to printer only
C55E confirm input, output cursors not separated
C565 prepare cursor character for display
C568 interchange cursors, set CRTC address registers, toggle VDU screen status
C588 get graphics cursor printing status bit
C58D YDU 14 – paged mode on
C596 YDU 02 – enable printer
C59B VDU 21 – disable VDU drivers or delete current line
C59D set VDU status or, if zero, reset default
C5A1 VDU 03 – disable printer
C5A6 YDU 15 – paged mode off
C5A8 reset specified VDU status bits
C5AD VDU 04 – write text at text cursor
C5B9 VDU 05 – write text at graphics cursor
C5C5 VDU 08 – backspace one character
C621 move graphics cursor one position
C65B VDU 11 – move cursor up one line
C664 VDU 09 – advance tent cursor if enabled
C684 set text cursor to new line, scrolling if required
C6AC clear text line to background, calculate offset, set CRTC address
C6AF calculate offsets of character row, set text cursor address register
C6B4 paged mode scrolling
C6F0 VDU 10 – move cursor down one line (line feed)
C6FA VDU 28 – define test window
C735 OSWORD 09 – read pixel value
C74B OSWORD 0B – read palette
C759 VDU 12 – clear test area
C779 VDU 30 – home text cursor to top left
C787 VDU 31 – move test cursor to 0,9
C7AB interchange current tent cursor with value from general graphics coordinate workspace
C7AF VDU 13 – move cursor to start of current line
C7C0 VDU 16 – clear graphics area
C7F9 VDU 17 – define text colour
C7FD VDU 18 – define graphics colour
C839 VDU 20 – restore default logical colour
C88F save colour index and define logical colour
C892 VDU 19 – define logical colour
C89E set logical/physical colour relationship
C8E0 OSWORD OC – write palette
C8EB VDU 22 – select screen MODE
C8F1 VDU 23 – re-program display character or write to CRTC
C938 process unrecognised VDU command
C93F setup CRTC
C951 set 6845 cursor register to previous value
C954 set 6845 cursor parameters register = A-register
C958 write parameter from VDU queue to specified CRTC register
C95E set specified CRTC register
C98C VDU 25 – PLOT k,X,Y
C994 backspace one row, set CRTC screen start address registers
C9A4 advance one row, set CRTC screen start address registers
C9B3 set 6845 CRTC screen start address registers
C9BD VDU 26 – restore default windows
C9F6 save 6845 test cursor position address, set corresponding 6845 registers
CA02 set 6845 text cursor address registers
CA0E set 6845 CRTC registers indexed by 9-register
CA2B write two bytes to consecutive 6845 registers
CA39 VDU 24 – define graphics window
CA88 set test window width according to character size
CAA2 VDU 29 – define graphics origin
CAAC VDU 127 – backspace and delete
CAD4 add number of bytes in row to display address
CAE0 zero POINT line counter and scroll if enabled
CAE3 scroll if enabled
CB14 zero page PRINT line counter
CB1D initialise video display parameters and workspace
CB33 set up video display parameters table
CBC1 initialise screen display parameters
CBF3 OSWORD 0A – read character definition
CC02 character font definition indirection vector lookup table
CCF5 process unrecognised VDU command
CCF8 scroll back one row, check if wrap-round seeded
CD07 OSBYTE 14 – explode soft character ROM allocation
CD3F move text cursor to next line
CD6A process character for display
CD77 recover A-register, processor status from stack
CD7A process cursor character for display
CDA4 soft scroll one line
CDCE set scan line address, scroll back until counter zero
CDDA interchange current test cursor with value from coordinate workspace
CDDE interchange two Page 3 bytes indexed by X,Y
CDE2 interchange old and current graphics cursors
CDE4 interchange old graphics cursor with value from coordinate workspace
CDE6 interchange four-byte block indexed by X,Y in Page 3
CDFF scroll text one line
CE2A set scan line address source line address
CE38 copy source line to scan line
CE5B determine test window height, if non-zero do CR
CE6E set text cursor U-coordinate to left-hand side of text window
CE73 add character to scan line
CEE8 confirm cursor in text window, calculate character row offset
CF06 calculate address of text cursor
CF63 PRINT character at graphics cursor
C046 home graphics cursor
CFAD set graphics cursor X-coordinate to left-hand column
CFB7 set up character definition and display character
CFBF display character
CFDC insert teletext character in scan line, convert if required
D03E set up character definition pointers
D060 process PLOT command
D0B3 set Page 0 colour processing bytes
D0D9 move graphics cursor to absolute position
D0DC copy current graphics cursor coordinates from VDU queue
D0DE copy four bytes from VDU queue
D0E3 set colour of point at current graphics cursor
D0EB omit last paint in line
D0F0 set colour of current graphics point, save to graphics scan line
D0F3 process colour and save to graphics scan line
D104 process colour of current graphics point
D10D check current graphics cursor position with respect to to window boundaries
D10F check position of indexed graphics coordinates with respect to window boundaries
D128 check current graphics point position with respect to window boundaries
D149 adjust coordinates according to display MODE
D14D adjust PLOT coordinate according to display options
D176 adjust coordinate for relative/absolute PLOT, divide it by 2
D1AD divide PLOT coordinate by 2
D1B8 calculate graphics cursor offset according to display MODE
D1D5 adjust cursor coordinates, calculate cursor offset
D1E3 use graphics origin to calculate cursor offset
D1ED execute PLOT command
D214 set up branch loops, PLOT parameters
D2E3 set scan byte if appropriate, adjust coordinates and scan position
D3D3 decrement graphics cell top line address by one raw, set Y=7
D3ED set graphics cask left-hand colour cask, increment graphics cell by use line
D3FD set graphics mask right-hand colour cask, decrement graphics cell by one line
DA0D calculate graphics cursor relative to graphics window
D411 calculate graphics coordinates relative to specified paint
D418 calculate graphics coordinate offset
D42C if necessary, set up working coordinates, evaluate difference,
D42C make positive, divide Y by 2
D459 take modulus of working coordinate, divide Y coordinate by 2
D467 change sign of working coordinate, if negative
D47C copy 8 Page 3 bytes to new location (indexed by X,Y)
D480 copy two Page 3 bytes to coordinate workspace
D482 copy two Page 3 bytes to new location (indexed by X,Y)
D486 copy current graphics cursor to coordinate workspace
D488 copy current graphics cursor to new Page 3 location (indexed by Y)
D48A copy four Page 3 bytes to new location (indexed by X,Y)
D49B fore 2s complement of number in Y-,A-registers
D4AA if byte legal, process colour, else, discard it and cove cursor
D4BF omit last point in inverting actions
D506 PLOT with dotted line
D545 move graphics cursor and calculate offset for MODE
D548 get current graphics byte cask, set colour, save byte to scan line
D574 reset graphics byte and save to scan line
D592 check X coordinate from VDU queue against graphics window boundary
D5AC process working I coordinate, transfer to YOU queue
D5CC OSWORD 0D – read last two graphics cursor positions
D5DE OSWORD 0D – read old and current graphics position
D5D5 transfer four bytes index by 4-register to OS buffer
D5EA PLOT and fill triangle
D632 11 old graphics cursor greater than new PLOT point, interchange thee
D636 of source coordinate greater than destination coordinate, interchange points
D647 OSBYTE 86 – read text cursor position (POS and VPOS)
D658 process coordinates and PLOT points til target reached
D6A2 set and arrange working coordinates…
D6A6 arrange working coordinates, process colour mask, save to scan line
D70E recover target coordinates from stack
D774 derive coordinates for next point in triangular PLOT
D7AC add stored value to working coordinate, increment counter if necessary
D7C2 OSBYTE 87 – read character at text cursor position
D808 derive character definition from displayed character
D839 determine logical colour of specified point
D85D get coordinates from YOU queue, set up graphics line address, colour mask
D85F set coordinate source index, set up line address, colour mask
D864 set up graphics line address
D8CE if enabled, PRINT at cursor position
D905 if test cursor enabled, read character
D918 reset CRTC cursor register, cursors together, enable screen, set 4-register to 80
D923 OSBYTE 85 – read HIMEM
8926 OSBYTE 85 – read address of screen buffer for MODE
Page 2 setup – default values.
D940 D976 Page 2 vectors default settings
D976 D9CC MOS variables default settings


4 Responses to Inside OS: BBC Micro ROM Routines

  1. childrens storage bins…

    […]Inside OS: BBC Micro ROM Routines « All Wrong[…]…

  2. dehumidifier says:

    dehumidifier reviews…

    […]Inside OS: BBC Micro ROM Routines « All Wrong[…]…

  3. stickers says:


    […]Inside OS: BBC Micro ROM Routines « All Wrong[…]…

  4. […] Inside OS: BBC Micro ROM Routines | All Wrong – Oct 15, 2007 · This entry was posted on Monday, October 15th, 2007 at 8:51 pm and is filed under BBC Micro, Retro Computing. You can follow any responses to this entry …… […]

Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

%d bloggers like this: