1
votes

I am trying to create Rust bindings for the C++ library cryptominisat. The actual code works, but I'm not sure how to properly package it up with Cargo.

The git repository looks like

src/
    c++ code here
.gitignore
readme, etc.

I added a rust directory, and created my Cargo project inside of it like so

rust/
    cryptominisat/
        Cargo.toml
        build.rs
            src/
                rust code here
src/
    c++ code here
.gitignore
readme, etc.

Unfortunately, cargo package doesn't seem to want to package up anything outside of the rust/cryptominisat directory, which means it doesn't include the C++ code needed to actually build the library. What can I do? I don't want to move the entire repository into the rust directory if I can avoid it, since that would make it impossible to merge upstream.

1
What about a symlink? Or maybe the Rust bindings should be in a separate project and you could use a git submodule to reference the C++ code.Shepmaster
There are git tools (git submodule and git subtee) which make it easier to manage remote repositories inside your own. I can elaborate if that's a useful direction for you.Chris Emerson
The rust-lua53 project takes a different approach, and downloads the Lua source at build time from build.rs.Chris Emerson

1 Answers

3
votes

The way it's generally solved:

  • Use a git submodule (or a script run before publishing) to embed a copy of the C++ repo inside the Rust repo (e.g. in rust/cryptominisat/vendor/). During development you could use a symlink instead to avoid having two copies of the C++ code.

  • Use build.rs to download a tarball/clone/rsync the code at build time. You can dump it into OUT_DIR env var specified by Cargo to avoid polluting user-visible directories.

  • Make the C++ code a system-level library. The Rust package would not build it, but expect it's already installed, and only search for it and specify link flags for it. That's how most *-sys crates work.