Skip to content

Latest commit

 

History

36 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Scientific programming in Modula-9 — first steps

The compiler, runtime and standard library this tutorial teaches are in the m9c repository (./build.sh needs gcc and nothing else), and so are the install packages for six Linux distributions -- and, from 0.8.0, an experimental Windows zip -- on its release page.

M9 (Modula-9) is a Wirth-family language for scientific computing, designed so the result can be trusted and reproduced — by your reviewer, by your future self, by whoever inherits the code. You get exactly what is written, and when what is written is wrong the compiler tells you and refuses to run it, rather than letting the program go quietly on and publish a number no one can reproduce. Every import is named, every numeric width is exact, every error a procedure can raise is written in its signature, every allocation says which pool owns it — and the safety checks are part of what a program means, always on, with no build that leaves them out. The cost is a little more typing; the return is code a colleague, a reviewer, or a student can read and trust without running it, that still rebuilds and gives the same bits years from now.

The tutorial is live at tutorial.modula9.net — every code example on those pages is editable and runs, sandboxed, on the server; what you read here is the same material, gated by the same tests.

The tutorial service is, of course, written entirely in M9 — the HTTP server, the compile-and-run sandbox pipeline, the whole backend — with a little JavaScript on the frontend for the editable cells. Serving the tutorial with the language it teaches is the claim made structural.

This repository holds the tutorial's example programs, the full tutorial text (tutorial/, the same chapters the site serves), and the M9 compiler package.

License

Code — the examples, the tutorial text, the M9 compiler in the package — is licensed under the GNU GPL v3 (see LICENSE). The measurement data in examples/data/icos-obspack.zarr remains CC BY 4.0 by the ICOS data licence (doi:10.18160/JZ2X-GZGU); cite ICOS when you use it.

The language itself is defined in one document, the M9 report -- the normative specification, where every rule is stated together with the observed failure that made it a rule. These chapters teach by worked example; that is where the rules live.

Install

The compiler's release page carries one package per distribution — Ubuntu 24.04 and 26.04, Debian 13, Fedora 43, Rocky 9 (RHEL 9 family) and Arch, x86-64 — each built on that distribution from the one attached source tarball and made to compile and run an M9 program there before it was published; the .receipt beside each says on what, with which gcc, and its sha256. gcc is the only compiler any of them needs. For Ubuntu 24.04:

sudo apt install ./m9_0.10.0-1_amd64.ubuntu24.04.deb

(dnf install ./m9-0.10.0-1.fc43.x86_64.rpm, ./m9-0.10.0-1.el9.x86_64.rpm, pacman -U ./m9-0.10.0-1-x86_64.pkg.tar.zst for the others; chapter 0 of the tutorial has the whole table.) This installs m9c (the compiler), the runtime, the standard library as readable M9 source in /usr/lib/m9, per-module reference pages in /usr/share/doc/m9/modules, man m9c, and a VS Code extension (syntax highlighting, hover documentation, completion) at /usr/share/m9/vscode-m9 — link it once with:

ln -s /usr/share/m9/vscode-m9 \
      ~/.vscode/extensions/atverm.m9-lang-0.2.0

The package is built on Ubuntu 26.04 for amd64. On another release the C library versions will not match — the compiler itself needs nothing but gcc, so building from source is the route there.

Windows, experimental. The same page carries m9-0.10.0-windows-x86_64.zip: one folder with its own gcc in it and an install.bat that compiles the compiler on your machine. It is verified under wine and on one Windows machine, and two chapters do not work there yet — 14 (netCDF resolves paths its own way on Windows) and 17 (it runs sort and uniq). Chapter 0 has the details.

The first program

git clone https://github.com/atverm/M9Tutorial
cd M9Tutorial/examples
m9c --make -o hello C1Hello.m9
./hello

m9c checks the program, generates C11, and drives gcc; --make also builds any imported library module. A refused program prints its diagnostics with line and column and writes nothing.

The examples

Every example is a complete program, and each lands one idea:

file the idea
C1Hello.m9 a module's body is the program; the root EXCEPT block is where failure is decided
C1Bounds.m9 a deliberate run off the end of an array: the access raises IndexError instead of reading past it
C2Widths.m9 exact widths; conversions are calls that RAISE when the value does not fit — I64 (NaN) included
C2Wrap.m9 checked + raises Overflow, always; wraparound is a different operator, +%, visible and greppable
Temps.m9 a DEFINITION is a checked contract: exceptions with payloads, complete RAISES lists
C3Use.m9 the client's side: the handler that names the module's exception and binds its payload
C4Mem.m9 memory made visible: pools own storage, slices view it, VAR says who writes, strings are slices of CHAR — with the docstring convention modelled
C5Csv.m9 reading data with declared column kinds and a declared missing value — nothing inferred
C6Stats.m9 mean, percentiles, regression and Welch's t-test with real p-values (gated digit-for-digit against scipy)
C6Nan.m9 a NaN in a sample RAISES; skipping gaps is the caller's one visible line
C7Series.m9 timeseries with resolution and time convention as data; per-column averaging rules, epoch-aligned windows
C8Zarr.m9 a zarr store over HTTP: checked shapes, NaN fills for deleted chunks, ownership that makes use-after-close uncompilable
C9Plot.m9 figures as deterministic SVG strings — a plot you can cmp
C10Icos.m9 the capstone: nine years of real ICOS CO2 (Hyltemossa, 150 m) from the Carbon Portal's zarr service — QC by the station's flags, a Fourier fit of trend + seasonal cycle, plotted. Point it at https://zarr.icos-cp.eu/icos-obspack.zarr and it reads the live service; examples/data/icos-obspack.zarr is a raw byte mirror of the same arrays for offline runs (ICOS ObsPack, CC BY 4.0, doi:10.18160/JZ2X-GZGU)

The four X*.m9 files must not compile — each carries an EXPECT-ERROR line naming the diagnostic the compiler must give: implicit conversion refused, an undeclared RAISES, a signature that drifts from its definition, a promised procedure never implemented, a pool-interior pointer escaping the frame that owns it.

expect/ holds the exact output of every runnable example; the upstream repository's CI compiles and runs all of them on every commit and compares byte for byte, so these programs cannot drift from the compiler you just installed.

Chapter 7 wants a local zarr store to read: any HTTP server over a zarr v2 directory works, and the example takes the URL as its first argument.

Chapters 7 and 8 bind C libraries (blosc; the SVG number formatter), so their build lines name those — see the comments in the files.

About

Scientific programming in Modula-9 (M9) — first steps: tutorial examples and the compiler package

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages