Skip to content

Instantly share code, notes, and snippets.

@amshinde
Last active March 2, 2023 17:25
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save amshinde/efbbdc41fc022a6ced4e9cec244c3cfe to your computer and use it in GitHub Desktop.
Save amshinde/efbbdc41fc022a6ced4e9cec244c3cfe to your computer and use it in GitHub Desktop.

Guide for Cross-compilation of rust binaries (for eg. s390x)

The following steps describe the setup required to cross-compile a rust binary on a amd64 platform. These steps setup the cross-compile toolchain on the host itself. After going through these steps manually, I came accross a tool cross that makes the process way easier. It uses docker for the build and does not require any changes to the host. Jump to the section directly if you dont want to make any changes to the host.

Install the cross-compiler for s390x

sudo apt-get install crossbuild-essential-s390x

The above package installs both the GNU C and C++ compiler for s390x.

Add architecture to dpkg:

dpkg --add-architecture s390x
# replace 'deb' with 'deb [arch=amd64]'
sudo sed 's/^deb http/deb [arch=amd64] http/' -i '/etc/apt/sources.list'

Add the apt mirror servers for s390x

Add a file /etc/apt/sources.list.d/s390x.list containing the s390x mirror servers. These will be used to install s390x package for openssl which is required by Kata rust binary.

echo >/etc/apt/sources.list.d/s390x.list <<EOF
deb [arch=s390x] http://ports.ubuntu.com/  focal-security  main restricted universe multiverse
deb [arch=s390x] http://ports.ubuntu.com/  focal           main restricted universe multiverse
deb [arch=s390x] http://ports.ubuntu.com/  focal-updates   main restricted universe multiverse
EOF
sudo apt-get update

Install dependency libraries

sudo apt install libssl-dev:s390x

Add target architecture to rust toolchain

rustup target add s390x-unknown-linux-gnu

Compilation and linking with cargo

You can now compile with:

export PKG_CONFIG_PATH=/usr/lib/s390x-linux-gnu/pkgconfig 
export PKG_CONFIG_ALLOW_CROSS=1 
cargo  build  --target=s390x-unknown-linux-gnu

The kata binary like the kata-agent or kata-ctl should now compile, but it will error out during the linking process. This is because cargo needs to be passed the linker, as it ends up using the host linker otherwise. You can pass the linker to cargo using env variable:

ENV CARGO_TARGET_S390X_UNKNOWN_LINUX_GNU_LINKER="s390x-linux-gnu-gcc"`

Or you can specify the linker as:

RUSTFLAGS="-C linker=s390x-linux-gnu-gcc" cargo build --target=s390x-unknown-linux-gnu

Fortunately, cross-compile support has been added to Kata makefiles. You can avoid the setup for linker and specify the architecture while running make as:

CC="s390x-linux-gnu-gcc" ARCH=s390x make

Cross Compiling with cross

The project cross is maintained by the cross-rs team and allows you to easily cross-compile Rust projects using Docker, without messing with your system or creating custom Dockerfiles.

Installation

It can be installed with:

cargo install -f cross

The list of targets supported can be seen here: https://github.com/cross-rs/cross/tree/main/docker

Build

To build for s390:

cross build  --target=s390x-unknown-linux-gnu

Add dependencies

cross enables you to add dependencies and run other necessary commands in the image before using it. For adding the libssl dependency required for Kata Containers, add it as a pre-build hook like so:

echo > Cross.toml <<EOF
[target.s390x-unknown-linux-gnu]
pre-build = ["dpkg --add-architecture s390x && apt-get update && apt-get install --assume-yes libssl-dev:s390x"]
EOF
cross build  --target=s390x-unknown-linux-gnu

Cross.toml needs to be in the rust project root directory.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment