π Cross-Compiling
Exploring the required Targets.
The Rust compiler functions as a cross-compiler by default. It allows us to translate our Rust code into the target platform and package it as a library. However, to enable this functionality, we need to ensure that all the required targets are installed on the host computer. In this chapter, we will delve into the relevant targets for IOTA for Flutter.
About Targets
In the context of software development, a "target" typically refers to the platform or environment for which software is being developed or compiled. The Components of a target specification can vary depending on the context and tooling being used.
-
Architecture: The target architecture specifies the instruction set and hardware architecture for which the software is being compiled or built. Examples include x86, x86_64, ARMv7, ARMv8, etc.
-
Vendor: The vendor component indicates the company or organization associated with the target platform. It helps identify the specific platform or ecosystem for which the software is intended. Examples include apple, android, linux, windows, etc.
-
Operating System: The operating system component represents the software layer that manages system resources and provides services to applications. It defines the environment in which the software will run. Examples include darwin (macOS, iOS), linux, windows, android, etc.
-
ABI (Application Binary Interface): The ABI component defines the interface between the compiled application code and the operating system and hardware. It defines how functions are called, how parameters and return values are passed, how memory is allocated, and other low-level details of interaction between software and the underlying system.
Targets needed for macOS and iOS Development
The Target Structure typically consists of the following Components:
<Architecture>-<Vendor>-<Operating System>
Target | Meaning |
---|---|
aarch64-apple-darwin | Targeting Apple devices running macOS with ARM 64-bit architecture (Apple Silicon). |
x86_64-apple-darwin | Targeting Apple devices running macOS with Intel 64-bit x86 architecture . |
aarch64-apple-ios | Targeting iOS devices with ARM 64-bit architecture, as used since the iPhone 5S and later, the iPad Air, Air 2 and Pro, with the A7 and later chips. |
armv7s-apple-ios | Targeting iOS devices with 32-bit ARMv7s architecture ("old"), used in A6 and A6X chips on iPhone 5, iPhone 5C and iPad 4. |
armv7-apple-ios | Targeting iOS devices with 32-bit ARMv7 architecture, used in A5 chip ("old"). |
aarch64-apple-ios-sim | Targeting iOS Simulator for Xcode 12 and later on hosts with ARM 64-bit architecture. |
x86_64-apple-ios-sim | Targeting iOS Simulator for Xcode 12 and later on hosts with 64-bit x86 architecture. |
i386-apple-ios | Targeting iOS Simulator on hosts with 32-bit x86 architecture ("old"). |
Example: My workstation computer is a MacBook Air with an M1 chip. Therefore, the following targets are essential for me when developing for macOS and iOS: aarch64-apple-darwin (for macOS), aarch64-apple-ios-sim (simulator for the M1 host environment), and aarch64-apple-ios (for iOS).
Targets needed for Android Development
In the context of IOTA for Flutter the Android Native Development Kit (NDK) must be installed. It is used to provide the necessary tools and APIs to interface with the cross-compiled library. The Target Structure then follows the format:
<Architecture>-<Operating_system>-<ABI*>
ABI* : As part of the Target, the ABI component is different to the correct ABI naming, due to historical reasons or to maintain compatibility. The correct ABI naming is listed in the second column.
Target | ABI | Meaning |
---|---|---|
aarch64-linux-android | arm64-v8a | Targeting Android devices on ARM 64-bit architecture (most modern ARM-based Android devices). |
armv7-linux-androideabi | armeabi-v7a | Targeting Android devices on ARMv7 architecture (older ARM-based Android devices). |
x86_64-linux-android | x86_64 | Targeting Android devices on 64-bit x86 architecture (Android emulators, modern x86-based devices). |
i686-linux-android | x86 | Targeting Android devices on 32-bit x86 architecture (Android emulators, older x86-based devices). |
Example: My only current Android Virtual Device is a Pixel 3a phone with arm64-v8a system image. Therefore the only interesting target for development is aarch64-linux-android.
Which targets are installed on my system?
To find out which targets are installed on your system, run the following command:
rustc --print target-list
How to add missing targets
When you first install a toolchain, rustup installs only the standard library for your host platform - that is, the architecture and operating system you are presently running. To compile to other platforms you must install other target platforms. This is done with the command:
rustup target add <target>
For example:
rustup target add armv7-linux-androideabi
π Β The Rustup Book - Cross-compilation
How to manually cross-compile to a target of your choice
Sometimes, you might need to cross-compile your Rust code to a specific target separately from the Flutter build process. To ensure that everything runs smoothly, make sure you are in the rust folder (on the same level as Cargo.toml).
Manually cross-compile for macOS or iOS
On macOS and/or iOS you can start the process by executing this command in the Terminal:
cargo build --target <target>
For example:
cargo build --target aarch64-apple-ios
Manually cross-compile for Android
On Android you can start the process by executing this command in the Terminal:
cargo ndk -t <abi> build
For example:
cargo ndk -t arm64-v8a build