Cross-language native dependency manager. Detect host lang, add libs via CLI, expose them in-process with equilibrium-ffi.
rig add --rust rx4
rig up
rig ui rx4
rig dr
Host projects consume native libs in-process; rotary (rx4) is a common Rust dep to expose into non-Rust hosts.
cargo install rigpkgOr from git:
cargo install --git https://github.com/tschk/rigBoth install the rig binary.
rig initWrites rig.toml + empty rig.lock. Detects host language from markers (Cargo.toml, build.zig, *.nimble, …).
rig add --rust rx4
rig i --cargo rx4
rig add --zig some_libAliases: i, install (short package-manager aliases).
Resolves the package, pins it in rig.toml / rig.lock, and auto-exposes a native in-process surface:
- Rust host ← cargo crate: adds the dep to
Cargo.tomland generatessrc/rig_bindings/<pkg>.rs(re-export + markers). - Zig host ← cargo crate: builds a generic
{crate}_fficdylib façade (markers:{crate}_abi_version/_version/_name), writessrc/rig_bindings/<pkg>_bindings.zig, and patchesbuild.zigwith// rig-expose-beginlink markers. - Nim host ← cargo crate: builds the same façade and writes
src/rig_bindings/<pkg>.nim(importc+passLlink hints). - C/C++ host ← cargo crate: builds the same façade and writes
src/rig_bindings/<pkg>.h(declarations +-L/-lmetadata macros). - C# host ← cargo crate: builds the same façade and writes
src/rig_bindings/<pkg>.cs(DllImportP/Invoke wrappers). - D host ← cargo crate: builds the same façade and writes
src/rig_bindings/<pkg>.d(extern(C)+pragma(lib)). - V host ← cargo crate: builds the same façade and writes
src/rig_bindings/<pkg>.v(#flag+fn C.…). - Odin host ← cargo crate: builds the same façade and writes
src/rig_bindings/<pkg>.odin(foreign import+foreignblock). - Hare host ← cargo crate: builds the same façade and writes
src/rig_bindings/<pkg>.ha(@symbolC ABI decls +-L/-lhints). - C/C++/Zig/Nim/V/Odin/Hare/C#/D host ← path/git c|cpp|zig|nim|v|odin|hare: compiles into
target/rig/<pkg>/lib*_native.{dylib,so}when feasible (flat sources, Makefile$OUT, CMake, meson, or language toolchain); honest error if the toolchain is missing. Simple C prototypes from discovered headers (and Zigexport fnwhen the dep is Zig) are emitted into Nim/V/Zig/Odin/Hare/C#/D binders. - Rust host ← foreign lang: generates an equilibrium-ffi
loadpath stub.
Ecosystem flags (mutually exclusive): --cargo/--rust, --zig, --nim, --c, --cpp, --v, --d, --odin, --hare, --csharp/--cs.
rig up
rig upgrade rx4rig ui rx4
rig rm rx4Aliases: rm, ui, uninstall.
rig ls
rig s serde
rig search --nim jester
rig search --d vibe
rig search --csharp Newtonsoft.Json
rig search --zig http # GitHub hints; no central Zig registry
rig search --c foo # clear unsupported (use path:/git+)
rig show rx4
rig info --nim jester
rig outdatedRegistry-backed today: cargo (crates.io), nim (nimble packages.json), d (code.dlang.org), csharp (NuGet).
zig accepts path: / git+ / https:// pins (search is hint-only).
c / cpp / v / odin / hare are path/git pins only.
rig lock
rig syncrig dr
rig check --fix --full
rig buildexamples/zig-host-rx4— Zig ←rx4via thinrx4_ffifaçade + equilibrium-ffi.examples/zig-host-multi— Zig ← multiple cargo crates (rx4+sha2) via the generic façade.examples/c-host-sha2— C ←sha2markers +sha2_hash_256/sha2_hash_512(cc+-lsha2_ffi).examples/c-host-libm— C ← auto-wrappedlibm(libm_sqrt, …) beyond markers.
cd examples/zig-host-rx4
rig init
rig add --rust rx4
zig build run
cd ../zig-host-multi
rig sync
zig build runFor every rig add --rust <crate> on a Zig (or other non-Rust) host, rig generates a thin cdylib under .rig/shims/<crate>/ (unless the crate already ships crate-type = ["cdylib"], in which case that library is linked through):
| Symbol | Meaning |
|---|---|
{crate}_abi_version |
Façade ABI revision (u32) |
{crate}_version |
Null-terminated version string |
{crate}_name |
Null-terminated crate name |
Known enrichments (today: rx4, sha2, crc32fast, md-5, hex, base64) may export additional methods beyond the markers (e.g. rx4_prompt_smoke, sha2_hash_256, hex_encode, base64_encode).
For other crates, rig auto-wraps a scanned public surface when sources are available (cargo registry / path / crates.io fetch):
- Existing
#[no_mangle] extern "C"functions are re-exported under the same name. - Plain
pub fn/pub const fnwith only FFI-safe scalar/pointer types become{crate}_{fn}exports (façade ABI 2). - Host binders (Zig/Nim/C/C#/D) emit the discovered declarations; see
.rig/shims/<crate>/surface.json.
- Skipped: generics,
async,implmethods/traits, tuples/arrays/refs,str/String/Vec,f16/f128,Option<scalar>(non-niche), and other non-FFI-safe types. - Wrapped niches (safe):
Option<*T>/Option<NonNull<T>>/NonNull<T>/NonZero*/*const ()/*mut (), plus morecore::ffi::c_*aliases;extern "C-unwind"treated likeextern "C". - cbindgen runs only when the crate ships
cbindgen.tomland thecbindgenbinary is onPATH(provenance header only; scan remains canonical). - Crates with
#![forbid(unsafe_code)]still work: unsafe lives only in the generated façade. - Auto-wrap caps at 256 symbols per crate; enrichments remain intentional for trait-heavy APIs (e.g.
sha2_hash_256). - Rust hosts keep the native Cargo re-export path (
src/rig_bindings/<pkg>.rs); the cdylib façade is for cross-language hosts.
See committed example rig.toml. Schema:
[host].language— rust | zig | nim | c | cpp | v | d | odin | hare | csharp[dependencies.<name>]— ecosystem, version, git/path, features, expose[expose].dir— defaultsrc/rig_bindings(usesrc/vendorfor Zig/C imports)
Lockfile: rig.lock (commit it).
| Language | Markers |
|---|---|
| Rust | Cargo.toml |
| Zig | build.zig, build.zig.zon |
| Nim | *.nimble, nimble.paths |
| D | dub.json, dub.sdl |
| C# | *.csproj, *.sln |
| V | v.mod |
| Odin | ols.json, *.odin |
| Hare | *.ha |
| C / C++ | CMakeLists.txt, meson.build, Makefile + sources |
Equilibrium-supported set: V, Zig, C, C++, C#, Rust, D, Nim, Odin, Hare.
ISC
GitHub Actions runs fmt / clippy -D warnings / cargo test on Ubuntu + macOS (+ Windows tests).
An optional path-c-smoke job on Ubuntu exercises flat-C and CMake path/git fixtures via scripts/ci-smoke-path-c.sh (cmake/ninja; meson when present).
scripts/ci-smoke-path-extra.sh additionally tries a Zig path fixture when zig is on PATH (skipped otherwise). Nim/V/Odin/Hare e2e compile smokes run locally when those toolchains are present (cargo test skips them quietly on stock CI).