Even though `Int` and `isize` should be the same in practice, we can't cleanly convert, as the type information isn't quite there. And anyway, strictly speaking per the report, `Int` is only guaranteed to hold 30 bits.
Note that this is essentially unchanged even if we specify `usize_is_size_t = true` for `cbindgen`.
We drop the tools specifically designed for Haskell and Rust together, in favour of general tools for using each with C.
Namely, we use Mozilla's `cbindgen` for generating header files from the Rust source, and Well-Typed's new `hs-bindgen` tool for generating Haskell from those header files.
The Rust code here is essentially the result of expanding the old macro, then inlining and renaming internals.
The most important thing here is that we're now relying solely on robust well-maintained tools.
See https://sraka.xyz/posts/hs-bindgen-introduction.html.
For now, this is a shell-based workflow, rather than using Nix to build everything, i.e. `nix develop` works but `nix build` doesn't. And `cargo build` has to be called manually to create the C library, rather than `cabal` being clever enough to invoke it itself.
We ran `cargo cabal init` from the `rust` directory (`nix shell github:yvan-sraka/cargo-cabal`), which generated `hsbindgen.toml` (which we use), and `Setup.lhs` (which just added `extra-lib-dirs`, and with the wrong paths, so we dspecify those statically instead in `garnet.cabal`). We also follow its advice to use `staticlib`.
Also, after we ran the first `cargo build` (requiring a `mkdir rust/src` before it would run), we took the generated the Haskell file, and moved the main contents in to `Main.hs` manually.