srmech — C library¶
Native-C parity surface for the srmech Python package's
Attested Multi-Source Collector (AMSC) framework. Ports the three
load-bearing AMSC primitives to portable C so srmech meets the same
Python/C parity discipline that
ephemerides-spectral
uses. Same monorepo, same quality bar.
Status — full 14-class native C parity shipped¶
The full 14-class A–N C-parity primitive vocabulary is implemented
in native C and ships in every platform wheel as
libsrmech.{so,dll,dylib}. The Python package binds it through a
ctypes shim (srmech.amsc._native) and falls back to a complete
pure-Python implementation of every API surface when no native
library is present (Pyodide / WASM, or any environment where the
shared library can't load). srmech is at v0.6.0rc9; this is no
longer scaffolding.
Source files (c/src/)¶
| File | Surface |
|---|---|
srmech_sha256.c |
Class A — FIPS 180-4 SHA-256 content-addressing |
srmech_ndjson.c |
Class C — streaming NDJSON line reader |
srmech_cyclic.c |
Class I — cyclic-group / modular arithmetic |
srmech_laplacian.c |
Class L — dense graph Laplacian + Jacobi eigvals |
srmech_primes.c |
Class J — primality / factorisation / order |
srmech_tlv.c |
Class B — TLV byte-canonical framing |
srmech_search.c |
Class G — byte-pattern search |
srmech_meta.c |
Class H — version + ABI self-introspection |
srmech_dispatch.c |
Class D — multi-needle pattern dispatch |
srmech_catalog.c |
Class E — sorted-key catalog lookup |
srmech_template.c |
Class F — template {key} substitution |
srmech_hdc.c |
Class M — HDC bind / bundle / permute / similarity |
srmech_rational.c |
Class N — rational approximation (best-rational) |
srmech_kepler.c |
equation-of-centre / Kepler algebra (libm) |
srmech_cascade.c |
cascade-composition primitives |
srmech_bus.c |
bus / handle-registry surface |
srmech_parallel.c |
Klein-4 four-sector parallel dispatch |
srmech_kuramoto.c |
native Kuramoto coupled-oscillator step |
The two newest v0.6.0 C files:
srmech_parallel.c— the Klein-4 four-sector parallel dispatch (#771 / #778), with a portable thread shim that selects pthreads, Win32CreateThread, or a serial fallback at build time so the same source compiles cleanly across the CI matrix.srmech_kuramoto.c— the native Kuramoto coupled-oscillator forward-Euler step (rc9), using libmsinexactly assrmech_kepler.cdoes.
ABI¶
C ABI version is 3 (SRMECH_ABI_VERSION 3 in
c/include/srmech.h). Bump it in lockstep only when the wire
format of an existing exported function changes; adding a new
symbol does not bump the ABI.
JPL Power-of-Ten¶
The C library is JPL Power-of-Ten clean — see
JPL_AUDIT.md for the rule-by-rule audit.
Enforcement is mechanical: tests/test_jpl_audit.py is a ratchet
(violations only ever go down) and the pedantic-build CI matrix
(-Werror / -Wpedantic, /WX on MSVC) runs on
Linux gcc / macOS clang / Windows MSVC, so any new warning fails CI.
Each rc auto-routes to TestPyPI via the rc-suffix gate in
srmech-publish.yml. A non-rc tag is the human-in-loop gate for
the production PyPI ship.
Why C¶
srmech is data-pipeline tooling, not embedded firmware — but C buys us three things ephemerides-spectral has already validated:
- Performance on hot paths. Every catalog read walks NDJSON; every descriptor edit recomputes the canonical-TOML hash; SHA-256 attestation is per-row at codegen time. The Python paths stay correct; C is the fast path runtime can opt into.
- Parity discipline as quality ratchet. The byte-exact Python/C parity tests catch any drift in either implementation. The C side is harder to get right; passing parity is evidence the Python side is also correct.
- JPL Power-of-Ten discipline (Phase B6). The same rules ephemerides-spectral's C library passes — Rule 1 (no goto), Rule 3 (no malloc), Rule 4 (<60-line functions), Rule 5 (≥2 assertions per function), Rule 6+7 (scope + return-value checks), Rule 10 (cross-platform pedantic-build CI matrix).
Layout¶
c/
├── include/srmech.h # public API (Phase B1)
├── src/ # implementation .c files (B3–B5)
│ └── .gitkeep # placeholder; empty at B1
├── test/ # C smoke + cross-language parity
│ └── .gitkeep # placeholder; empty at B1
├── Makefile # local build/test/parity flow
├── JPL_AUDIT.md # JPL Power-of-Ten compliance log
├── .gitignore # build/
├── .pages # mkdocs nav
└── README.md # this file
The top-level CMakeLists.txt lives one directory up at
docs/srmech/CMakeLists.txt, mirroring ephemerides-spectral's
docs/antikythera-maths/ephemerides-spectral/CMakeLists.txt.
scikit-build-core (wired in Phase B2) drives it via
cmake.source-dir = ".." from python/pyproject.toml.
Build & test (post-B3)¶
cd c
# Build the static library
make lib
# Build + run the C smoke tests
make test
# Build + run the cross-language parity test
make parity
# Clean
make clean
make defaults to cc -std=c17 -Wall -Wextra -Wpedantic -O2 -fPIC.
Override CC and STD for cross-compilation; the source compiles
cleanly under C11.
Windows note¶
The feedback_run_wsl_smoke_before_amsc_push memory applies once
real C code lands. WSL2 catches libm last-bit divergence that
Windows-local pytest doesn't. Run scripts/smoke_local.sh (or the
equivalent) under WSL before pushing any branch that touches C
source.
License¶
GPL-3.0-or-later (parent project: mlehaptics).