Skip to main content

Ada compiler targeting Z80 processor

Project description

uada80 - Ada Compiler for Z80/CP/M

Tests Pylint

An Ada compiler targeting the Z80 processor and CP/M 2.2 operating system, aiming for ACATS (Ada Conformity Assessment Test Suite) compliance.

Project Status

🔧 Alpha - Core compiler functionality implemented

Overview

uada80 is a compiler for the Ada programming language that generates code for the Z80 8-bit microprocessor running CP/M 2.2. The project aims to support a substantial subset of Ada 2012 and pass the ACATS conformance tests.

Target Platforms: CP/M 2.2 and MP/M II on Z80

  • CP/M 2.2: .com executables, single-threaded, programs load at 0x0100
  • MP/M II: .prl relocatable executables, preemptive multitasking via OS primitives
  • Access to BDOS for file I/O and console operations
  • Approximately 57K TPA on typical 64K system

Goals

  1. Compile Ada source code to Z80 assembly/machine code
  2. Generate CP/M .COM executables
  3. Pass ACATS test suite (or as many tests as feasible for Z80/CP/M)
  4. Generate efficient code suitable for CP/M systems
  5. Provide clear error messages and diagnostics

Inspiration

This project builds on experience from uplm80, a PL/M-80 compiler for Z80, reusing proven optimization techniques.

Features

Phase 1 (MVP) ✅

  • Project structure
  • Lexer and parser
  • Basic types: Integer, Boolean, Character
  • Procedures and functions
  • Control flow: if, case, loop, for
  • Arrays and records
  • Z80 code generation

Phase 2 (Expanded) ✅

  • Packages
  • Enumeration types
  • Access types (pointers)
  • Derived types
  • Unconstrained arrays
  • AST optimization

Phase 3 (ACATS Compliance) 🔧

  • Generics
  • Exception handling
  • Full attribute support
  • Representation clauses
  • Standard library (adapted for Z80)
  • ACATS test validation

Architecture

Ada Source → Lexer → Parser → AST → Semantic Analysis → Optimizer → Code Gen → Z80 Assembly

See docs/ARCHITECTURE.md for detailed design documentation.

Building

Requirements

  • Python 3.10 or later
  • um80_and_friends - Z80 assembler and linker (um80, ul80)
  • cpmemu - CP/M emulator for running compiled programs

Installation

# Clone the repository
git clone https://github.com/avwohl/uada80.git
cd uada80

# Create virtual environment
python3 -m venv venv
source venv/bin/activate

# Install in development mode
pip install -e ".[dev]"

# Install assembler/linker
pip install um80

Running Tests

pytest tests/ -v -o addopts=""

Usage

# Compile Ada to Z80 assembly
python -m uada80 hello.ada -o hello.asm

# Assemble and link
um80 -o hello.rel hello.asm
ul80 -o hello.com hello.rel -L runtime/ -l libada.lib

# Run on CP/M emulator
cpmemu --z80 hello.com

Example Programs

Hello World

with Ada.Text_IO;

procedure Hello is
begin
   Ada.Text_IO.Put_Line("Hello from Ada on Z80!");
end Hello;

Fibonacci

procedure Fibonacci is
   A, B, Temp : Integer;
   N : Integer := 10;
begin
   A := 0;
   B := 1;

   for I in 1 .. N loop
      Temp := A + B;
      A := B;
      B := Temp;
   end loop;
end Fibonacci;

See learn-ada-z80 for 99 example programs covering basics through tasking, generics, and applications.

Ada Tasking on MP/M II

Ada tasking (tasks, entries, rendezvous, protected types) runs on MP/M II using OS-native primitives for preemptive multitasking. On CP/M 2.2 (single-user), the runtime provides cooperative tasking stubs.

How It Works

Ada tasks become MP/M II subprocesses sharing one memory bank. The OS handles preemptive scheduling, and all inter-task communication uses BDOS queue operations:

Ada Construct MP/M II Primitive
Task creation P_CREATE (BDOS 144)
Entry call Q_WRITE (BDOS 139) - blocking send to queue
Accept statement Q_READ (BDOS 137) - blocking receive from queue
Select/else Q_CREAD (BDOS 138) - conditional (non-blocking) read
Protected object MX queue (mutual exclusion)
Delay P_DELAY (BDOS 141)
Abort P_ABORT (BDOS 157)

Building for MP/M II

# Compile Ada to assembly
python -m uada80 program.ada -o program.asm

# Assemble
um80 -o program.rel program.asm

# Link as PRL (relocatable for MP/M II)
ul80 --prl -p 0 -o program.prl program.rel -L runtime/ -l libada_mpm.lib

# Or link as COM (also works under MP/M)
ul80 -o program.com program.rel -L runtime/ -l libada_mpm.lib

Running on the MP/M II Emulator

The mpm2 emulator provides a full MP/M II environment with SSH terminal access:

# Start the emulator (up to 4 concurrent consoles)
mpm2_emu --no-auth -p 127.0.0.1:2222 -d A:disks/mpm2_system_work.img

# Connect via SSH
ssh -p 2222 user@localhost

# Upload and run
sftp -P 2222 user@localhost
put program.prl /A.0/PROGRAM.PRL

Runtime Libraries

Two runtime libraries are provided:

  • libada.lib - CP/M 2.2 runtime with cooperative tasking stubs
  • libada_mpm.lib - MP/M II runtime with OS-native preemptive tasking

Rebuild after changes:

cd runtime && make clean && make

Documentation

Compiler Documentation

