For a sideproject of mine I wanted to use rust inside Magic Mirror which is written in nodejs. So it was instantly clear to me that I need neon to help me talk to Rust from node. This will document how I got it to cross-compile on my mac for the raspberrypi where it is actually running.

If you only need cross-compilation please use Cross.

I assume you want to cross-compile an existing neon-module. All path are relative to the neon-root-folder (the one containing the native folder).

  1. Build the build-Container

    1. git clone https://github.com/piceaTech/rust-on-raspberry-docker
    2. cd rust-on-raspberry-docker
    3. git checkout neon
    4. If you need another node version than the current LTS-Version: Edit the Dockerfile and switch to correct BaseImage.
    5. docker build --tag "neon-pi-cross:latest" .
  2. Follow instructions for native dependencies (https://github.com/piceaTech/rust-on-raspberry-docker/tree/neon#platform-dependencies-optional)

    • the default location in the script from the following step is in native/pi_deps (you can customise it in the build.sh file)
  3. copy the file found here into your native folder

    • This is not strictly needed but I found it easier to compile the neon module with it instead of a long command line
  4. fix the native code

    1. Add a .cargo/config file in your module with the following content
      [target.arm-unknown-linux-gnueabihf]
      
      rustflags = ["-C", "link-arg=-Wl,-init=node_addon_init"]
      
    2. Change the crate-type to crate-type = ["cdylib"] in your native/Cargo.toml
  5. Inside your neon-folder run native/build.sh. This should create a native/index.node which should be compatible with arm.

  6. Deploy this artifact to the pi!

  7. Done

With this PR beeing merged and hopefully released soon it will build like a breese. Until then you sadly have to monkey patch that in by yourself.

I was/am using neon-serde but I noticed that it doesn't work on 32-bit systems because a lib it depends on is changing return value based on the arch. So I had to patch before it actually ran. See the PR I created

Helpful error-messages collection

As I was working through the issues I often came across the same problems of other people. Some interesting links to look at if you see similar problems:

  • Module did not self-register
    • https://github.com/neon-bindings/neon/issues/362#issuecomment-425814276
      • https://github.com/katyo/ledb/commit/0e7fbce88be5471bf52bcf69b5824d2f90cc6baa
      • https://github.com/katyo/neon/commit/3319c6ce54ba67451b236901ca0669397d68c659
  • Cross compiling gist
    • https://gist.github.com/crabtw/5150198
  • Codegen options
    • https://doc.rust-lang.org/rustc/codegen-options/index.html
  • cross compile node gyp
    • https://stackoverflow.com/questions/6696222/cross-compiling-with-gyp -common|optimizers|params|target|warnings|[^]{joined|separate|undocumented
  • Strangly Openssl was not packaged to be used with this setup in mind. So I had to copy out some files
    • cp $OPENSSL_INCLUDE_DIR/arm-linux-gnueabihf/openssl/opensslconf.h $OPENSSL_INCLUDE_DIR/openssl/