parent
ea189123e2
commit
db229315e3
@ -1,3 +1,4 @@ |
||||
target |
||||
result |
||||
result-* |
||||
*.tmp |
||||
|
@ -1,4 +1,60 @@ |
||||
# Cross compilation with `rust-overlay` |
||||
|
||||
There an example for cross compilation to `aarch64-linux` in |
||||
[`example/cross-aarch64`](../examples/cross-aarch64). |
||||
There are examples for cross compilation in [`example` directory](../examples). |
||||
To try examples, |
||||
1. `cd` into `example/cross-aarch64` (or other directory). |
||||
2. `nix-shell` to enter the development environment. |
||||
3. `make run` to build and run the program in an emulater. |
||||
|
||||
The structure of `shell.nix` should like this, |
||||
```nix |
||||
# Import from global `<nixpkgs>`. Can also be from flake input if you like. |
||||
(import <nixpkgs> { |
||||
# Target triple in nixpkgs format, can be abbreviated. |
||||
# Some special targets, like `wasm32-wasi`, need special configurations here, check |
||||
# `examples/cross-wasi/shell.nix` for details. |
||||
crossSystem = "aarch64-linux"; |
||||
# Apply `rust-overlay`. |
||||
overlays = [ (import ../..) ]; |
||||
|
||||
# Workaround: we need `callPackage` to enable auto package-splicing, thus we don't need to manually prefix |
||||
# everything in `nativeBuildInputs` with `buildPackages.`. |
||||
# See: https://github.com/NixOS/nixpkgs/issues/49526 |
||||
}).callPackage ( |
||||
{ mkShell, stdenv, rust-bin, pkg-config, openssl, qemu }: |
||||
mkShell { |
||||
# Build-time dependencies. build = host = your-machine, target = aarch64 |
||||
# Typically contains, |
||||
# - Configure-related: cmake, pkg-config |
||||
# - Compiler-related: gcc, rustc, binutils |
||||
# - Code generators run at build time: yacc, bision |
||||
nativeBuildInputs = [ |
||||
# `minimal` is enough for basic building and running. |
||||
# Can also be `default` to bring other components like `rustfmt`, `clippy`, and etc. |
||||
rust-bin.stable.latest.minimal |
||||
pkg-config |
||||
]; |
||||
|
||||
# Build-time tools which are target agnostic. build = host = target = your-machine. |
||||
# Emulaters should essentially also go `nativeBuildInputs`. But with some packaging issue, |
||||
# currently it would cause some rebuild. |
||||
# We put them here just for a workaround. |
||||
# See: https://github.com/NixOS/nixpkgs/pull/146583 |
||||
depsBuildBuild = [ qemu ]; |
||||
|
||||
# Run-time dependencies. build = your-matchine, host = target = aarch64 |
||||
# Usually are libraries to be linked. |
||||
buildInputs = [ openssl ]; |
||||
|
||||
# Tell cargo about the linker and an optional emulater. So they can be used in `cargo build` |
||||
# and `cargo run`. |
||||
# Environment variables are in format `CARGO_TARGET_<UPPERCASE_UNDERSCORE_RUST_TRIPLE>_LINKER`. |
||||
# They are also be set in `.cargo/config.toml` instead. |
||||
# See: https://doc.rust-lang.org/cargo/reference/config.html#target |
||||
CARGO_TARGET_AARCH64_UNKNOWN_LINUX_GNU_LINKER = "${stdenv.cc.targetPrefix}cc"; |
||||
CARGO_TARGET_AARCH64_UNKNOWN_LINUX_GNU_RUNNER = "qemu-aarch64"; |
||||
}) {} |
||||
``` |
||||
|
||||
For more details about these different kinds of dependencies, |
||||
see also [Nix Wiki - Cross Compiling](https://nixos.wiki/wiki/Cross_Compiling#How_to_specify_dependencies). |
||||
|
@ -1,6 +0,0 @@ |
||||
[build] |
||||
target-dir = "target" |
||||
|
||||
[target.aarch64-unknown-linux-gnu] |
||||
linker = "aarch64-unknown-linux-gnu-gcc" |
||||
runner = "qemu-aarch64" |
@ -1,9 +1,11 @@ |
||||
.PHONY: all test |
||||
# This Makefile is expected to be run inside nix-shell.
|
||||
|
||||
test: all |
||||
nix-shell ./shell.nix --command \
|
||||
"cargo test --target aarch64-unknown-linux-gnu"
|
||||
CARGO_FLAGS := --target aarch64-unknown-linux-gnu
|
||||
|
||||
.PHONY: all |
||||
all: Cargo.toml Cargo.lock src/main.rs |
||||
nix-shell ./shell.nix --command \
|
||||
"cargo test --target aarch64-unknown-linux-gnu --no-run"
|
||||
cargo build $(CARGO_FLAGS)
|
||||
|
||||
.PHONY: test |
||||
run: all |
||||
cargo run $(CARGO_FLAGS)
|
||||
|
@ -1,22 +1,19 @@ |
||||
# See docs/cross_compilation.md for details. |
||||
(import <nixpkgs> { |
||||
crossSystem = "aarch64-linux"; |
||||
overlays = [ (import ../..) ]; |
||||
}).callPackage ( |
||||
{ mkShell, rust-bin, pkg-config, openssl, pkgsBuildBuild }: |
||||
{ mkShell, stdenv, rust-bin, pkg-config, openssl, qemu }: |
||||
mkShell { |
||||
nativeBuildInputs = [ |
||||
# Manual `buildPackages` is required here. See: https://github.com/NixOS/nixpkgs/issues/49526 |
||||
# build = host = x86_64, target = aarch64 |
||||
rust-bin.stable.latest.minimal |
||||
pkg-config |
||||
|
||||
# build = host = target = x86_64 |
||||
# qemu itself is multi-platform and `target` doesn't matter for it. |
||||
# Use build system's to avoid rebuild. |
||||
pkgsBuildBuild.qemu |
||||
]; |
||||
buildInputs = [ |
||||
# build = x86_64, host = target = aarch64 |
||||
openssl |
||||
]; |
||||
|
||||
depsBuildBuild = [ qemu ]; |
||||
|
||||
buildInputs = [ openssl ]; |
||||
|
||||
CARGO_TARGET_AARCH64_UNKNOWN_LINUX_GNU_LINKER = "${stdenv.cc.targetPrefix}cc"; |
||||
CARGO_TARGET_AARCH64_UNKNOWN_LINUX_GNU_RUNNER = "qemu-aarch64"; |
||||
}) {} |
||||
|
@ -0,0 +1,7 @@ |
||||
# This file is automatically @generated by Cargo. |
||||
# It is not intended for manual editing. |
||||
version = 3 |
||||
|
||||
[[package]] |
||||
name = "cross-wasi" |
||||
version = "0.1.0" |
@ -0,0 +1,8 @@ |
||||
[package] |
||||
name = "cross-wasi" |
||||
version = "0.1.0" |
||||
edition = "2021" |
||||
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html |
||||
|
||||
[dependencies] |
@ -0,0 +1,11 @@ |
||||
# This Makefile is expected to be run inside nix-shell.
|
||||
|
||||
CARGO_FLAGS := --target wasm32-wasi
|
||||
|
||||
.PHONY: all |
||||
all: Cargo.toml Cargo.lock src/main.rs |
||||
cargo build $(CARGO_FLAGS)
|
||||
|
||||
.PHONY: test |
||||
run: all |
||||
cargo run $(CARGO_FLAGS)
|
@ -0,0 +1,21 @@ |
||||
# See docs/cross_compilation.md for details. |
||||
(import <nixpkgs> { |
||||
crossSystem = { |
||||
config = "wasm32-wasi"; |
||||
# Nixpkgs currently only supports LLVM lld linker for wasm32-wasi. |
||||
useLLVM = true; |
||||
}; |
||||
overlays = [ (import ../..) ]; |
||||
}).callPackage ( |
||||
{ mkShell, stdenv, rust-bin, wasmtime }: |
||||
mkShell { |
||||
nativeBuildInputs = [ rust-bin.stable.latest.minimal ]; |
||||
|
||||
depsBuildBuild = [ wasmtime ]; |
||||
|
||||
# This is optional for wasm32-like targets, since rustc will automatically use |
||||
# the bundled `lld` for linking. |
||||
# CARGO_TARGET_WASM32_WASI_LINKER = "${stdenv.cc.targetPrefix}cc"; |
||||
CARGO_TARGET_WASM32_WASI_RUNNER = "wasmtime"; |
||||
}) {} |
||||
|
@ -0,0 +1,3 @@ |
||||
fn main() { |
||||
println!("Hello, world!"); |
||||
} |
Loading…
Reference in new issue