CP/M Target Platform

Ada Language Specifications

  • specs/ - Ada language specifications and ACATS tests

Testing

ACATS End-to-End Execution

The ACATS 4.2 test suite is included in tests/acats/. Tests are compiled to Z80 assembly, assembled with um80, linked with ul80, and executed on cpmemu.

579 ACATS tests pass end-to-end (compile + assemble + link + execute on cpmemu):

$ pytest tests/test_acats_execution.py -o addopts=""
===== 257 failed, 579 passed, 624 skipped in 5197s =====
Result Count Description
Passed 579 Compiled, ran on cpmemu, output contains PASSED
Failed 257 Compiled and ran but produced wrong results (codegen bugs)
Skipped 624 Compile/link/timeout failures (multi-file deps, missing features)

ACATS Front-End

All 5,787 legal ACATS files pass parsing and semantic analysis:

$ pytest tests/test_acats.py -o addopts=""
======================= 5,787 passed in 248s =======================

learn-ada-z80 Programs

The learn-ada-z80 companion project has 99 example programs. 98 of 99 compile to Z80 assembly (full pipeline: parse, semantic analysis, lowering, code generation). One program fails due to a codegen bug with negative array bounds.

Execution Tests

End-to-end execution tests (compile + assemble + link + run on cpmemu) are in tests/test_execution.py:

pytest tests/test_execution.py -v -o addopts=""

Limitations

Due to the Z80's 8-bit architecture and limited resources:

  • Integer sizes limited to 8-bit and 16-bit (32-bit via library)
  • Software floating-point only (IEEE 754 double via float64.mac)
  • Reduced standard library
  • Tasking requires MP/M II (CP/M 2.2 provides stubs only)
  • Limited heap (small memory space)

Contributing

Contributions are welcome! Please:

  1. Fork the repository
  2. Create a feature branch
  3. Make your changes with tests
  4. Run the test suite
  5. Submit a pull request

License

This project is licensed under the GNU General Public License v2.0 - see LICENSE for details.

References

Related Projects

  • 80un - Unpacker for CP/M compression and archive formats (LBR, ARC, squeeze, crunch, CrLZH)
  • cpmdroid - Z80/CP/M emulator for Android with RomWBW HBIOS compatibility and VT100 terminal
  • cpmemu - CP/M 2.2 emulator with Z80/8080 CPU emulation and BDOS/BIOS translation to Unix filesystem
  • ioscpm - Z80/CP/M emulator for iOS and macOS with RomWBW HBIOS compatibility
  • learn-ada-z80 - Ada programming examples for the uada80 compiler targeting Z80/CP/M
  • mbasic - Modern MBASIC 5.21 Interpreter & Compilers
  • mbasic2025 - MBASIC 5.21 source code reconstruction - byte-for-byte match with original binary
  • mbasicc - C++ implementation of MBASIC 5.21
  • mbasicc_web - WebAssembly MBASIC 5.21
  • mpm2 - MP/M II multi-user CP/M emulator with SSH terminal access and SFTP file transfer
  • romwbw_emu - Hardware-level Z80 emulator for RomWBW with 512KB ROM + 512KB RAM banking and HBIOS support
  • scelbal - SCELBAL BASIC interpreter - 8008 to 8080 translation
  • uc80 - ANSI C compiler targeting Z80 processor and CP/M 2.2 operating system
  • ucow - Unix/Linux Cowgol to Z80 compiler
  • um80_and_friends - Microsoft MACRO-80 compatible toolchain for Linux: assembler, linker, librarian, disassembler
  • upeepz80 - Universal peephole optimizer for Z80 compilers
  • uplm80 - PL/M-80 compiler targeting Intel 8080 and Zilog Z80 assembly language
  • z80cpmw - Z80 CP/M emulator for Windows (RomWBW)

See Also

  • GNAT - For production Ada development, use GNAT or other mature Ada compilers

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

uada80-0.4.0.tar.gz (627.1 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

uada80-0.4.0-py3-none-any.whl (529.2 kB view details)

Uploaded Python 3

File details

Details for the file uada80-0.4.0.tar.gz.

File metadata

  • Download URL: uada80-0.4.0.tar.gz
  • Upload date:
  • Size: 627.1 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for uada80-0.4.0.tar.gz
Algorithm Hash digest
SHA256 0fb1d704647fab86c24921000cb737afbe21112fd0884a9b7ca984ed62d71017
MD5 b5bd9fe0a11cb0c09813268e92cc9870
BLAKE2b-256 d9886179258df75068f3af4c8561dcbec11ba16268c99ebc99e38525ed6af11a

See more details on using hashes here.

Provenance

The following attestation bundles were made for uada80-0.4.0.tar.gz:

Publisher: publish.yml on avwohl/uada80

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file uada80-0.4.0-py3-none-any.whl.

File metadata

  • Download URL: uada80-0.4.0-py3-none-any.whl
  • Upload date:
  • Size: 529.2 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for uada80-0.4.0-py3-none-any.whl
Algorithm Hash digest
SHA256 fd31a663ffb29103da3ce3def13db8f04127aa30ecaa7b804eaed02b0de7bbb9
MD5 9ed1ef14aadaa81c54e51d281b1b8bd8
BLAKE2b-256 e5dc30fa88603f86d34bb355d2c1113a8db206c8c38f53ae97bb227f9aaa842e

See more details on using hashes here.

Provenance

The following attestation bundles were made for uada80-0.4.0-py3-none-any.whl:

Publisher: publish.yml on avwohl/uada80

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page