CMOC

Permalink: http://sarrazip.com/dev/cmoc.html

By Pierre Sarrazin

CMOC is a 6809-generating cross-compiler for a large subset of the C language. It generates assembly language code for the Motorola 6809 processor and targets the Tandy Color Computer, the Dragon computer, the Vectrex video game console, the Thomson MO and TO computers, and the OS-9 and FLEX operating systems. It runs under GNU/Linux and other Unix-like environments like Darwin, WSL and Cygwin. It requires the LWTOOLS assembler (lwasm) and linker, by William Astle.

The most significant difference between CMOC and a complete C compiler is the absence of a complete C standard library. Color Basic. CMOC comes with a small library that serves as a starting kit.

For a summary of the C features that are supported or not by CMOC, see the C Language Features section of the manual.

The November 19, 2022 episode of CoCoTALK features an 8-minute discussion of this page. The February 25, 2023 episode of The CoCo Nation features a 5-minute discussion that starts with BGraph, a library to draw graphics.

CMOC is free software distributed under the GNU General Public License, version 3 or later, except for the files of the USim 6809 simulator by Ray Bellis, which is used for testing.

The current version is 0.1.89. It was released on 2024-10-16.

Release notes for 0.1.89:

Release notes for 0.1.88:

  • Zero-length arrays are now supported.
  • Added #pragma push_calling_convention __gcccall and #pragma pop_calling_convention to help set the calling convention of several functions at once.
  • Fixed bugs and some performance problems with __gcccall functions.
  • Added command-line option --cpp=<path> to allow the cmoc invocation to specify an alternate C preprocessor.
  • Added command-line option -Waccept-word-sized-return-type-mismatch to make the compiler only issue a warning instead of an error when a return statement mismatches the function's return type, but both types are a word, a pointer or an array. This may help port K&R code.

Release notes for 0.1.87:

  • Experimental support for the GCC6809 calling convention, which can use the B and X registers to pass parameters to a function.
  • An OS-9 interrupt function is now allowed to receive a parameter, which helps implement a signal handler that receives the signal number in B.
  • New command-line option -funsigned-char to specify that char is unsigned by default.
  • New command-line option --initial-s=hex-address, which generates an immediate-mode LDS instruction as the first instruction of the executable.
  • New command-line option --lwasm-pragma=pragmas that allows specifying the pragma(s) passed to lwasm's --pragma option.
  • Several minor bug fixes, improvements and optimizations.

Release notes for 0.1.86:

  • Added experimental command-line option --mc6839, which allows single-precision floating point operations, by adding the 8k image of Motorola's MC6839 ROM. Those operations are then independent of Color Basic's floating point routines, and Basic does not have to be present. When using this option, the use of the %f placeholder in a printf() statement requires calling enable_printf_float() at the beginning of main().
  • Added strspn(), strcspn(), strtok(), strpbrk(), strrchr().
  • Added sbrk() and sbrkmax() for OS-9.
  • Several minor bug fixes, improvements and optimizations.

I can be contacted (in French or English) at sarrazip at sarrazip dot com.

Questions regarding the Vectrex support should be directed to Johan Van den Brande.

Questions regarding the Thomson support should be directed to Dino Florenzi.

Questions regarding the FLEX support should be directed to Ulrich Boetzel. For more information about FLEX, see the FLEX User Group page. For a FLEX emulator, see Flexemu.

Download

Compiler

See SHA512 signatures of these and other files.

Libraries and sample programs

The following libraries and programs were written by me, unless otherwise stated. The "🐲" icon means that the program or library is compilable and usable on the Dragon computer, at least in part.

CoCoSDC Commander (by Michael Furman)

A cross-platform tool (DECB, OS-9, FLEX, FUZIX) for commanding a CoCoSDC. It is written in K&R C and the DECB version is compiled with CMOC.

CROSS-LIB (by Fabrizio Caruso) 🐲

A retro-hardware abstraction layer for coding "universal" demos, games and programs for hundreds of mostly 8-bit systems.a

Space Bandits (by Jamie Cho)

A work-in-progress video game based on Space Invaders and developed with Dynosprite, an object oriented game engine for the CoCo 3 by Richard Goedeken.

newcmd (0.1.1) (Public domain)

A program that replaces Basic's SKIPF command with a different command that does something else, and is implemented in C. The new command can interpret its arguments and store output values that the Basic program can use. Published 2022-03-05.

decbfile (0.1.10, 2024-08-28) (Public domain)

A library that implements read/write access to files on a floppy disk in the Disk Extended Color Basic format. (Not necessarily compatible with DECB replacements.) (Not compatible with the Dragon format.)

Version 0.1.10 removes stray UTF-8 characters from test program w.c, and fixes a typo in rdwrdemo.asm. Version 0.1.9 fixed a bug with decbfile_runDOSLoader() that allowed Basic's IRQ service to corrupt memory around $0985, which would typically cause a crash. It also added decbutil_readFileToDynamicMemory(), which allows a callback to indicate at which address the file must be loaded, and to specify the number of file sectors to load.

  • decbfile uses Disk Basic's sector routine by default, but can be made to use a stand-alone sector routine, therefore making Basic's presence unnecessary. (Note that this stand-alone routine comes with CMOC, not with decbfile.)
  • decbfile could be made to work with systems other than the Tandy floppy controller by making the library use an alternate sector routine. The Tandy FAT and granule-based floppy format would still be assumed however.
  • For quick development, it provides functions decbutil_readFileToMemory() and decbutil_writeMemoryToFile(), which read or write a file to or from memory in a single call, without requiring Disk Basic.
  • It provides decbfile_runDOSLoader(), which runs a loader that loads an application that can use the full 64k of the CoCo. This loader is typically launched using the DOS command in DECB. The caller must provide the application filename, some addresses, and some callbacks that will be invoked to let the caller show the progression.
  • It provides a demo that shows how to use a driver made with decbfile to read and write a file from your own assembly language program.

BGraph (0.1.8, 2023-10-15) (Public domain) 🐲

A graphics library that offers functions similar to Basic's LINE, DRAW, PAINT and CIRCLE commands. It does not assume the presence of the Color Basic interpreter. Requires CMOC 0.1.75 or later. Contains a new CoCo 3 driver and a demo for it. The driver takes care of the dirty work of bank switching to draw to the 320x200x16 screen. To create a CoCo 3 drawing program, copy the demo to a new C file, change the main drawing function to make your calls to draw(), paint(), printText(), etc., and link your C file with BGraph.

Supports clipping lines on a rectangle, using the Cohen-Sutherland algorithm, and drawing Catmull-Rom splines, as described in "Computer Graphics: Principles and Practice" (by Foley, van Dam, Feiner, Hughes, 2nd Edition, pp. 483, 505). A demo (cmdemo.bin) draws such curves, or lets the user place points with the joystick and draws a curve through them. These functions do not use floating-point arithmetic.

Version 0.1.8 adds a point() function to lores.h, to get the color of a pixel in the 32x16 screen (like POINT in Basic). It also adds shapes-demo.c, a demo that keeps drawing several shapes simulatenously using Primitive_line().

Download the CoCo disk image here.

BSound (0.1.3) (Public domain) 🐲

A library that offers functions similar to Basic's PLAY and SOUND commands. It can also play an array of 6-bit samples. It does not assume the presence of the Color Basic interpreter.

Version 0.1.3 (2022-12-18) adds a function that plays 6-bit samples at a given frequency. A demo is included (bsound.c). It generates and plays a square wave of varying tones and volumes.

BControl (0.1.5, 2024-08-29) (Public domain) 🐲

A library that offers functions similar to Color Basic's INKEY$, JOYSTK and BUTTON. It does not assume the presence of the Color Basic interpreter. Version 0.1.5 slightly optimizes the joystick comparator read routine with inline asm. (Not applicable to the OS-9 version.) It also removes UTF-8 characters from Keyboard.c.

Color Eights (0.1.14) (GPLv3) 🐲

A card game derived from Crazy Eights that I wrote with CMOC. Requires the Cardgame library (see below).

Cardgame (0.1.12, 2024-06-08) (Public domain) 🐲

A PMODE 4 (card) game library. Contains the generic code used by my Color Eights game: drawing and erasing cards (32x42 pixels), and drawing text (uppercase 32x24 grid), in a PMODE 4 screen. Beep and "white noise" functions. The 8x8 text font can be reused independently, as done by cc3dblb (see below).
With Version 0.1.12, OS-9 support has been restored. (The sound features are still not supported however.)
Since Version 0.1.11, the library does not assume the presence of Color Basic anymore.
Version 0.1.10 added drawCharWithoutMovingCursor(), moveCursorLeft(), invertCharAtCursor(), waitForKeyWithAnimatedCursor(), readLineFromKeyboard(), runPMode4GameDoubleBufferLoop().

cc3dblb (0.1.1) (Public domain)

A skeleton for a CoCo 3 double-buffering game. Start a new game project by renaming the files, then recode the onFlip() function. Uses the 8x8 text font from the Cardgame library to print text on the graphics screen. Requires Cardgame and BGraph (see above).

CoCo MiniLisp (by Jamie Cho)

A port of Rui Ueyama's MiniLisp. Version 0.5.0, released in October 2017, uses CMOC's support for 32-bit arithmetic.

xdaliclock port (by Jamie Cho)

A port of Jamie Zawinski's xdaliclock to the CoCo.

Splinter (by Jamie Cho)

A CoCo 3 break-the-bricks video game written by Jamie Cho with CMOC. Splinter features colorful 320x192 graphics and smooth animation.

hirestxt (0.4.2, 2024-11-28) (Public domain) 🐲

A library that redirects printf() to a software 51x24 or 42x24 black-on-green PMODE 4 text screen. (A sample program is included.) Optionally supports several VT52 terminal sequences. Useful to get true lowercase, including Latin-1 accented characters, on all CoCos. Usable under OS-9.

Version 0.4.2 added showOS9PMode4Screen(), quitOS9Graphics(), OS9Timer_init(), OS9Timer_shutdown() and OS9Timer_getTimerAddress() under OS-9. Version 0.4.1 added support for inverted colors and bold characters. A version of hirestxt is used by Michael Furman's DwTerm to provide a 51x24 mode.

Color Verbiste (0.1.5) (GPLv3)

A partial CoCo port of my French verb conjugator. Requires hirestxt. There is a precompiled disk image. Details on the Verbiste home page and its CoCo section.

nobasic (0.1.10) (Public domain*) 🐲

A program that puts the CoCo in all-RAM mode, tunes out the Basic interpreter, moves the program and the stack to the end of the 64K of RAM and redirects the 60 Hz interrupt, as an example of a program that can use the entire 64K of RAM. Contains a disk sector read demo and a CoCo 3 graphics mode demo.

bigapp (0.2.0) (Public domain)

A demo of a program that is too large to be loaded by Basic's LOADM command and can use the whole 64K of RAM. The user calls LOADM and EXEC on a small loader program that takes care of loading the large program. Requires a 64K CoCo and the decbfile library 0.1.6, available on this page.

In version 0.2.0 (2022-08-25), the app is now shipped in raw format instead of the BIN format, which simplifies the loader. The app (code and data) can now use RAM from $0400 to $FEED.

autostart.c (0.1.2) (Public domain)

A program to be compiled as a bootloader that goes on track 34, so that the CoCo's DOS command will execute it. (The autostart.bin file is not meant to be loaded with LOADM.) The program feeds Color Basic's console input with the command RUN"*.BAS" in order to run that Basic program automatically. Install this on a disk image with this command: install-coco-boot-loader foo.dsk autostart.bin

FuncPlot (0.2.4, 2024-03-10) (GPLv3)

A demo program that plots a mathematical function in PMODE 4 graphics. The program implements an expression parser and an RPN interpreter to evaluate the user's function across an interval. Requires hirestxt and BControl. Version 0.2.4 can be built to use the MC6839 ROM image by passing USE_MC6839=1 to make and using CMOC 0.1.86 or later.

Demo of Basic variable access from a CMOC program (Public domain)

(Updated 2018-04-03.) This archive contains a .dsk image file that contains VARPTR.BAS and VARPTR.BIN. Type RUN"VARPTR" on a CoCo. The archive also contains the C source file, which is compilable under CMOC. The Basic and C listings can be studied to learn how to access Basic variables from a CMOC program.

parse-coco-bin (Public domain)

A Perl script that lists the blocks of a CoCo Disk Basic .BIN file, along with the entry point.

Bouncy Ball (by Lee Patterson)

A game for all CoCos. (It does not come with the source code.)

CoCoTair: an 8080 emulator (by Mark Sherman)

This was Mark's Retrochallenge in 2017. This emulator can be used to run Altair BASIC. (To compile with CMOC 0.1.66 or later, the makefile of this project must be edited to remove the --a09=a09 option passed to CMOC.)

DwTerm (by Michael Furman)

A DriveWire 4 Terminal Program for the Disk Basic environment. Can be used with other DriveWire-related programs written by Michael.

makefile-example (0.1.0) (Public domain)

(2022-07-23) A minimal example of a program that is made of more than one C file, and that uses a makefile to build the program. This makefile automatically generates dependency files (.d). This means that after modifying a header file (.h), the next invocation of make will automatically recompile the .c files that depend on that .h file, and only those .c files. Learning to use makefiles is useful to handle increasingly large projects.

astar (0.1.0) (Public domain)

(2022-07-23) A* is a graph traversal and path search algorithm. This package offers an implementation that assumes that the graph is a rectangular grid.

Documentation

See the manual that comes with CMOC. This manual includes instructions on building CMOC from the sources.

I have written a small manual titled CMOC for BASIC Programmers, which may help Basic programmers who want a quick reference on mapping Basic constructs to their equivalents in C.

As of July 2022, I am developing CMOC on an Ubuntu 20.04 GNU/Linux system using GCC 9.3.0.

Building on Linux and FreeBSD

On Linux, the typical ./configure && make && make install sequence must be used. On FreeBSD, gmake must be used instead of make.

Building on Windows

CMOC cannot currently be compiled directly as a native Windows application, but it can be compiled under Cygwin. It has been shown to work under that Unix-like environment.

MinGW is not recommended because the pipe calls (popen()) do not behave as expected, as of Fall 2018. In particular, the apostrophes on the command lines composed by CMOC, when calling the C preprocessor, do not appear to be interpreted as they should by the shell called by popen().

Note that LWTOOLS should then also be compiled for Cygwin. Packages that were pre-built for Windows or MinGW will probably not work as CMOC expects.

CMOC is also likely to be functional under the Windows Subsystem for Linux (WSL) but I have not tested it there.

Building on Mac OS X

The configure script should recognize that it is running on a Mac OS X system, but if it does not, the following instructions may help:

Thanks to Jamie Cho for these Mac instructions.

Glen Hewlett has posted an article on his blog about using CMOC from Mac OS or Linux.

Other resources


Last update to this page: 2024-11-28 20:51:39 EST5EDT